rendered paste bodytypedef std::map<int, AnyDataP> argMap;
template<typename... Args> struct Caster;
template<>
struct Caster<>
{
static const int something = 0;
int setup( const argMap &m, int arg ) { return arg; }
};
template<typename T>
void assignThing( T **thing, void *with )
{
*thing = (T *)with;
}
template<typename T>
void assignThing( T *thing, void *with )
{
}
template<typename T, typename... Args>
struct Caster<T, Args...>
{
typedef
typename boost::mpl::if_<
boost::is_reference<T>,
typename boost::add_pointer<typename boost::remove_reference<T>::type >::type,
T >::type NonRefType;
NonRefType a;
Caster<Args...> b;
int setup( argMap &m, int arg = 0 )
{
if ( boost::is_reference<T>::value )
{
std::cout << "Reference argument" << std::endl;
assignThing( &a, (m[arg]).asVoid() );
} else
{
std::cout << "Fetching arg #" << arg << std::endl;
if ( !m.count( arg ) )
throw std::string( "Wrong number of args" );
a = (m[arg]).getValue<NonRefType>();
std::cout << "Left the fetching function, set to " << TypeName<NonRefType>::getValue() << " - " << a << std::endl;
}
return b.setup( m, ++arg );
}
};
template<typename... Args> struct argsToAnyDataP;
template<> struct argsToAnyDataP<>
{
static const int num = 0;
static const int deepest = 0;
static int argGetter( int n, argMap &m ) { return 0; }
};
template<typename T, typename... Args>
struct argsToAnyDataP<T, Args...>
{
static int argGetter( int n, argMap &m,
const T& arg,
const Args&... args )
{
argsToAnyDataP<Args...>::argGetter( n+1, m, args... );
m[ n ] = arg;
}
};
template<typename... Args>
AnyData AnyData::operator()(const Args&... args)
{
typedef AnyData (*fptr)(void *, argMap &);
fptr f = (fptr)callerFunc;
argMap m;
argsToAnyDataP<Args...>::argGetter( 0, m, args... );
//std::cout << "I am here.." << std::endl;
return f( getValue<void *>(), m );
}
template<typename RET, typename... Args>
AnyData theCaller( void * funcToCall, argMap &m ) //, const Args... a )
{
std::cout << "I am in the caller." << sizeof...( Args) << std::endl;
Caster<Args...> them;
if ( them.setup( m ) != m.size() )
throw std::string("Wrong number of arguments");
typedef RET (*fptr)( Caster<Args...> );
std::cout << "On my way out.." << std::endl;
return AnyData( ((fptr)funcToCall)( them ) );
}
template<typename... Args>
void AnyData::setCallerFunc( AnyData (*p)(const Args...) )
{
callerFunc = (void *)p;
}
template<typename RET, typename... Args>
AnyData &AnyData::operator=( RET (*assign)( Args... ) )
{
typedef __typeof(assign) funcp;
//Args...;
std::cout << "Assigning function pointer..." << std::endl;
funcArgs = functionGetter<Args...>();
setCallerFunc( &theCaller<RET, Args...> );
//theCaller<Args...>( 1, 2 );
delete data;
data = new Storage<funcp>( assign );
return *this;
}