text:
#ifndef ATL_FFI_HPP
#define ATL_FFI_HPP
/**
 * @file /home/ryan/programming/atl/ffi_2.hpp
 * @author Ryan Domigan <ryan_domigan@sutdents@uml.edu>
 * Created on Dec 29, 2013
 */

#include <array>                           // for tuple_element
#include <boost/mpl/aux_/adl_barrier.hpp>  // for mpl
#include <cstddef>                         // for size_t
#include <functional>                      // for function
#include <string>                          // for string
#include <tuple>                           // for tuple
#include <type_traits>                     // for remove_pointer

#include "./helpers/make_ast.hpp"          // for fn
#include "./type.hpp"                      // for iterator, Ast, tag, value_...
#include "./type_traits.hpp"               // for cxx_to_atl
#include "./utility.hpp"                   // for Apply, BuildIndicies, Indexer
#include "gc/marked.hpp"                   // for Marked
#include "helpers/misc.hpp"                // for from_bytes, to_bytes
#include "wrap.hpp"                        // for value

namespace atl {
	namespace mpl = boost::mpl;

	namespace byte_code
	{
		typedef typename vm_stack::value_type value_type;
		template<class T>
		vm_stack::value_type to_bytes(T input)
		{ return reinterpret_cast<vm_stack::value_type>(input); }

		// TODO: use the `std::is_integral` and static cast for all integral (and floating?) types.
		value_type to_bytes(long input)
		{ return static_cast<value_type>(input); }

		value_type to_bytes(bool input)
		{ return static_cast<value_type>(input); }

		value_type to_bytes(void* input)
		{ return reinterpret_cast<value_type>(input); }

		value_type to_bytes(Pointer input)
		{ return reinterpret_cast<value_type>(input.value); }

		template<class R>
		struct PntrCaster
		{
			typedef PntrCaster<R> type;
			static R a(value_type input)
			{ return reinterpret_cast<R>(input); }
		};

		template<class I>
		struct StaticCaster
		{
			typedef StaticCaster<I> type;
			static I a(value_type input)
			{ return static_cast<I>(input); }
		};

		template<class T>
		struct Caster
			: public std::conditional<std::is_integral<T>::value,
			                          StaticCaster<T>,
			                          PntrCaster<T>
			                          >::type
		{};

		template<class R>
		R from_bytes(value_type input) { return Caster<R>::a(input); }
	}

	namespace cxx_functions
	{
		using namespace tmpl;

		template<class T>
		struct GuessTag
			: public Apply<tag, Apply<type_mapping::cxx_to_atl,
			                          std::remove_pointer<T> >
			               >::type
		{};

		struct Metadata
		{
			template<class R, class ... Rest>
			struct apply
			{
				static constexpr size_t arity()
				{ return sizeof...(Rest); }

				template<class Alloc>
				static Ast parameter_types(Alloc& gc)
				{ return *gc(fn_type::fn(GuessTag<Rest>::value..., GuessTag<R>::value)); }
			};
		};

		// wraps a c++ std::function
		template<class Sig> struct WrapStdFunction {};

		template<class R, class ... Sig>
		class WrapStdFunction<R (Sig ...)> :
			public Metadata::template apply<R, Sig...>
		{
		private:
			template <std::size_t... Index>
			static void call_packed(std::function<R (Sig...)> fn
			                        , vm_stack::iterator begin
			                        , tmpl::Indexer<Index...>)
			{
				using namespace byte_code;
				*begin = to_bytes(atl::value<R>(fn(from_bytes<Sig>(begin[Index])...)));
			}
		public:

			/**
			 * using the 'a' for 'apply' convention, builds the wrapped version of fn
			 * @return: wrapped function
			 */
			template<class Alloc>
			static Marked<CxxFunctor> a(std::function<R (Sig...)> const& fn, Alloc &gc
			                            , std::string const & name = "#<Unnamed-CxxFunctor>")
			{
				return gc.template make<CxxFunctor>
					([fn](vm_stack::iterator vv, vm_stack::iterator _)
					 {
						 return call_packed(fn, vv,
						                    typename tmpl::BuildIndicies<WrapStdFunction::arity()>::type {});
					 }
					 , name
					 , WrapStdFunction::parameter_types(gc)
					 , WrapStdFunction::arity());
			}
		};
	}

	template<class Sig>
	using WrapStdFunction = cxx_functions::WrapStdFunction<Sig>;

	namespace signature
	{
		template<class R, class ... Sig>
		struct Pack;

		template<class R, class ... Sig>
		struct Pack<R (Sig...)>
		{
			typedef Pack<R (Sig...)> type;

			typedef R Return;
			typedef std::tuple<Sig...> Args;

			static constexpr std::size_t arity = sizeof...(Sig);
		};

		template<class R, class Fn, class Args, class Indexes>
		struct _Unpack;

		template<class R, class Target, class Args, std::size_t... Index>
		struct _Unpack<R, Target, Args, tmpl::Indexer<Index...> >
		{ typedef typename Target::template type<R, typename std::tuple_element<Index, Args>::type...> type; };

		// Unpack Pack to instantiate Target
		template<class Pack, class Target>
		struct Unpack
			: public _Unpack<typename Pack::Return,
			                 Target,
			                 typename Pack::Args,
			                 typename tmpl::BuildIndicies<Pack::arity>::type >
		{};

		struct _StdFunction
		{
			template<class R, class ... Args>
			using type = std::function<R (Args...)>;
		};

		template<class Pack>
		struct StdFunction
			: public Unpack<Pack, _StdFunction>
		{};

		struct _Wrapper
		{
			template<class R, class ... Args>
			using type = cxx_functions::WrapStdFunction<R (Args...)>;
		};

		template<class Pack>
		struct Wrapper
			: public Unpack<Pack, _Wrapper>
		{};
	}
}

#endif

max_stars_repo_name: rcdomigan/atl

max_issues_repo_name: rcdomigan/atl

max_forks_repo_name: rcdomigan/atl


text:
#line 16 "./samples/gtest/gtest.cgfeature"

// gtest.cgfeature
#include <gtest>
#line 5 "./samples/gtest/modelselection.s.cgfeature"

#line 4 "./samples/gtest/instruments.s.cgfeature"

#line 6 "./samples/gtest/instruments.s.cgfeature"
// instruments.s.cgfeature
#include <bsl_unorderedmap.h>
#include <bsl_string.h>
#include <dlibcoretypes_model.h>
#include <dlibdealapi_contractapifactory.h>
#include <dlibdealapi_lexificontractapi.h>

#line 7 "./samples/gtest/modelselection.s.cgfeature"

// modelselection.s.cgfeature
#include <bsl_unordered_map.h>
#include <dlibcoretypes_model.h>
#include <dlibdealapi_contractapifactory.h>
#include <dlibdealapi_lexificontractapi.h>

#line 20 "./samples/gtest/gtest.cgfeature"

using namespace BloombergLP;

namespace { // Anon ns for helpers

namespace { const char LOG_CATEGORY[] = "MODELSELECTIONTEST_GTEST"; }

#line 15 "./samples/gtest/instruments.s.cgfeature"

#line 17 "./samples/gtest/instruments.s.cgfeature"

// instruments.s.cgfeature
void load_equities(
    bsl::unordered_map<bsl::string, ContractApi::Underlying> &underlyings,
    const cglang::utils::table<3> &data)
{
    for(size_t r = 0; r < data.rows(); r++) {
        underlyings.emplace(
            data.get(r, "name"),
            dlibdealapi::ContractApi::Equity(data.get(r, "ticker"), data.get(r, "currency")));
    }
}

void load_libor_rates(
    bsl::unordered_map<bsl::string, ContractApi::Underlying> &underlyings,
    const cglang::utils::table<4> &data)
{
    for(size_t r = 0; r < data.rows(); r++) {
        underlyings.emplace(
            data.get(r, "name"),
            dlibdealapi::ContractApi::Libor(
                data.get(r, "ticker"),
                dlibcoretypes::BBSecurity::Libor(
                    data.get(r, "tenor"),
                    data.get(r, "currency"))));
    }
}

void load_instruments(
    bsl::unordered_map<bsl::string, ContractApi::Underlying> &underlyings,
    bsl::vector<ContractApi::Underlying> &loaded_instruments,
    const cglang::utils::table<1> &data)
{
    for(size_t r = 0; r < data.rows(); r++) {
        auto f = underlyings.find(data.get(r, "instrument"));
        ASSERT_TRUE(f != underlyings.end());
        loaded_instruments.push_back(f.second);
    }
}

#line 28 "./samples/gtest/gtest.cgfeature"

} // anonymous namespace

namespace gtest { // Open the namespace for this module

#line 40 "./samples/gtest/gtest.cgfeature"

TEST(ModelSelectionTest, modelSelectionEQBasketIRSingleCcy)
{
    #line 16 "./samples/gtest/modelselection.s.cgfeature"

    #line 60 "./samples/gtest/instruments.s.cgfeature"

#line 62 "./samples/gtest/instruments.s.cgfeature"
    // instruments.s.cgfeature
    bsl::unordered_map<bsl::string, ContractApi::Underlying> underlyings;
    bsl::vector<ContractApi::Underlying> loaded_instruments;

#line 18 "./samples/gtest/modelselection.s.cgfeature"

    // modelselection.s.cgfeature
    bde::Date asOfDate;
    bde::Date expiryDate;
    bsl::vector<bsl::string> warnings;
    bsl::vector<bsl::string> models;

#line 45 "./samples/gtest/gtest.cgfeature"

    try
    {
            {
         static const char data[] = "name\0ticker\0currency\0\0IBM\0IBM US Equity\0USD\0\0MSFT\0MSFT US Equity\0USD\0\0SPX\0SPX Index\0USD\0\0SX5E\0SX5E Index\0EUR\0\0\0";
         static const char *indexes[] = { data, data + 5, data + 12, data + 22, data + 26, data + 40, data + 45, data + 50, data + 65, data + 70, data + 74, data + 84, data + 89, data + 94, data + 105 };
         struct headers
         {
             enum
             {
                 name = 0,
                 ticker = 1,
                 currency = 2
             };
         };
         cglang::utils::table<3, char> tbl(indexes, 5);
#line 67 "./samples/gtest/instruments.s.cgfeature"
 load_equities(underlyings, tbl);
    }
    {
         static const char data[] = "name\0ticker\0currency\0tenor\0\0US0003M\0US0003M Index\0USD\03M\0\0\0";
         static const char *indexes[] = { data, data + 5, data + 12, data + 21, data + 28, data + 36, data + 50, data + 54 };
         struct headers
         {
             enum
             {
                 name = 0,
                 ticker = 1,
                 currency = 2,
                 tenor = 3
             };
         };
         cglang::utils::table<4, char> tbl(indexes, 2);
#line 68 "./samples/gtest/instruments.s.cgfeature"
 load_libor_rates(underlyings, tbl);
    }
    { #line 26 "./samples/gtest/modelselection.s.cgfeature"
 asOfDate.set(2014, 10, 09);
    }
    { #line 27 "./samples/gtest/modelselection.s.cgfeature"
 expiryDate.set(2014, 11, 08);
    }
    {
         static const char data[] = "instrument\0\0IBM\0\0MSFT\0\0US0003M\0\0\0";
         static const char *indexes[] = { data, data + 12, data + 17, data + 23 };
         struct headers
         {
             enum
             {
                 instrument = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 4);
#line 69 "./samples/gtest/instruments.s.cgfeature"
 load_instruments(underlyings, loaded_instruments, tbl);
    }
    {
         static const char data[] = "currency\0\0USD\0\0\0";
         static const char *indexes[] = { data, data + 10 };
         struct headers
         {
             enum
             {
                 currency = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 2);
#line 29 "./samples/gtest/modelselection.s.cgfeature"

    bsl::vector<bsl::string> currencies;
    for(size_t r = 0; r < tbl.rows(); r++) {
        currencies.push_back(tbl.get(r, "currency"));
    }
    select_models(asOfDate, expiryDate, loaded_instruments, currencies, models, warnings);
    }
    { #line 36 "./samples/gtest/modelselection.s.cgfeature"
 ASSERT_EQ(0, warnings.size());
    }
    {
         static const char data[] = "model\0\0HULL_WHITE_1F_BS_BASKET\0\0HULL_WHITE_1F_LV\0\0LOCAL_VOLATILITY\0\0BLACK_SCHOLES\0\0HULL_WHITE_2F_BS_BASKET\0\0HULL_WHITE_2F_LV\0\0\0";
         static const char *indexes[] = { data, data + 7, data + 32, data + 50, data + 68, data + 83, data + 108 };
         struct headers
         {
             enum
             {
                 model = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 7);
#line 37 "./samples/gtest/modelselection.s.cgfeature"
 tbl.assert_equivalent(models.begin(), models.end());
    }

#line 49 "./samples/gtest/gtest.cgfeature"
    }
    catch(std::exception ex) {
        FAIL(ex.what());
    }
}

#line 40 "./samples/gtest/gtest.cgfeature"

TEST(ModelSelectionTest, modelSelectionEQBasketIRMultipleCcy)
{
    #line 16 "./samples/gtest/modelselection.s.cgfeature"

    #line 60 "./samples/gtest/instruments.s.cgfeature"

#line 62 "./samples/gtest/instruments.s.cgfeature"
    // instruments.s.cgfeature
    bsl::unordered_map<bsl::string, ContractApi::Underlying> underlyings;
    bsl::vector<ContractApi::Underlying> loaded_instruments;

#line 18 "./samples/gtest/modelselection.s.cgfeature"

    // modelselection.s.cgfeature
    bde::Date asOfDate;
    bde::Date expiryDate;
    bsl::vector<bsl::string> warnings;
    bsl::vector<bsl::string> models;

#line 45 "./samples/gtest/gtest.cgfeature"

    try
    {
            {
         static const char data[] = "name\0ticker\0currency\0\0IBM\0IBM US Equity\0USD\0\0MSFT\0MSFT US Equity\0USD\0\0SPX\0SPX Index\0USD\0\0SX5E\0SX5E Index\0EUR\0\0\0";
         static const char *indexes[] = { data, data + 5, data + 12, data + 22, data + 26, data + 40, data + 45, data + 50, data + 65, data + 70, data + 74, data + 84, data + 89, data + 94, data + 105 };
         struct headers
         {
             enum
             {
                 name = 0,
                 ticker = 1,
                 currency = 2
             };
         };
         cglang::utils::table<3, char> tbl(indexes, 5);
#line 67 "./samples/gtest/instruments.s.cgfeature"
 load_equities(underlyings, tbl);
    }
    {
         static const char data[] = "name\0ticker\0currency\0tenor\0\0US0003M\0US0003M Index\0USD\03M\0\0\0";
         static const char *indexes[] = { data, data + 5, data + 12, data + 21, data + 28, data + 36, data + 50, data + 54 };
         struct headers
         {
             enum
             {
                 name = 0,
                 ticker = 1,
                 currency = 2,
                 tenor = 3
             };
         };
         cglang::utils::table<4, char> tbl(indexes, 2);
#line 68 "./samples/gtest/instruments.s.cgfeature"
 load_libor_rates(underlyings, tbl);
    }
    { #line 26 "./samples/gtest/modelselection.s.cgfeature"
 asOfDate.set(2014, 10, 09);
    }
    { #line 27 "./samples/gtest/modelselection.s.cgfeature"
 expiryDate.set(2014, 11, 08);
    }
    {
         static const char data[] = "instrument\0\0SPX\0\0SX5E\0\0US0003M\0\0\0";
         static const char *indexes[] = { data, data + 12, data + 17, data + 23 };
         struct headers
         {
             enum
             {
                 instrument = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 4);
#line 69 "./samples/gtest/instruments.s.cgfeature"
 load_instruments(underlyings, loaded_instruments, tbl);
    }
    {
         static const char data[] = "currency\0\0USD\0\0\0";
         static const char *indexes[] = { data, data + 10 };
         struct headers
         {
             enum
             {
                 currency = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 2);
#line 29 "./samples/gtest/modelselection.s.cgfeature"

    bsl::vector<bsl::string> currencies;
    for(size_t r = 0; r < tbl.rows(); r++) {
        currencies.push_back(tbl.get(r, "currency"));
    }
    select_models(asOfDate, expiryDate, loaded_instruments, currencies, models, warnings);
    }
    { #line 36 "./samples/gtest/modelselection.s.cgfeature"
 ASSERT_EQ(0, warnings.size());
    }
    {
         static const char data[] = "model\0\0LOCAL_VOLATILITY\0\0BLACK_SCHOLES\0\0\0\0\0";
         static const char *indexes[] = { data, data + 7, data + 25, data + 40 };
         struct headers
         {
             enum
             {
                 model = 0
             };
         };
         cglang::utils::table<1, char> tbl(indexes, 4);
#line 37 "./samples/gtest/modelselection.s.cgfeature"
 tbl.assert_equivalent(models.begin(), models.end());
    }

#line 49 "./samples/gtest/gtest.cgfeature"
    }
    catch(std::exception ex) {
        FAIL(ex.what());
    }
}

#line 34 "./samples/gtest/gtest.cgfeature"

}

ext: cpp

max_stars_repo_name: David-Lindeque/cglang

max_issues_repo_name: David-Lindeque/cglang

max_forks_repo_name: David-Lindeque/cglang


text:
/*    Copyright (c) 2010-2015, Delft University of Technology
 *    All rights reserved.
 *
 *    Redistribution and use in source and binary forms, with or without modification, are
 *    permitted provided that the following conditions are met:
 *      - Redistributions of source code must retain the above copyright notice, this list of
 *        conditions and the following disclaimer.
 *      - Redistributions in binary form must reproduce the above copyright notice, this list of
 *        conditions and the following disclaimer in the documentation and/or other materials
 *        provided with the distribution.
 *      - Neither the name of the Delft University of Technology nor the names of its contributors
 *        may be used to endorse or promote products derived from this software without specific
 *        prior written permission.
 *
 *    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
 *    OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 *    MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
 *    COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 *    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
 *    GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
 *    AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 *    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 *    OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 *    Changelog
 *      YYMMDD    Author            Comment
 *      15XXXX    D. Dirkx          File created.
 *
 *    References
 *
 *    Notes
 *
 */

#include <iostream>
#include <boost/make_shared.hpp>

#include "Tudat/Astrodynamics/Gravitation/gravityFieldModel.h"

namespace tudat
{
namespace gravitation
{

//! Set predefined central gravity field settings.
boost::shared_ptr< GravityFieldModel > getPredefinedCentralGravityField(
    BodiesWithPredefinedCentralGravityFields bodyWithPredefinedCentralGravityField )
{
    double gravitationalParameter = 0.0;

    // Select body with prefined central gravity field.
    switch( bodyWithPredefinedCentralGravityField )
    {
    case sun:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 1.32712440018e20;

        break;

    case mercury:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.2, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 2.203289218e13;

        break;

    case venus:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.2, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 3.2485504415e14;

        break;

    case earth:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.2, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 3.9859383624e14;

        break;

    case moon:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.2, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 4.903686391e12;

        break;

    case mars:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.2, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 4.2828018915e13;

        break;

    case jupiter:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.3, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 1.2668579374e17;

        break;

    case saturn:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.3, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 3.793100511400001e16;

        break;

    case uranus:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.3, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 5.793943348799999e15;

        break;

    case neptune:

        // Set gravitational parameter [m^3 s^-2].
        // Reference: Mass taken from Table 1.3, pg. 6, (de Pater, 2010), value
        //            of gravitational constant taken from
        //            http://ssd.jpl.nasa.gov/?constants#ref.
        gravitationalParameter = 6.834733937e15;

        break;

    default:

        // Print cerr statement.
        std::cerr << "Desired predefined central gravity field does not exist." << std::endl;
    }
    return boost::make_shared< GravityFieldModel >( gravitationalParameter );
}

} // namespace gravitation
} // namespace tudat

max_stars_repo_name: JPelamatti/ThesisTUDAT

max_issues_repo_name: JPelamatti/ThesisTUDAT

max_forks_repo_name: JPelamatti/ThesisTUDAT


text:
/* Copyright (C) 2019-2021 Junruoyu Zheng. Home page: https://junruoyu-zheng.gitee.io/ligral

    Distributed under MIT license.
    See file LICENSE for detail or copy at https://opensource.org/licenses/MIT
*/

#include <iostream>
#include <Eigen/Dense>
using Eigen::Matrix;

#include "config.h"

int main() {
    Matrix<double, n, 1> x;
    x << 0, 1;
    for (int i=0; i<10; i++) {
        double t = ((double)i)*h;
        x = integral(f, x, h);
        std::cout << "t = " << t << std::endl;
        std::cout << x << std::endl;
    }
    return 0;
}

ext: cc

max_stars_repo_name: JRY-Zheng/ligral

max_issues_repo_name: JRY-Zheng/ligral

max_forks_repo_name: JRY-Zheng/ligral


text:
//  (C) Copyright Gennadiy Rozental 2001-2005.
//  Distributed under the Boost Software License, Version 1.0.
//  (See accompanying file LICENSE_1_0.txt or copy at
//  http://www.boost.org/LICENSE_1_0.txt)

//  See http://www.boost.org/libs/test for the library home page.
//
//  File        : $RCSfile: boost_check_equal_str.cpp,v $
//
//  Version     : $Revision: 1.2 $
//
//  Description : basic_cstring unit test
// *****************************************************************************

#include <boost/test/test_tools.hpp>

int test_main( int, char *[] )
{
    char const* buf_ptr_cch     = "abc";
    char const  buf_array_cch[] = "abc";
    char*       buf_ptr_ch      = "abc";
    char        buf_array_ch[]  = "abc";
    std::string buf_str         = "abc";

    BOOST_CHECK_EQUAL(buf_ptr_cch, buf_ptr_cch);
    BOOST_CHECK_EQUAL(buf_ptr_cch, buf_array_cch);
    BOOST_CHECK_EQUAL(buf_ptr_cch, buf_ptr_ch);
    BOOST_CHECK_EQUAL(buf_ptr_cch, buf_array_ch);
    BOOST_CHECK_EQUAL(buf_ptr_cch, buf_str);

    BOOST_CHECK_EQUAL(buf_array_cch, buf_ptr_cch);
    BOOST_CHECK_EQUAL(buf_array_cch, buf_array_cch);
    BOOST_CHECK_EQUAL(buf_array_cch, buf_ptr_ch);
    BOOST_CHECK_EQUAL(buf_array_cch, buf_array_ch);
    BOOST_CHECK_EQUAL(buf_array_cch, buf_str);

    BOOST_CHECK_EQUAL(buf_ptr_ch, buf_ptr_cch);
    BOOST_CHECK_EQUAL(buf_ptr_ch, buf_array_cch);
    BOOST_CHECK_EQUAL(buf_ptr_ch, buf_ptr_ch);
    BOOST_CHECK_EQUAL(buf_ptr_ch, buf_array_ch);
    BOOST_CHECK_EQUAL(buf_ptr_ch, buf_str);

    BOOST_CHECK_EQUAL(buf_array_ch, buf_ptr_cch);
    BOOST_CHECK_EQUAL(buf_array_ch, buf_array_cch);
    BOOST_CHECK_EQUAL(buf_array_ch, buf_ptr_ch);
    BOOST_CHECK_EQUAL(buf_array_ch, buf_array_ch);
    BOOST_CHECK_EQUAL(buf_array_ch, buf_str);

    BOOST_CHECK_EQUAL(buf_str, buf_ptr_cch);
    BOOST_CHECK_EQUAL(buf_str, buf_array_cch);
    BOOST_CHECK_EQUAL(buf_str, buf_ptr_ch);
    BOOST_CHECK_EQUAL(buf_str, buf_array_ch);
    BOOST_CHECK_EQUAL(buf_str, buf_str);

    return 0;
}

// EOF

max_stars_repo_name: spxuw/RFIM

max_issues_repo_name: spxuw/RFIM

max_forks_repo_name: spxuw/RFIM


text:
/*
 * Copyright (C) 2016 Fondazione Istituto Italiano di Tecnologia iCub Facility
 * Authors: Marco Randazzo <marco.randazzo@iit.it>
 * CopyPolicy: Released under the terms of the LGPLv2.1 or any later version, see LGPL.TXT or LGPL3.TXT
 */

#ifndef GAZEBO_VIDEO_VISUAL_H
#define GAZEBO_VIDEO_VISUAL_H

#include <boost/thread/mutex.hpp>
#include <opencv2/opencv.hpp>

#include <yarp/sig/Image.h>
#include <yarp/os/Port.h>
#include <yarp/os/Network.h>
#include <yarp/os/BufferedPort.h>
#include <gazebo/common/Events.hh>
#include <gazebo/common/Plugin.hh>
#include <gazebo/common/Time.hh>
#include <gazebo/rendering/rendering.hh>
#include <gazebo/transport/TransportTypes.hh>

typedef yarp::sig::ImageOf<yarp::sig::PixelRgb> ImageType;
#define FORMAT Ogre::PF_B8G8R8

namespace gazebo
{

  class VideoTexture : public VisualPlugin
  {
      void Update();
    public:

      VideoTexture();
      virtual ~VideoTexture();
      void Load(rendering::VisualPtr parent, sdf::ElementPtr sdf);

    protected:
      yarp::os::BufferedPort<ImageType> m_VideoPort;

      std::string            m_texName;
      Ogre::MaterialPtr      m_material;
      Ogre::TexturePtr       m_texture;
      event::ConnectionPtr   m_connection;
      rendering::VisualPtr   m_model;
      yarp::os::Property     m_parameters;
      boost::mutex           m_image;
      int                    m_height;
      int                    m_width;
      double                 m_scale;
      yarp::os::Network*     m_network;
      yarp::os::Port         m_input_port;
      std::string            m_port_name;
  };

}

#endif

ext: hh


text:
#pragma once
#include <boost/multi_index/composite_key.hpp>

#include <scorum/chain/schema/scorum_object_types.hpp>

#include <fc/exception/exception.hpp>
#include <functional>

namespace scorum {
namespace chain {

class withdraw_scorumpower_route_object
    : public object<withdraw_scorumpower_route_object_type, withdraw_scorumpower_route_object>
{
public:
    CHAINBASE_DEFAULT_CONSTRUCTOR(withdraw_scorumpower_route_object)

    id_type id;

    withdrawable_id_type from_id;
    withdrawable_id_type to_id;

    uint16_t percent = 0;
    bool auto_vest = false;
};

class withdraw_scorumpower_route_statistic_object
    : public object<withdraw_scorumpower_route_statistic_object_type, withdraw_scorumpower_route_statistic_object>
{
public:
    CHAINBASE_DEFAULT_CONSTRUCTOR(withdraw_scorumpower_route_statistic_object)

    id_type id;

    withdrawable_id_type from_id;

    uint16_t withdraw_routes = 0u;
};

using scorum::protocol::asset;

class withdraw_scorumpower_object : public object<withdraw_scorumpower_object_type, withdraw_scorumpower_object>
{
public:
    CHAINBASE_DEFAULT_CONSTRUCTOR(withdraw_scorumpower_object)

    id_type id;

    withdrawable_id_type from_id;

    asset vesting_withdraw_rate
        = asset(0, SP_SYMBOL); ///< at the time this is updated it can be at most scorumpower/104
    time_point_sec next_vesting_withdrawal
        = fc::time_point_sec::maximum(); ///< after every withdrawal this is incremented by 1 week
    asset withdrawn = asset(0, SP_SYMBOL); /// Track how many shares have been withdrawn
    asset to_withdraw = asset(0, SP_SYMBOL); /// Might be able to look this up with operation history.
};

namespace withdraw_scorumpower_objects {

class ids_visitor
{
public:
    typedef bool result_type;

    template <typename Op> bool operator()(const Op&) const
    {
        FC_ASSERT(false, "Unknown type.");
        return false;
    }

protected:
    ids_visitor(const withdrawable_id_type& right)
        : _right(right)
    {
    }

    const withdrawable_id_type& _right;
};

class less_ids_visitor : public ids_visitor
{
public:
    less_ids_visitor(const withdrawable_id_type& right)
        : ids_visitor(right)
    {
    }

    bool operator()(const account_id_type& left) const
    {
        return left < _right.get<account_id_type>();
    }

    bool operator()(const dev_committee_id_type& left) const
    {
        return left < _right.get<dev_committee_id_type>();
    }
};

class equal_ids_visitor : public ids_visitor
{
public:
    equal_ids_visitor(const withdrawable_id_type& right)
        : ids_visitor(right)
    {
    }

    bool operator()(const account_id_type& left) const
    {
        return _right.get<account_id_type>() == left;
    }

    bool operator()(const dev_committee_id_type& left) const
    {
        return _right.get<dev_committee_id_type>() == left;
    }
};
}

struct less_for_withdrawable_id : public std::binary_function<withdrawable_id_type, withdrawable_id_type, bool>
{
    bool operator()(const withdrawable_id_type& a, const withdrawable_id_type& b) const
    {
        using namespace withdraw_scorumpower_objects;

        if (a.which() == b.which()) // both have same type
        {
            return a.visit(less_ids_visitor(b));
        }
        return a.which() < b.which(); // compare by type
    }
};

inline bool is_equal_withdrawable_id(const withdrawable_id_type& a, const withdrawable_id_type& b)
{
    using namespace withdraw_scorumpower_objects;

    if (a.which() == b.which())
    {
        return a.visit(equal_ids_visitor(b));
    }

    return false;
}

struct by_withdraw_route;
struct by_destination;
typedef shared_multi_index_container<withdraw_scorumpower_route_object,
                                     indexed_by<ordered_unique<tag<by_id>,
                                                               member<withdraw_scorumpower_route_object,
                                                                      withdraw_scorumpower_route_id_type,
                                                                      &withdraw_scorumpower_route_object::id>>,
                                                ordered_unique<tag<by_withdraw_route>,
                                                               composite_key<withdraw_scorumpower_route_object,
                                                                             member<withdraw_scorumpower_route_object,
                                                                                withdrawable_id_type,
                                                                                &withdraw_scorumpower_route_object::
                                                                                from_id>,
                                                                             member<withdraw_scorumpower_route_object,
                                                                                withdrawable_id_type,
                                                                                &withdraw_scorumpower_route_object::
                                                                                to_id>>,
                                                               composite_key_compare<less_for_withdrawable_id,
                                                                                less_for_withdrawable_id>>,
                                                ordered_unique<tag<by_destination>,
                                                               composite_key<withdraw_scorumpower_route_object,
                                                                             member<withdraw_scorumpower_route_object,
                                                                                withdrawable_id_type,
                                                                                &withdraw_scorumpower_route_object::
                                                                                to_id>,
                                                                             member<withdraw_scorumpower_route_object,
                                                                                withdraw_scorumpower_route_id_type,
                                                                                &withdraw_scorumpower_route_object::
                                                                                id>>,
                                                               composite_key_compare<less_for_withdrawable_id,
                                                                                std::
                                                                                less<withdraw_scorumpower_route_id_type>>>>>
    withdraw_scorumpower_route_index;

typedef shared_multi_index_container<withdraw_scorumpower_route_statistic_object,
                                     indexed_by<ordered_unique<tag<by_id>,
                                                               member<withdraw_scorumpower_route_statistic_object,
                                                                      withdraw_scorumpower_route_statistic_id_type,
                                                                      &withdraw_scorumpower_route_statistic_object::
                                                                          id>>,
                                                ordered_unique<tag<by_destination>,
                                                               member<withdraw_scorumpower_route_statistic_object,
                                                                      withdrawable_id_type,
                                                                      &withdraw_scorumpower_route_statistic_object::
                                                                          from_id>,
                                                               less_for_withdrawable_id>>>
    withdraw_scorumpower_route_statistic_index;

struct by_next_vesting_withdrawal;
typedef shared_multi_index_container<withdraw_scorumpower_object,
                                     indexed_by<ordered_unique<tag<by_id>,
                                                               member<withdraw_scorumpower_object,
                                                                      withdraw_scorumpower_id_type,
                                                                      &withdraw_scorumpower_object::id>>,
                                                ordered_unique<tag<by_destination>,
                                                               member<withdraw_scorumpower_object,
                                                                      withdrawable_id_type,
                                                                      &withdraw_scorumpower_object::from_id>,
                                                               less_for_withdrawable_id>,
                                                ordered_unique<tag<by_next_vesting_withdrawal>,
                                                               composite_key<withdraw_scorumpower_object,
                                                                             member<withdraw_scorumpower_object,
                                                                                time_point_sec,
                                                                                &withdraw_scorumpower_object::
                                                                                next_vesting_withdrawal>,
                                                                             member<withdraw_scorumpower_object,
                                                                                withdraw_scorumpower_id_type,
                                                                                &withdraw_scorumpower_object::
                                                                                id>>>>>
    withdraw_scorumpower_index;

} // namespace chain
} // namespace scorum

// clang-format off
FC_REFLECT_TYPENAME(scorum::chain::withdrawable_id_type)
FC_REFLECT(scorum::chain::withdraw_scorumpower_route_object,
           (id)
           (from_id)
           (to_id)
           (percent)
           (auto_vest))
CHAINBASE_SET_INDEX_TYPE(scorum::chain::withdraw_scorumpower_route_object, scorum::chain::withdraw_scorumpower_route_index)

FC_REFLECT(scorum::chain::withdraw_scorumpower_route_statistic_object,
           (id)
           (from_id)
           (withdraw_routes))
CHAINBASE_SET_INDEX_TYPE(scorum::chain::withdraw_scorumpower_route_statistic_object, scorum::chain::withdraw_scorumpower_route_statistic_index)

FC_REFLECT(scorum::chain::withdraw_scorumpower_object,
           (id)
           (from_id)
           (vesting_withdraw_rate)
           (next_vesting_withdrawal)
           (withdrawn)
           (to_withdraw))
CHAINBASE_SET_INDEX_TYPE(scorum::chain::withdraw_scorumpower_object, scorum::chain::withdraw_scorumpower_index)
// clang-format on

ext: hpp

max_stars_repo_name: scorum/scorum

max_issues_repo_name: Scorum/Scorum

max_forks_repo_name: Scorum/Scorum


text:
//==================================================================================================
/*!
  @file

  Aggregates SIMD extension tags for Intel X86 and AMD

  @copyright 2016 NumScale SAS

  Distributed under the Boost Software License, Version 1.0.
  (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)

**/
//==================================================================================================
#ifndef BOOST_SIMD_ARCH_X86_AVX2_TAGS_HPP_INCLUDED
#define BOOST_SIMD_ARCH_X86_AVX2_TAGS_HPP_INCLUDED

#include <boost/simd/arch/x86/avx/tags.hpp>
#include <boost/simd/detail/support.hpp>
#include <boost/simd/detail/cpuid.hpp>

namespace boost { namespace simd
{
  /*!
    @ingroup group-hierarchy
    @brief Intel AVX2 SIMD architecture hierarchy tag

    This tag represent architectures implementing the Intel AVX2 SIMD instructions set.
  **/
  struct avx2_ : avx_
  {
    using parent = avx_;
  };

  namespace detail
  {
    template<> struct support<::boost::simd::avx2_>
    {
      support()
      {
        #if BOOST_ARCH_X86
        support_ =   detect_features( (1<< 5)|(1<< 3)|(1<< 8), 0x00000007, detail::ebx)
                 &&  detect_features( (1<<27)|(1<<22)|(1<<12), 0x00000001, detail::ecx);
        #else
        support_ = false;
        #endif
      }

      inline bool is_supported() const { return support_; }

      private:
      bool support_;
    };
  }

  /*!
    @ingroup  group-api
    Global object for accessing AVX2 support informations
  **/
  static detail::support<avx2_> const avx2 = {};
} }

#endif

max_stars_repo_name: xmar/pythran

max_issues_repo_name: xmar/pythran

max_forks_repo_name: xmar/pythran


text:
#include "MBTB_TimeStepping.hpp"
#include "MBTB_PYTHON_API.hpp"
#include "MBTB_internalTool.hpp"
#include <boost/math/quaternion.hpp>
//#define TS_DEBUG
MBTB_TimeStepping::MBTB_TimeStepping(SP::TimeDiscretisation td,
                                     SP::OneStepIntegrator osi,
                                     SP::OneStepNSProblem osnspb_velo):TimeStepping(td,osi,osnspb_velo)
{
}

void MBTB_TimeStepping::updateWorldFromDS()
{
#ifdef TS_DEBUG
  printf("MBTB_TimeStepping::updateWordFromDS \n");
#endif
  MBTB_updateDSFromSiconos();
  _MBTB_updateContactFromDS();
}

max_stars_repo_name: siconos/siconos-deb

max_issues_repo_name: siconos/siconos-deb

max_forks_repo_name: siconos/siconos-deb


text:
#include "Options.hpp"
#include "lvr2/geometry/BoundingBox.hpp"
#include "lvr2/io/IOUtils.hpp"
#include "lvr2/io/ScanIOUtils.hpp"
#include "lvr2/io/Timestamp.hpp"
#include "lvr2/io/hdf5/ScanProjectIO.hpp"
#include "lvr2/io/hdf5/HDF5FeatureBase.hpp"
#include "lvr2/types/ScanTypes.hpp"

#include <boost/filesystem.hpp>

using namespace lvr2;

using BaseHDF5IO = lvr2::Hdf5IO<>;

// Extend IO with features (dependencies are automatically fetched)
using HDF5IO =
    BaseHDF5IO::AddFeatures<lvr2::hdf5features::ScanProjectIO, lvr2::hdf5features::ArrayIO>;

bool m_usePreviews;
int m_previewReductionFactor;

template <typename T>
boost::shared_array<T> reduceData(boost::shared_array<T> data,
                                  size_t dataCount,
                                  size_t dataWidth,
                                  unsigned int reductionFactor,
                                  size_t* reducedDataCount)
{
    *reducedDataCount = dataCount / reductionFactor + 1;

    boost::shared_array<T> reducedData =
        boost::shared_array<T>(new T[(*reducedDataCount) * dataWidth]);

    size_t reducedDataIdx = 0;
    for (size_t i = 0; i < dataCount; i++)
    {
        if (i % reductionFactor == 0)
        {
            std::copy(data.get() + i * dataWidth,
                      data.get() + (i + 1) * dataWidth,
                      reducedData.get() + reducedDataIdx * dataWidth);

            reducedDataIdx++;
        }
    }

    return reducedData;
}

int main(int argc, char** argv)
{
    hdf5tool2::Options options(argc, argv);
    boost::filesystem::path inputDir(options.getInputDir());
    boost::filesystem::path outputDir(options.getOutputDir());

    boost::filesystem::path outputPath(outputDir / options.getOutputFile());

    m_usePreviews = options.getPreview();
    m_previewReductionFactor = options.getPreviewReductionRatio();

    HDF5IO hdf;
    uint pos = 0;

    // check if input directory exists
    if (!boost::filesystem::exists(inputDir))
    {
        std::cout << timestamp << "Error: Directory " << options.getInputDir() << " does not exist"
                  << std::endl;
        exit(-1);
    }

    // check if output directory exists
    if (!boost::filesystem::exists(outputDir))
    {
        std::cout << timestamp << "Creating directory " << options.getOutputDir() << std::endl;
        if (!boost::filesystem::create_directory(outputDir))
        {
            std::cout << timestamp << "Error: Unable to create " << options.getOutputDir()
                      << std::endl;
            exit(-1);
        }
    }

    bool exitsts = false;
    ScanProjectPtr existingScanProject;

    // check if HDF5 already exists
    if (boost::filesystem::exists(outputPath))
    {
        std::cout << timestamp << "File already exists. Expanding File..." << std::endl;

        // get existing scans
        hdf.open(outputPath.string());
        existingScanProject = hdf.loadScanProject();
        exitsts = true;
    }
    else
    {
        hdf.open(outputPath.string());
    }

    ScanProjectPtr scanProject(new ScanProject());

    // reading scan project from given directory into ScanProject
    std::cout << timestamp << "Reading ScanProject from directory" << std::endl;
    loadScanProject(inputDir, *scanProject);

    // saving ScanProject into HDF5 file
    std::cout << timestamp << "Writing ScanProject to HDF5" << std::endl;
    if (exitsts)
    {
        for (ScanPositionPtr scanPosPtr : scanProject->positions)
        {
            existingScanProject->positions.push_back(scanPosPtr);
        }
        hdf.save(existingScanProject);
    }
    else
    {
        hdf.save(scanProject);
    }

    if (m_usePreviews)
    {
        for (int i = 0; i < scanProject->positions.size(); i++)
        {
            char buffer[128];
            sprintf(buffer, "%08d", i);
            string nr_str(buffer);
            std::string previewGroupName = "/preview/" + nr_str;

            std::cout << timestamp << "Generating preview for position " << nr_str << std::endl;

            ScanPositionPtr scanPositionPtr = scanProject->positions[i];

            ScanPtr scanPtr = scanPositionPtr->scans[0];
            floatArr points = scanPtr->points->getPointArray();

            if (points)
            {
                size_t numPreview;
                floatArr previewData = reduceData(points,
                                                  scanPtr->points->numPoints(),
                                                  3,
                                                  m_previewReductionFactor,
                                                  &numPreview);

                std::vector<size_t> previewDim = {numPreview, 3};
                hdf.save<float>(previewGroupName, "points", previewDim, previewData);
            }
        }
    }

    std::cout << timestamp << "Program finished" << std::endl;
}

max_stars_repo_name: uos/lvr

max_issues_repo_name: uos/lvr

max_forks_repo_name: uos/lvr


text:
/**
 * Copyright (c) 2018, University Osnabrück
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *     * Redistributions of source code must retain the above copyright
 *       notice, this list of conditions and the following disclaimer.
 *     * Redistributions in binary form must reproduce the above copyright
 *       notice, this list of conditions and the following disclaimer in the
 *       documentation and/or other materials provided with the distribution.
 *     * Neither the name of the University Osnabrück nor the
 *       names of its contributors may be used to endorse or promote products
 *       derived from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED. IN NO EVENT SHALL University Osnabrück BE LIABLE FOR ANY
 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#ifndef __LBKDTREE_HPP
#define __LBKDTREE_HPP

#include <lvr2/geometry/LBPointArray.hpp>

#include <ctpl.h>

#include <stdlib.h>
#include <math.h>
#include <boost/shared_ptr.hpp>
#include <list>
#include <unordered_set>

namespace lvr2
{

/**
 * @brief The LBKdTree class implements a left-balanced array-based index kd-tree.
 *          Left-Balanced: minimum memory
 *          Array-Based: Good for GPU - Usage
 */
class LBKdTree {
public:

    LBKdTree( LBPointArray<float>& vertices , int num_threads=8);

    ~LBKdTree();

    void generateKdTree( LBPointArray<float>& vertices );

    boost::shared_ptr<LBPointArray<float> > getKdTreeValues();

    boost::shared_ptr<LBPointArray<unsigned char> > getKdTreeSplits();

private:

    void generateKdTreeArray(LBPointArray<float>& V,
            LBPointArray<unsigned int>* sorted_indices,
            int max_dim);

    boost::shared_ptr<LBPointArray<float> > m_values;

    // split dim 4 dims per split_dim
    boost::shared_ptr<LBPointArray<unsigned char> > m_splits;

    // Static member

    static int st_num_threads;
    static int st_depth_threads;

    static ctpl::thread_pool *pool;

    static void fillCriticalIndices(const LBPointArray<float>& V,
            LBPointArray<unsigned int>& sorted_indices,
            unsigned int current_dim,
            float split_value, unsigned int split_index,
            std::list<unsigned int>& critical_indices_left,
            std::list<unsigned int>& critical_indices_right);

    static void fillCriticalIndicesSet(const LBPointArray<float>& V,
            LBPointArray<unsigned int>& sorted_indices,
            unsigned int current_dim,
            float split_value, unsigned int split_index,
            std::unordered_set<unsigned int>& critical_indices_left,
            std::unordered_set<unsigned int>& critical_indices_right);

    static void generateKdTreeRecursive(int id, LBPointArray<float>& V,
            LBPointArray<unsigned int>* sorted_indices, int current_dim, int max_dim,
            LBPointArray<float> *values, LBPointArray<unsigned char> *splits,
            int size, int max_tree_depth, int position, int current_depth);

    static void test(int id, LBPointArray<float>* sorted_indices);

};

}  /* namespace lvr2 */

#endif // !__LBKDTREE_HPP


text:
#include <iostream>
#include <vector>
#include <ctime>
#include <memory>
#include <boost/asio.hpp>

namespace IP = boost::asio::ip;
namespace Asio = boost::asio;

std::string make_string_time() {
    time_t now = time(0);
    return  ctime(&now);
}

class TCPConnection : public std::enable_shared_from_this<TCPConnection> {
public:
    typedef std::shared_ptr<TCPConnection> pointer;
    static pointer Create(Asio::io_context &io_context) {
        return pointer(new TCPConnection(io_context));
    }

    IP::tcp::socket &socket() {
        return socket_;
    }

    void Start() {
        msg_ = make_string_time();

        Asio::async_write(socket_, Asio::buffer(msg_), boost::bind(&TCPConnection::HandleWrite, shared_from_this(),
                                                                 Asio::placeholders::error,
                                                                 Asio::placeholders::bytes_transferred));
    }

private:
    TCPConnection(Asio::io_context &io_context)
        : socket_(io_context) {

    }

    void HandleWrite(const boost::system::error_code &ec, size_t byte_transferred) {

    }

    IP::tcp::socket socket_;
    std::string msg_;
};

class TCPServer {
public:
    TCPServer(Asio::io_context &io_context)
            : acceptor_(io_context, IP::tcp::endpoint(IP::tcp::v4(), 9999)){
        StartAccept();
    }
private:
    void StartAccept() {
        TCPConnection::pointer new_connection = TCPConnection::Create(acceptor_.get_executor().context());

        acceptor_.async_accept(new_connection->socket(), boost::bind(&TCPServer::HandleAccept, this, new_connection, Asio::placeholders::error));
    }

    void HandleAccept(TCPConnection::pointer new_connection, const boost::system::error_code &ec) {
        if (!ec) {
            new_connection->Start();
        }
        StartAccept();
    }
    IP::tcp::acceptor acceptor_;
};

int main() {
    try {
        Asio::io_context io_context;
        TCPServer server(io_context);
        io_context.run();
    }
    catch(std::exception &e) {
        std::cerr << e.what() << std::endl;
    }
    return 0;
}


text:
#ifndef Aliases_hpp
#define Aliases_hpp

/** @file Aliases.hpp
 * @brief
 * @author C.D. Clark III
 * @date 06/16/17
 */

#include <boost/multi_array.hpp>

// alias for the index_range type
using IRange = boost::multi_array_types::index_range;

// pull some commonly used boost types into global namespace
using boost::extent;
using boost::indices;
using boost::multi_array_types::index_range;

#endif  // include protector


text:
// Copyright (C) 2013-2020 Internet Systems Consortium, Inc. ("ISC")
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

#include <config.h>

#include <hooks/callout_handle.h>
#include <hooks/callout_manager.h>
#include <hooks/library_handle.h>
#include <hooks/server_hooks.h>

#include <boost/lexical_cast.hpp>
#include <boost/scoped_ptr.hpp>
#include <gtest/gtest.h>

#include <algorithm>
#include <string>

/// @file
/// CalloutHandle/LibraryHandle interaction tests
///
/// This file holds unit tests checking the interaction between the
/// CalloutHandle/LibraryHandle and CalloutManager classes.  In particular,
/// they check that:
///
/// - A CalloutHandle's context is shared between callouts from the same
///   library, but there is a separate context for each library.
///
/// - The various methods manipulating the items in the CalloutHandle's context
///   work correctly.
///
/// - An active callout can only modify the registration of callouts registered
///   by its own library.

using namespace isc::hooks;
using namespace std;

namespace {

class HandlesTest : public ::testing::Test {
public:
    /// @brief Constructor
    ///
    /// Sets up the various elements used in each test.
    HandlesTest() {
        // Set up four hooks, although through gamma
        ServerHooks& hooks = ServerHooks::getServerHooks();
        hooks.reset();
        alpha_index_ = hooks.registerHook("alpha");
        beta_index_ = hooks.registerHook("beta");
        gamma_index_ = hooks.registerHook("gamma");
        delta_index_ = hooks.registerHook("delta");

        // Set up for three libraries.
        manager_.reset(new CalloutManager(3));

        // Initialize remaining variables.
        common_string_ = "";
    }

    /// @brief Return callout manager
    boost::shared_ptr<CalloutManager> getCalloutManager() {
        return (manager_);
    }

    /// Hook indexes - these are frequently accessed, so are accessed directly.
    int alpha_index_;
    int beta_index_;
    int gamma_index_;
    int delta_index_;

    /// String accessible by all callouts whatever the library
    static std::string common_string_;

private:
    /// Callout manager.  Declared static so that the callout functions can
    /// access it.
    boost::shared_ptr<CalloutManager> manager_;
};

/// Define the common string
std::string HandlesTest::common_string_;

// The next set of functions define the callouts used by the tests.  They
// manipulate the data in such a way that callouts called - and the order in
// which they were called - can be determined.  The functions also check that
// the "callout context" data areas are separate.
//
// Three libraries are assumed, and each supplies four callouts.  All callouts
// manipulate two context elements the CalloutHandle, the elements being called
// "string" and "int" (which describe the type of data manipulated).
//
// For the string item, each callout shifts data to the left and inserts its own
// data.  The data is a string of the form "nmc", where "n" is the number of
// the library, "m" is the callout number and "y" is the indication of what
// callout handle was passed as an argument ("1" or "2": "0" is used when no
// identification has been set in the callout handle).
//
// For simplicity, and to cut down the number of functions actually written,
// the callout indicator ("1" or "2") ) used in the in the CalloutHandle
// functions is passed via a CalloutArgument.  The argument is named "string":
// use of a name the same as that of one of the context elements serves as a
// check that the argument name space and argument context space are separate.
//
// For integer data, the value starts at zero and an increment is added on each
// call.  This increment is equal to:
//
// 100 * library number + 10 * callout number + callout handle
//
// Although this gives less information than the string value, the reasons for
// using it are:
//
// - It is a separate item in the context, so checks that the context can
//   handle multiple items.
// - It provides an item that can be deleted by the context deletion
//   methods.

// Values set in the CalloutHandle context.  There are three libraries, so
// there are three contexts for the callout, one for each library.

std::string& resultCalloutString(int index) {
    static std::string result_callout_string[3];
    return (result_callout_string[index]);
}

int& resultCalloutInt(int index) {
    static int result_callout_int[3];
    return (result_callout_int[index]);
}

// A simple function to zero the results.

static void zero_results() {
    for (int i = 0; i < 3; ++i) {
        resultCalloutString(i) = "";
        resultCalloutInt(i) = 0;
    }
}

// Library callouts.

// Common code for setting the callout context values.

int
execute(CalloutHandle& callout_handle, int library_num, int callout_num) {

    // Obtain the callout handle number
    int handle_num = 0;
    try  {
        callout_handle.getArgument("handle_num", handle_num);
    } catch (const NoSuchArgument&) {
        // handle_num argument not set: this is the case in the tests where
        // the context_create hook check is tested.
        handle_num = 0;
    }

    // Create the basic data to be appended to the context value.
    int idata = 100 * library_num + 10 * callout_num + handle_num;
    string sdata = boost::lexical_cast<string>(idata);

    // Get the context data. As before, this will not exist for the first
    // callout called. (In real life, the library should create it when the
    // "context_create" hook gets called before any packet processing takes
    // place.)
    int int_value = 0;
    try {
        callout_handle.getContext("int", int_value);
    } catch (const NoSuchCalloutContext&) {
        int_value = 0;
    }

    string string_value = "";
    try {
        callout_handle.getContext("string", string_value);
    } catch (const NoSuchCalloutContext&) {
        string_value = "";
    }

    // Update the values and set them back in the callout context.
    int_value += idata;
    callout_handle.setContext("int", int_value);

    string_value += sdata;
    callout_handle.setContext("string", string_value);

    return (0);
}

// The following functions are the actual callouts - the name is of the
// form "callout_<library number>_<callout number>"

int
callout11(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 1, 1));
}

int
callout12(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 1, 2));
}

int
callout13(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 1, 3));
}

int
callout21(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 2, 1));
}

int
callout22(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 2, 2));
}

int
callout23(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 2, 3));
}

int
callout31(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 3, 1));
}

int
callout32(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 3, 2));
}

int
callout33(CalloutHandle& callout_handle) {
    return (execute(callout_handle, 3, 3));
}

// Common callout code for the fourth hook (which makes the data available for
// checking).  It copies the library and callout context data to the global
// variables.

int printExecute(CalloutHandle& callout_handle, int library_num) {
    callout_handle.getContext("string", resultCalloutString(library_num - 1));
    callout_handle.getContext("int", resultCalloutInt(library_num - 1));

    return (0);
}

// These are the actual callouts.

int
print1(CalloutHandle& callout_handle) {
    return (printExecute(callout_handle, 1));
}

int
print2(CalloutHandle& callout_handle) {
    return (printExecute(callout_handle, 2));
}

int
print3(CalloutHandle& callout_handle) {
    return (printExecute(callout_handle, 3));
}

// This test checks the many-faced nature of the context for the CalloutContext.

TEST_F(HandlesTest, ContextAccessCheck) {
    // Register callouts for the different libraries.
    CalloutHandle handle(getCalloutManager());

    getCalloutManager()->registerCallout("alpha", callout11, 0);
    getCalloutManager()->registerCallout("beta", callout12, 0);
    getCalloutManager()->registerCallout("gamma", callout13, 0);
    getCalloutManager()->registerCallout("delta", print1, 0);

    getCalloutManager()->registerCallout("alpha", callout21, 1);
    getCalloutManager()->registerCallout("beta", callout22, 1);
    getCalloutManager()->registerCallout("gamma", callout23, 1);
    getCalloutManager()->registerCallout("delta", print2, 1);

    getCalloutManager()->registerCallout("alpha", callout31, 2);
    getCalloutManager()->registerCallout("beta", callout32, 2);
    getCalloutManager()->registerCallout("gamma", callout33, 2);
    getCalloutManager()->registerCallout("delta", print3, 2);

    // Create the callout handles and distinguish them by setting the
    // "handle_num" argument.
    CalloutHandle callout_handle_1(getCalloutManager());
    callout_handle_1.setArgument("handle_num", static_cast<int>(1));

    CalloutHandle callout_handle_2(getCalloutManager());
    callout_handle_2.setArgument("handle_num", static_cast<int>(2));

    // Now call the callouts attached to the first three hooks.  Each hook is
    // called twice (once for each callout handle) before the next hook is
    // called.
    getCalloutManager()->callCallouts(alpha_index_, callout_handle_1);
    getCalloutManager()->callCallouts(alpha_index_, callout_handle_2);
    getCalloutManager()->callCallouts(beta_index_, callout_handle_1);
    getCalloutManager()->callCallouts(beta_index_, callout_handle_2);
    getCalloutManager()->callCallouts(gamma_index_, callout_handle_1);
    getCalloutManager()->callCallouts(gamma_index_, callout_handle_2);

    // Get the results for each callout (the callout on hook "delta" copies
    // the context values into a location the test can access).  Explicitly
    // zero the variables before getting the results so we are certain that
    // the values are the results of the callouts.

    zero_results();

    // To explain the expected callout context results.
    //
    // Each callout handle maintains a separate context for each library.  When
    // the first call to callCallouts() is made, "111" gets appended to
    // the context for library 1 maintained by the first callout handle, "211"
    // gets appended to the context maintained for library 2, and "311" to
    // the context maintained for library 3.  In each case, the first digit
    // corresponds to the library number, the second to the callout number and
    // the third to the "handle_num" of the callout handle. For the first call
    // to callCallouts, handle 1 is used, so the last digit is always 1.
    //
    // The next call to callCallouts() calls the same callouts but for the
    // second callout handle.  It also maintains three contexts (one for
    // each library) and they will get "112", "212", "312" appended to
    // them. The explanation for the digits is the same as before, except that
    // in this case, the callout handle is number 2, so the third digit is
    // always 2.  These additions don't affect the contexts maintained by
    // callout handle 1.
    //
    // The process is then repeated for hooks "beta" and "gamma" which, for
    // callout handle 1, append "121", "221" and "321" for hook "beta" and
    // "311", "321" and "331" for hook "gamma".
    //
    // The expected integer values can be found by summing up the values
    // corresponding to the elements of the strings.

    // At this point, we have only called the "print" function for callout
    // handle "1", so the following results are checking the context values
    // maintained in that callout handle.

    getCalloutManager()->callCallouts(delta_index_, callout_handle_1);
    EXPECT_EQ("111121131", resultCalloutString(0));
    EXPECT_EQ("211221231", resultCalloutString(1));
    EXPECT_EQ("311321331", resultCalloutString(2));

    EXPECT_EQ((111 + 121 + 131), resultCalloutInt(0));
    EXPECT_EQ((211 + 221 + 231), resultCalloutInt(1));
    EXPECT_EQ((311 + 321 + 331), resultCalloutInt(2));

    // Repeat the checks for callout 2.

    zero_results();
    getCalloutManager()->callCallouts(delta_index_, callout_handle_2);

    EXPECT_EQ((112 + 122 + 132), resultCalloutInt(0));
    EXPECT_EQ((212 + 222 + 232), resultCalloutInt(1));
    EXPECT_EQ((312 + 322 + 332), resultCalloutInt(2));

    EXPECT_EQ("112122132", resultCalloutString(0));
    EXPECT_EQ("212222232", resultCalloutString(1));
    EXPECT_EQ("312322332", resultCalloutString(2));
}

// Now repeat the test, but add a deletion callout to the list.  The "beta"
// hook of library 2 will have an additional callout to delete the "int"
// element: the same hook for library 3 will delete both elements.  In
// addition, the names of context elements for the libraries at this point
// will be printed.

// List of context item names.

vector<string>&
getItemNames(int index) {
    static vector<string> context_items[3];
    return (context_items[index]);
}

// Context item deletion functions.

int
deleteIntContextItem(CalloutHandle& handle) {
    handle.deleteContext("int");
    return (0);
}

int
deleteAllContextItems(CalloutHandle& handle) {
    handle.deleteAllContext();
    return (0);
}

// Generic print function - copy names in sorted order.

int
printContextNamesExecute(CalloutHandle& handle, int library_num) {
    const int index = library_num - 1;
    getItemNames(index) = handle.getContextNames();
    sort(getItemNames(index).begin(), getItemNames(index).end());
    return (0);
}

int
printContextNames1(CalloutHandle& handle) {
    return (printContextNamesExecute(handle, 1));
}

int
printContextNames2(CalloutHandle& handle) {
    return (printContextNamesExecute(handle, 2));
}

int
printContextNames3(CalloutHandle& handle) {
    return (printContextNamesExecute(handle, 3));
}

// Perform the test including deletion of context items.

TEST_F(HandlesTest, ContextDeletionCheck) {
    getCalloutManager()->registerCallout("alpha", callout11, 0);
    getCalloutManager()->registerCallout("beta", callout12, 0);
    getCalloutManager()->registerCallout("beta", printContextNames1, 0);
    getCalloutManager()->registerCallout("gamma", callout13, 0);
    getCalloutManager()->registerCallout("delta", print1, 0);

    getCalloutManager()->registerCallout("alpha", callout21, 1);
    getCalloutManager()->registerCallout("beta", callout22, 1);
    getCalloutManager()->registerCallout("beta", deleteIntContextItem, 1);
    getCalloutManager()->registerCallout("beta", printContextNames2, 1);
    getCalloutManager()->registerCallout("gamma", callout23, 1);
    getCalloutManager()->registerCallout("delta", print2, 1);

    getCalloutManager()->registerCallout("alpha", callout31, 2);
    getCalloutManager()->registerCallout("beta", callout32, 2);
    getCalloutManager()->registerCallout("beta", deleteAllContextItems, 2);
    getCalloutManager()->registerCallout("beta", printContextNames3, 2);
    getCalloutManager()->registerCallout("gamma", callout33, 2);
    getCalloutManager()->registerCallout("delta", print3, 2);

    // Create the callout handles and distinguish them by setting the "long"
    // argument.
    CalloutHandle callout_handle_1(getCalloutManager());
    callout_handle_1.setArgument("handle_num", static_cast<int>(1));

    CalloutHandle callout_handle_2(getCalloutManager());
    callout_handle_2.setArgument("handle_num", static_cast<int>(2));

    // Now call the callouts attached to the first three hooks.  Each hook is
    // called twice (once for each callout handle) before the next hook is
    // called.
    getCalloutManager()->callCallouts(alpha_index_, callout_handle_1);
    getCalloutManager()->callCallouts(alpha_index_, callout_handle_2);
    getCalloutManager()->callCallouts(beta_index_, callout_handle_1);
    getCalloutManager()->callCallouts(beta_index_, callout_handle_2);
    getCalloutManager()->callCallouts(gamma_index_, callout_handle_1);
    getCalloutManager()->callCallouts(gamma_index_, callout_handle_2);

    // Get the results for each callout.  Explicitly zero the variables before
    // getting the results so we are certain that the values are the results
    // of the callouts.

    zero_results();
    getCalloutManager()->callCallouts(delta_index_, callout_handle_1);

    // The logic by which the expected results are arrived at is described
    // in the ContextAccessCheck test.  The results here are different
    // because context items have been modified along the way.

    EXPECT_EQ((111 + 121 + 131), resultCalloutInt(0));
    EXPECT_EQ((            231), resultCalloutInt(1));
    EXPECT_EQ((            331), resultCalloutInt(2));

    EXPECT_EQ("111121131", resultCalloutString(0));
    EXPECT_EQ("211221231", resultCalloutString(1));
    EXPECT_EQ(      "331", resultCalloutString(2));

    // Repeat the checks for callout handle 2.

    zero_results();
    getCalloutManager()->callCallouts(delta_index_, callout_handle_2);

    EXPECT_EQ((112 + 122 + 132), resultCalloutInt(0));
    EXPECT_EQ((            232), resultCalloutInt(1));
    EXPECT_EQ((            332), resultCalloutInt(2));

    EXPECT_EQ("112122132", resultCalloutString(0));
    EXPECT_EQ("212222232", resultCalloutString(1));
    EXPECT_EQ(      "332", resultCalloutString(2));

    // ... and check what the names of the context items are after the callouts
    // for hook "beta".  We know they are in sorted order.

    EXPECT_EQ(2, getItemNames(0).size());
    EXPECT_EQ(string("int"),    getItemNames(0)[0]);
    EXPECT_EQ(string("string"), getItemNames(0)[1]);

    EXPECT_EQ(1, getItemNames(1).size());
    EXPECT_EQ(string("string"), getItemNames(1)[0]);

    EXPECT_EQ(0, getItemNames(2).size());
}

// Tests that the CalloutHandle's constructor and destructor call the
// context_create and context_destroy callbacks (if registered).  For
// simplicity, we'll use the same callout functions as used above.

TEST_F(HandlesTest, ConstructionDestructionCallouts) {

    // Register context callouts.
    getCalloutManager()->registerCallout("context_create", callout11, 0);
    getCalloutManager()->registerCallout("context_create", print1, 0);
    getCalloutManager()->registerCallout("context_destroy", callout12, 0);
    getCalloutManager()->registerCallout("context_destroy", print1, 0);

    // Create the CalloutHandle and check that the constructor callout
    // has run.
    zero_results();
    boost::scoped_ptr<CalloutHandle>
        callout_handle(new CalloutHandle(getCalloutManager()));
    EXPECT_EQ("110", resultCalloutString(0));
    EXPECT_EQ(110, resultCalloutInt(0));

    // Check that the destructor callout runs.  Note that the "print1" callout
    // didn't destroy the library context - it only copied it to where it
    // could be examined.  As a result, the destructor callout appends its
    // elements to the constructor's values and the result is printed.
    zero_results();
    callout_handle.reset();

    EXPECT_EQ("110120", resultCalloutString(0));
    EXPECT_EQ((110 + 120), resultCalloutInt(0));
}

// Testing the operation of the "skip" flag.  Callouts print the value
// they see in the flag and either leave it unchanged, set it or clear it.
int
calloutPrintSkip(CalloutHandle& handle) {
    static const std::string YES("Y");
    static const std::string NO("N");
    static const std::string DROP("D");
    static const std::string PARK("P");

    switch (handle.getStatus()) {
    case CalloutHandle::NEXT_STEP_CONTINUE:
        HandlesTest::common_string_ += NO; // skip = no
        break;
    case CalloutHandle::NEXT_STEP_SKIP:
        HandlesTest::common_string_ += YES; // skip = yes
        break;
    case CalloutHandle::NEXT_STEP_DROP:
        HandlesTest::common_string_ += DROP; // drop
        break;
    case CalloutHandle::NEXT_STEP_PARK:
        HandlesTest::common_string_ += PARK; // park
        break;
    }
    return (0);
}

int
calloutSetSkip(CalloutHandle& handle) {
    static_cast<void>(calloutPrintSkip(handle));
    handle.setStatus(CalloutHandle::NEXT_STEP_SKIP);
    return (0);
}

int
calloutClearSkip(CalloutHandle& handle) {
    static_cast<void>(calloutPrintSkip(handle));
    handle.setStatus(CalloutHandle::NEXT_STEP_CONTINUE);
    return (0);
}

// Do a series of tests, returning with the skip flag set "true".

TEST_F(HandlesTest, ReturnSkipSet) {
    getCalloutManager()->registerCallout("alpha", calloutPrintSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 0);

    getCalloutManager()->registerCallout("alpha", calloutPrintSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 1);

    getCalloutManager()->registerCallout("alpha", calloutPrintSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 2);

    CalloutHandle callout_handle(getCalloutManager());
    getCalloutManager()->callCallouts(alpha_index_, callout_handle);

    // Check result.  For ease of visual checking, the expected string is
    // divided into sections corresponding to the blocks of callouts above.
    EXPECT_EQ(std::string("NNYY" "NNYYN" "NNYN"), common_string_);

    // ... and check that the skip flag on exit from callCallouts is set.
    EXPECT_EQ(CalloutHandle::NEXT_STEP_SKIP, callout_handle.getStatus());
}

// Repeat the test, returning with the skip flag clear.
TEST_F(HandlesTest, ReturnSkipClear) {
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 0);

    getCalloutManager()->registerCallout("alpha", calloutPrintSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 1);

    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutPrintSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutClearSkip, 2);

    CalloutHandle callout_handle(getCalloutManager());
    getCalloutManager()->callCallouts(alpha_index_, callout_handle);

    // Check result.  For ease of visual checking, the expected string is
    // divided into sections corresponding to the blocks of callouts above.
    EXPECT_EQ(std::string("NYY" "NNYNYN" "NNNY"), common_string_);

    // ... and check that the skip flag on exit from callCallouts is set.
    EXPECT_EQ(CalloutHandle::NEXT_STEP_CONTINUE, callout_handle.getStatus());
}

// Check that the skip flag is cleared when callouts are called - even if
// there are no callouts.

TEST_F(HandlesTest, NoCalloutsSkipTest) {
    // Note - no callouts are registered on any hook.
    CalloutHandle callout_handle(getCalloutManager());

    // Clear the skip flag and call a hook with no callouts.
    callout_handle.setStatus(CalloutHandle::NEXT_STEP_CONTINUE);
    getCalloutManager()->callCallouts(alpha_index_, callout_handle);
    EXPECT_EQ(CalloutHandle::NEXT_STEP_CONTINUE, callout_handle.getStatus());

    // Set the skip flag and call a hook with no callouts.
    callout_handle.setStatus(CalloutHandle::NEXT_STEP_SKIP);
    getCalloutManager()->callCallouts(alpha_index_, callout_handle);
    EXPECT_EQ(CalloutHandle::NEXT_STEP_CONTINUE, callout_handle.getStatus());
}

// The next set of callouts do a similar thing to the above "skip" tests,
// but alter the value of a string argument.  This is for testing that the
// a callout is able to change an argument and return it to the caller.

const char* MODIFIED_ARG = "modified_arg";

int
calloutSetArgumentCommon(CalloutHandle& handle, const char* what) {
    std::string modified_arg = "";

    handle.getArgument(MODIFIED_ARG, modified_arg);
    modified_arg = modified_arg + std::string(what);
    handle.setArgument(MODIFIED_ARG, modified_arg);
    return (0);
}

int
calloutSetArgumentSkip(CalloutHandle& handle) {
    return (calloutSetArgumentCommon(handle, "S"));
}

int
calloutSetArgumentContinue(CalloutHandle& handle) {
    return (calloutSetArgumentCommon(handle, "C"));
}

int
calloutSetArgumentDrop(CalloutHandle& handle) {
    return (calloutSetArgumentCommon(handle, "D"));
}

int
calloutSetArgumentPark(CalloutHandle& handle) {
    return (calloutSetArgumentCommon(handle, "P"));
}

// ... and a callout to just copy the argument to the "common_string_" variable
// but otherwise not alter it.

int
calloutPrintArgument(CalloutHandle& handle) {
    handle.getArgument(MODIFIED_ARG, HandlesTest::common_string_);
    return (0);
}

// This test verifies that the next step status is processed appropriately.
// The test checks the following next step statuses: CONTINUE, SKIP, DROP.
TEST_F(HandlesTest, CheckModifiedArgument) {
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentSkip, 0);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentContinue, 0);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentContinue, 0);

    getCalloutManager()->registerCallout("alpha", calloutSetArgumentSkip, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentDrop, 1);
    getCalloutManager()->registerCallout("alpha", calloutPrintArgument, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentDrop, 1);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentContinue, 1);

    getCalloutManager()->registerCallout("alpha", calloutSetArgumentSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentContinue, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentPark, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentSkip, 2);
    getCalloutManager()->registerCallout("alpha", calloutSetArgumentPark, 2);

    // Create the argument with an initial empty string value.  Then call the
    // sequence of callouts above.
    CalloutHandle callout_handle(getCalloutManager());
    std::string modified_arg = "";
    callout_handle.setArgument(MODIFIED_ARG, modified_arg);
    getCalloutManager()->callCallouts(alpha_index_, callout_handle);

    // Check the intermediate and results.  For visual checking, the expected
    // string is divided into sections corresponding to the blocks of callouts
    // above.
    EXPECT_EQ(std::string("SCC" "SD"), common_string_);

    callout_handle.getArgument(MODIFIED_ARG, modified_arg);
    EXPECT_EQ(std::string("SCC" "SDDC" "SCPSP"), modified_arg);
}

// Test that the CalloutHandle provides the name of the hook to which the
// callout is attached.

int
callout_hook_name(CalloutHandle& callout_handle) {
    HandlesTest::common_string_ = callout_handle.getHookName();
    return (0);
}

int
callout_hook_dummy(CalloutHandle&) {
    return (0);
}

TEST_F(HandlesTest, HookName) {
    getCalloutManager()->registerCallout("alpha", callout_hook_name, 0);
    getCalloutManager()->registerCallout("beta", callout_hook_name, 0);

    // Call alpha and beta callouts and check the hook to which they belong.
    CalloutHandle callout_handle(getCalloutManager());

    EXPECT_EQ(std::string(""), HandlesTest::common_string_);

    getCalloutManager()->callCallouts(alpha_index_, callout_handle);
    EXPECT_EQ(std::string("alpha"), HandlesTest::common_string_);

    getCalloutManager()->callCallouts(beta_index_, callout_handle);
    EXPECT_EQ(std::string("beta"), HandlesTest::common_string_);

    // Make sure that the callout accesses the name even if it is not the
    // only callout in the list.
    getCalloutManager()->registerCallout("gamma", callout_hook_dummy, 1);
    getCalloutManager()->registerCallout("gamma", callout_hook_name, 1);
    getCalloutManager()->registerCallout("gamma", callout_hook_dummy, 1);

    EXPECT_EQ(std::string("beta"), HandlesTest::common_string_);
    getCalloutManager()->callCallouts(gamma_index_, callout_handle);
    EXPECT_EQ(std::string("gamma"), HandlesTest::common_string_);
}

} // Anonymous namespace

max_stars_repo_name: svenauhagen/kea

max_issues_repo_name: svenauhagen/kea

max_forks_repo_name: svenauhagen/kea


text:
/* json_service_endpoint_test.cc
   Jeremy Barnes, 9 November 2012
   Copyright (c) 2012 Datacratic Inc.  All rights reserved.

   Test for the JSON service endpoint.
*/

#define BOOST_TEST_MAIN
#define BOOST_TEST_DYN_LINK

#include <boost/test/unit_test.hpp>
#include <boost/make_shared.hpp>
#include "soa/service/named_endpoint.h"
#include "soa/service/message_loop.h"
#include "soa/service/rest_service_endpoint.h"
#include "soa/service/rest_proxy.h"
#include <sys/socket.h>
#include "jml/utils/guard.h"
#include "jml/arch/exception_handler.h"
#include "jml/utils/testing/watchdog.h"
#include "jml/utils/testing/fd_exhauster.h"
#include "jml/utils/vector_utils.h"
#include "jml/arch/timers.h"
#include <thread>
#include "soa/service/zmq_utils.h"
#include "soa/service/testing/zookeeper_temporary_server.h"

using namespace std;
using namespace ML;
using namespace Datacratic;

/*****************************************************************************/
/* ECHO SERVICE                                                              */
/*****************************************************************************/

/** Simple test service that listens on zeromq and simply echos everything
    that it gets back.
*/

struct EchoService : public ServiceBase, public RestServiceEndpoint {

    EchoService(std::shared_ptr<ServiceProxies> proxies,
                const std::string & serviceName)
        : ServiceBase(serviceName, proxies),
          RestServiceEndpoint(proxies->zmqContext)
    {
        proxies->config->removePath(serviceName);
        RestServiceEndpoint::init(proxies->config,
                                  serviceName, 0.0005 /* maxAddedLatency */);
    }

    ~EchoService()
    {
        shutdown();
    }

    virtual void handleRequest(const ConnectionId & connection,
                               const RestRequest & request) const
    {
        //cerr << "handling request " << request << endl;
        if (request.verb != "POST")
            throw ML::Exception("echo service needs POST");
        if (request.resource != "/echo")
            throw ML::Exception("echo service only responds to /echo");
        connection.sendResponse(200, request.payload, "text/plain");
    }
};

BOOST_AUTO_TEST_CASE( test_named_endpoint )
{
    ZooKeeper::TemporaryServer zookeeper;
    zookeeper.start();

    auto proxies = std::make_shared<ServiceProxies>();
    proxies->useZookeeper(ML::format("localhost:%d", zookeeper.getPort()));

    int totalPings = 1000;

    EchoService service(proxies, "echo");
    auto addr = service.bindTcp();
    cerr << "echo service is listening on " << addr.first << " and "
         << addr.second << endl;

    service.start();

    proxies->config->dump(cerr);

    volatile int numPings = 0;

    auto runZmqThread = [=, &numPings] ()
        {
            RestProxy proxy(proxies->zmqContext);
            proxy.init(proxies->config, "echo");
            proxy.start();
            cerr << "connected" << endl;

            volatile int numOutstanding = 0;

            while (numPings < totalPings) {
                int i = __sync_add_and_fetch(&numPings, 1);

                if (i && i % 1000 == 0)
                    cerr << i << " with " << numOutstanding << " outstanding"
                         << endl;

                auto onResponse = [=, &numOutstanding]
                    (std::exception_ptr ptr,
                     int responseCode,
                     std::string body)
                    {
                        //cerr << "got response " << responseCode
                        //     << endl;
                        ML::atomic_dec(numOutstanding);

                        if (ptr)
                            throw ML::Exception("response returned exception");
                        ExcAssertEqual(responseCode, 200);
                        ExcAssertEqual(body, to_string(i));

                        futex_wake(numOutstanding);
                    };

                proxy.push(onResponse,
                           "POST", "/echo", {}, to_string(i));
                ML::atomic_inc(numOutstanding);
            }

            proxy.sleepUntilIdle();

            //ML::sleep(1.0);

            cerr << "shutting down proxy " << this << endl;
            proxy.shutdown();
            cerr << "done proxy shutdown" << endl;
        };

#if 0
    auto runHttpThread = [&] ()
        {
            HttpNamedRestProxy proxy;
            proxy.init(proxies->config);
            proxy.connect("echo/http");

            while (numPings < totalPings) {
                int i = __sync_add_and_fetch(&numPings, 1);

                if (i && i % 1000 == 0)
                    cerr << i << endl;

                auto response = proxy.post("/echo", to_string(i));

                ExcAssertEqual(response.code_, 200);
                ExcAssertEqual(response.body_, to_string(i));
            }

        };
#endif

    boost::thread_group threads;

    for (unsigned i = 0;  i < 8;  ++i) {
        threads.create_thread(runZmqThread);
    }

    //for (unsigned i = 0;  i < 5;  ++i) {
    //    threads.create_thread(runHttpThread);
    //}

    threads.join_all();

    cerr << "finished requests" << endl;

    service.shutdown();
}

max_stars_repo_name: etnrlz/rtbkit

max_issues_repo_name: TuanTranEngineer/rtbkit

max_forks_repo_name: TuanTranEngineer/rtbkit