Add index tags to FunctionInterface features.

The functors in the ForEach, StaticTransform, and DynamicTransform
methods sometimes can use the index of the parameter that they are
operating on. This can be a helpful diagnostic in compile and run-time
errors. It is also helpful when linking parameters from one
FunctionInterface with those of another.

This new features are now replacing implementations using the Zip
functionality that was removed earlier. The implementation is actually
simplified a bit.
This commit is contained in:
Kenneth Moreland 2015-01-13 17:26:13 -08:00
parent 0fdc311682
commit 37dac92052
12 changed files with 721 additions and 485 deletions

@ -30,6 +30,8 @@
#include <boost/static_assert.hpp> #include <boost/static_assert.hpp>
#include <sstream>
namespace vtkm { namespace vtkm {
namespace cont { namespace cont {
@ -128,16 +130,17 @@ struct CompositeVectorArrayToPortalCont {
template<typename DeviceAdapterTag> template<typename DeviceAdapterTag>
struct CompositeVectorArrayToPortalExec { struct CompositeVectorArrayToPortalExec {
template<typename ArrayHandleType> template<typename ArrayHandleType, vtkm::IdComponent Index>
struct ReturnType { struct ReturnType {
typedef typename ArrayHandleType::template ExecutionTypes< typedef typename ArrayHandleType::template ExecutionTypes<
DeviceAdapterTag>::PortalConst type; DeviceAdapterTag>::PortalConst type;
}; };
template<typename ArrayHandleType> template<typename ArrayHandleType, vtkm::IdComponent Index>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
typename ReturnType<ArrayHandleType>::type typename ReturnType<ArrayHandleType, Index>::type
operator()(const ArrayHandleType &array) const { operator()(const ArrayHandleType &array,
vtkm::internal::IndexTag<Index>) const {
return array.PrepareForInput(DeviceAdapterTag()); return array.PrepareForInput(DeviceAdapterTag());
} }
}; };
@ -146,12 +149,15 @@ struct CheckArraySizeFunctor {
vtkm::Id ExpectedSize; vtkm::Id ExpectedSize;
CheckArraySizeFunctor(vtkm::Id expectedSize) : ExpectedSize(expectedSize) { } CheckArraySizeFunctor(vtkm::Id expectedSize) : ExpectedSize(expectedSize) { }
template<typename T> template<typename T, vtkm::IdComponent Index>
void operator()(const T &a) const { void operator()(const T &a, vtkm::internal::IndexTag<Index>) const {
if (a.GetNumberOfValues() != this->ExpectedSize) if (a.GetNumberOfValues() != this->ExpectedSize)
{ {
throw vtkm::cont::ErrorControlBadValue( std::stringstream message;
"All input arrays to ArrayHandleCompositeVector must be the same size."); message << "All input arrays to ArrayHandleCompositeVector must be the same size.\n"
<< "Array " << Index-1 << " has " << a.GetNumberOfValues()
<< ". Expected " << this->ExpectedSize << ".";
throw vtkm::cont::ErrorControlBadValue(message.str().c_str());
} }
} }
}; };

@ -20,7 +20,7 @@
#ifndef vtk_m_cont_internal_DynamicTransform_h #ifndef vtk_m_cont_internal_DynamicTransform_h
#define vtk_m_cont_internal_DynamicTransform_h #define vtk_m_cont_internal_DynamicTransform_h
#include "vtkm/internal/ExportMacros.h" #include "vtkm/internal/IndexTag.h"
namespace vtkm { namespace vtkm {
namespace cont { namespace cont {
@ -62,10 +62,13 @@ struct DynamicTransformTraits {
/// ///
struct DynamicTransform struct DynamicTransform
{ {
template<typename InputType, typename ContinueFunctor> template<typename InputType,
typename ContinueFunctor,
vtkm::IdComponent Index>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
void operator()(const InputType &input, void operator()(const InputType &input,
const ContinueFunctor &continueFunc) const const ContinueFunctor &continueFunc,
vtkm::internal::IndexTag<Index>) const
{ {
this->DoTransform( this->DoTransform(
input, input,

@ -85,22 +85,24 @@ void TestBasicTransform()
std::cout << "Testing basic transform." << std::endl; std::cout << "Testing basic transform." << std::endl;
vtkm::cont::internal::DynamicTransform transform; vtkm::cont::internal::DynamicTransform transform;
vtkm::internal::IndexTag<1> indexTag;
std::cout << " Trying with simple scalar." << std::endl; std::cout << " Trying with simple scalar." << std::endl;
TRY_TRANSFORM(transform(vtkm::FloatDefault(5), ScalarFunctor())); TRY_TRANSFORM(transform(vtkm::FloatDefault(5), ScalarFunctor(), indexTag));
std::cout << " Trying with basic scalar array." << std::endl; std::cout << " Trying with basic scalar array." << std::endl;
vtkm::cont::ArrayHandle<vtkm::FloatDefault> concreteArray; vtkm::cont::ArrayHandle<vtkm::FloatDefault> concreteArray;
TRY_TRANSFORM(transform(concreteArray, ArrayHandleScalarFunctor())); TRY_TRANSFORM(transform(concreteArray, ArrayHandleScalarFunctor(), indexTag));
std::cout << " Trying scalar dynamic array." << std::endl; std::cout << " Trying scalar dynamic array." << std::endl;
vtkm::cont::DynamicArrayHandle dynamicArray = concreteArray; vtkm::cont::DynamicArrayHandle dynamicArray = concreteArray;
TRY_TRANSFORM(transform(dynamicArray, ArrayHandleScalarFunctor())); TRY_TRANSFORM(transform(dynamicArray, ArrayHandleScalarFunctor(), indexTag));
std::cout << " Trying with unusual (string) dynamic array." << std::endl; std::cout << " Trying with unusual (string) dynamic array." << std::endl;
dynamicArray = vtkm::cont::ArrayHandle<std::string>(); dynamicArray = vtkm::cont::ArrayHandle<std::string>();
TRY_TRANSFORM(transform(dynamicArray.ResetTypeList(TypeListTagString()), TRY_TRANSFORM(transform(dynamicArray.ResetTypeList(TypeListTagString()),
ArrayHandleStringFunctor())); ArrayHandleStringFunctor(),
indexTag));
} }
void TestFunctionTransform() void TestFunctionTransform()

@ -25,6 +25,7 @@ set(headers
FunctionInterface.h FunctionInterface.h
FunctionInterfaceDetailPost.h FunctionInterfaceDetailPost.h
FunctionInterfaceDetailPre.h FunctionInterfaceDetailPre.h
IndexTag.h
Invocation.h Invocation.h
ListTagDetail.h ListTagDetail.h
) )

@ -20,9 +20,10 @@
#ifndef vtk_m_internal_FunctionInterface_h #ifndef vtk_m_internal_FunctionInterface_h
#define vtk_m_internal_FunctionInterface_h #define vtk_m_internal_FunctionInterface_h
#include <vtkm/Pair.h>
#include <vtkm/Types.h> #include <vtkm/Types.h>
#include <vtkm/internal/IndexTag.h>
#include <boost/function_types/components.hpp> #include <boost/function_types/components.hpp>
#include <boost/function_types/function_arity.hpp> #include <boost/function_types/function_arity.hpp>
#include <boost/function_types/function_type.hpp> #include <boost/function_types/function_type.hpp>
@ -301,27 +302,75 @@ public:
} }
/// Gets the value for the parameter of the given index. Parameters are /// Gets the value for the parameter of the given index. Parameters are
/// indexed starting at 1. To use this method you have to specify the index /// indexed starting at 1. To use this method you have to specify a static,
/// as a template parameter. If you are using FunctionInterface within a /// compile time index. There are two ways to specify the index. The first is
/// template (which is almost always the case), then you will have to use the /// to specify a specific template parameter (e.g.
/// template keyword. For example, here is a simple implementation of a /// <tt>GetParameter<1>()</tt>). Note that if you are using FunctionInterface
/// method that grabs the first parameter of FunctionInterface. /// within a template (which is almost always the case), then you will have
/// to use the template keyword. For example, here is a simple implementation
/// of a method that grabs the first parameter of FunctionInterface.
/// ///
/// \code{.cpp} /// \code{.cpp}
/// template<FunctionSignature> /// template<FunctionSignature>
/// void Foo(const vtkm::cont::internal::FunctionInterface<FunctionSignature> &fInterface) /// void Foo(const vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// { /// {
/// bar(fInterface.template GetParameter<1>()); /// bar(fInterface.template GetParameter<1>());
/// } /// }
/// \endcode /// \endcode
/// ///
/// Alternatively the \c GetParameter method also has an optional argument
/// that can be a \c IndexTag that specifies the parameter index. Here is
/// a repeat of the previous example using this method.
///
/// \code{.cpp}
/// template<FunctionSignature>
/// void Foo(const vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// {
/// using vtkm::internal::IndexTag;
/// bar(fInterface.GetParameter(IndexTag<1>()));
/// }
/// \endcode
///
template<vtkm::IdComponent ParameterIndex> template<vtkm::IdComponent ParameterIndex>
VTKM_EXEC_CONT_EXPORT VTKM_EXEC_CONT_EXPORT
typename ParameterType<ParameterIndex>::type typename ParameterType<ParameterIndex>::type
GetParameter() const { GetParameter(
vtkm::internal::IndexTag<ParameterIndex> =
vtkm::internal::IndexTag<ParameterIndex>()) const {
return detail::GetParameter<ParameterIndex>(this->Parameters); return detail::GetParameter<ParameterIndex>(this->Parameters);
} }
/// Sets the value for the parameter of the given index. Parameters are
/// indexed starting at 1. To use this method you have to specify a static,
/// compile time index. There are two ways to specify the index. The first is
/// to specify a specific template parameter (e.g.
/// <tt>SetParameter<1>(value)</tt>). Note that if you are using
/// FunctionInterface within a template (which is almost always the case),
/// then you will have to use the template keyword. For example, here is a
/// simple implementation of a method that grabs the first parameter of
/// FunctionInterface.
///
/// \code{.cpp}
/// template<FunctionSignature>
/// void Foo(vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// {
/// fInterface.template SetParameter<1>(bar);
/// }
/// \endcode
///
/// Alternatively the \c GetParameter method also has an optional argument
/// that can be a \c IndexTag that specifies the parameter index. Here is
/// a repeat of the previous example using this method.
///
/// \code{.cpp}
/// template<FunctionSignature>
/// void Foo(vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// {
/// using vtkm::internal::IndexTag;
/// fInterface.SetParameter(bar, IndexTag<1>());
/// }
/// \endcode
///
/// Sets the value for the parameter of the given index. Parameters are /// Sets the value for the parameter of the given index. Parameters are
/// indexed starting at 1. To use this method you have to specify the index /// indexed starting at 1. To use this method you have to specify the index
/// as a template parameter. If you are using FunctionInterface within a /// as a template parameter. If you are using FunctionInterface within a
@ -330,7 +379,10 @@ public:
/// ///
template<vtkm::IdComponent ParameterIndex> template<vtkm::IdComponent ParameterIndex>
VTKM_EXEC_CONT_EXPORT VTKM_EXEC_CONT_EXPORT
void SetParameter(typename ParameterType<ParameterIndex>::type parameter) void SetParameter(
typename ParameterType<ParameterIndex>::type parameter,
vtkm::internal::IndexTag<ParameterIndex> =
vtkm::internal::IndexTag<ParameterIndex>())
{ {
detail::SetParameter<ParameterIndex>(this->Parameters, parameter); detail::SetParameter<ParameterIndex>(this->Parameters, parameter);
} }
@ -461,15 +513,47 @@ public:
/// Returns a new \c FunctionInterface with all the parameters of this \c /// Returns a new \c FunctionInterface with all the parameters of this \c
/// FunctionInterface except that the parameter indexed at the template /// FunctionInterface except that the parameter indexed at the template
/// parameter \c ParameterIndex is replaced with the given argument. This /// parameter \c ParameterIndex (also specified with the optional second
/// method can be used in place of SetParameter when the parameter type /// argument) is replaced with the given argument. This method can be used in
/// changes. The return type can be determined with the \c ReplaceType /// place of SetParameter when the parameter type changes. The return type
/// template. /// can be determined with the \c ReplaceType template.
/// Gets the value for the parameter of the given index. Parameters are
/// indexed starting at 1. To use this method you have to specify a static,
/// compile time index. There are two ways to specify the index. The first is
/// to specify a specific template parameter (e.g.
/// <tt>GetParameter<1>()</tt>). Note that if you are using FunctionInterface
/// within a template (which is almost always the case), then you will have
/// to use the template keyword. For example, here is a simple implementation
/// of a method that grabs the first parameter of FunctionInterface.
///
/// \code{.cpp}
/// template<FunctionSignature>
/// void Foo(const vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// {
/// bar(fInterface.template GetParameter<1>());
/// }
/// \endcode
///
/// Alternatively the \c GetParameter method also has an optional argument
/// that can be a \c IndexTag that specifies the parameter index. Here is
/// a repeat of the previous example using this method.
///
/// \code{.cpp}
/// template<FunctionSignature>
/// void Foo(const vtkm::internal::FunctionInterface<FunctionSignature> &fInterface)
/// {
/// using vtkm::internal::IndexTag;
/// bar(fInterface.GetParameter(IndexTag<1>()));
/// }
/// \endcode
///
/// ///
template<vtkm::IdComponent ParameterIndex, typename NewType> template<vtkm::IdComponent ParameterIndex, typename NewType>
VTKM_EXEC_CONT_EXPORT VTKM_EXEC_CONT_EXPORT
typename ReplaceType<ParameterIndex, NewType>::type typename ReplaceType<ParameterIndex, NewType>::type
Replace(NewType newParameter) const { Replace(NewType newParameter,
vtkm::internal::IndexTag<ParameterIndex> =
vtkm::internal::IndexTag<ParameterIndex>()) const {
typename ReplaceType<ParameterIndex, NewType>::type replacedFuncInterface; typename ReplaceType<ParameterIndex, NewType>::type replacedFuncInterface;
detail::FunctionInterfaceCopyParameters<ParameterIndex-1>:: detail::FunctionInterfaceCopyParameters<ParameterIndex-1>::
Copy(replacedFuncInterface.Parameters, this->Parameters); Copy(replacedFuncInterface.Parameters, this->Parameters);
@ -491,11 +575,13 @@ public:
/// ///
/// The \c StaticTransform methods transform all the parameters of this \c /// The \c StaticTransform methods transform all the parameters of this \c
/// FunctionInterface to different types and values based on compile-time /// FunctionInterface to different types and values based on compile-time
/// information. It operates by accepting a functor that defines a unary /// information. It operates by accepting a functor that two arguments. The
/// function whose argument is the parameter to transform and the return /// first argument is the parameter to transform and the second argument is
/// value is the transformed value. The functor must also contain a templated /// an \c IndexTag specifying the index of the parameter (which can be
/// struct name ReturnType with an internal type named \c type that defines /// ignored in many cases). The functor's return value is the transformed
/// the return type of the transform for a given input type. /// value. The functor must also contain a templated struct name ReturnType
/// with an internal type named \c type that defines the return type of the
/// transform for a given input type and parameter index.
/// ///
/// The transformation is only applied to the parameters of the function. The /// The transformation is only applied to the parameters of the function. The
/// return argument is unaffected. /// return argument is unaffected.
@ -509,14 +595,14 @@ public:
/// ///
/// \code /// \code
/// struct MyTransformFunctor { /// struct MyTransformFunctor {
/// template<typename T> /// template<typename T, vtkm::IdComponent Index>
/// struct ReturnType { /// struct ReturnType {
/// typedef const T *type; /// typedef const T *type;
/// }; /// };
/// ///
/// template<typename T> /// template<typename T, vtkm::IdComponent Index>
/// VTKM_CONT_EXPORT /// VTKM_CONT_EXPORT
/// const T *operator()(const T &x) const { /// const T *operator()(const T &x, vtkm::internal::IndexTag<Index>) const {
/// return &x; /// return &x;
/// } /// }
/// }; /// };
@ -557,10 +643,11 @@ public:
/// The \c DynamicTransform method transforms all the parameters of this \c /// The \c DynamicTransform method transforms all the parameters of this \c
/// FunctionInterface to different types and values based on run-time /// FunctionInterface to different types and values based on run-time
/// information. It operates by accepting two functors. The first functor /// information. It operates by accepting two functors. The first functor
/// accepts two arguments. The first argument is a parameter to transform and /// accepts three arguments. The first argument is a parameter to transform,
/// the second is a functor to call with the transformed result. /// the second is a functor to call with the transformed result, and the third
/// is an instance of \c IndexTag denoting the index parameter..
/// ///
/// The second argument to \c DynamicTransform is another function that /// The second argument to \c DynamicTransform is another functor that
/// accepts the transformed \c FunctionInterface and does something. If that /// accepts the transformed \c FunctionInterface and does something. If that
/// transformed \c FunctionInterface has a return value, that return value /// transformed \c FunctionInterface has a return value, that return value
/// will be passed back to this \c FunctionInterface. /// will be passed back to this \c FunctionInterface.
@ -568,23 +655,27 @@ public:
/// Here is a contrived but illustrative example. This transformation will /// Here is a contrived but illustrative example. This transformation will
/// pass all arguments except any string that looks like a number will be /// pass all arguments except any string that looks like a number will be
/// converted to a vtkm::FloatDefault. Note that because the types are not /// converted to a vtkm::FloatDefault. Note that because the types are not
/// determined till runtime, this transform cannot be determined at compile /// determined until runtime, this transform cannot be determined at compile
/// time with meta-template programming. /// time with meta-template programming.
/// ///
/// \code /// \code
/// struct MyTransformFunctor { /// struct MyTransformFunctor {
/// template<typename InputType, typename ContinueFunctor> /// template<typename InputType,
/// typename ContinueFunctor,
/// vtkm::IdComponent Index>
/// VTKM_CONT_EXPORT /// VTKM_CONT_EXPORT
/// void operator()(const InputType &input, /// void operator()(const InputType &input,
/// const ContinueFunctor &continueFunc) const /// const ContinueFunctor &continueFunc,
/// vtkm::internal::IndexTag<Index>) const
/// { /// {
/// continueFunc(input); /// continueFunc(input);
/// } /// }
/// ///
/// template<typename ContinueFunctor> /// template<typename ContinueFunctor, vtkm::IdComponent Index>
/// VTKM_CONT_EXPORT /// VTKM_CONT_EXPORT
/// void operator()(const std::string &input, /// void operator()(const std::string &input,
/// const ContinueFunctor &continueFunc) const /// const ContinueFunctor &continueFunc,
/// vtkm::internal::IndexTag<Index>) const
/// { /// {
/// if ((input[0] >= '0' && (input[0] <= '9')) /// if ((input[0] >= '0' && (input[0] <= '9'))
/// { /// {
@ -642,9 +733,11 @@ public:
/// \brief Applies a function to all the parameters. /// \brief Applies a function to all the parameters.
/// ///
/// The \c ForEach methods take a function and apply that function to each /// The \c ForEach methods take a functor and apply that functor to each of
/// of the parameters in the \c FunctionInterface. (Return values are not /// the parameters in the \c FunctionInterface. (Return values are not
/// effected.) /// effected.) The first argument of the functor is the parameter value and
/// the second argument is an \c IndexTag, which can be used to identify the
/// index of the parameter.
/// ///
template<typename Functor> template<typename Functor>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
@ -721,8 +814,12 @@ public:
nextInterface, nextInterface,
this->Transform, this->Transform,
this->Finish); this->Finish);
this->Transform(this->OriginalInterface.template GetParameter<vtkm::internal::FunctionInterface<NextFunction>::ARITY + 1>(), static const vtkm::IdComponent Index =
nextContinue); vtkm::internal::FunctionInterface<NextFunction>::ARITY + 1;
vtkm::internal::IndexTag<Index> indexTag;
this->Transform(this->OriginalInterface.GetParameter(indexTag),
nextContinue,
indexTag);
} }
template<typename NextFunction> template<typename NextFunction>

@ -53,7 +53,7 @@ template<typename Transform,
typename P1> typename P1>
struct FunctionInterfaceStaticTransformType<R(P1), Transform> { struct FunctionInterfaceStaticTransformType<R(P1), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type typename Transform::template ReturnType<P1,1>::type
); );
}; };
@ -63,8 +63,8 @@ template<typename Transform,
typename P2> typename P2>
struct FunctionInterfaceStaticTransformType<R(P1,P2), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type typename Transform::template ReturnType<P2,2>::type
); );
}; };
@ -75,9 +75,9 @@ template<typename Transform,
typename P3> typename P3>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type typename Transform::template ReturnType<P3,3>::type
); );
}; };
@ -89,10 +89,10 @@ template<typename Transform,
typename P4> typename P4>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type typename Transform::template ReturnType<P4,4>::type
); );
}; };
@ -105,11 +105,11 @@ template<typename Transform,
typename P5> typename P5>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type typename Transform::template ReturnType<P5,5>::type
); );
}; };
@ -123,12 +123,12 @@ template<typename Transform,
typename P6> typename P6>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type, typename Transform::template ReturnType<P5,5>::type,
typename Transform::template ReturnType<P6>::type typename Transform::template ReturnType<P6,6>::type
); );
}; };
@ -143,13 +143,13 @@ template<typename Transform,
typename P7> typename P7>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type, typename Transform::template ReturnType<P5,5>::type,
typename Transform::template ReturnType<P6>::type, typename Transform::template ReturnType<P6,6>::type,
typename Transform::template ReturnType<P7>::type typename Transform::template ReturnType<P7,7>::type
); );
}; };
@ -165,14 +165,14 @@ template<typename Transform,
typename P8> typename P8>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type, typename Transform::template ReturnType<P5,5>::type,
typename Transform::template ReturnType<P6>::type, typename Transform::template ReturnType<P6,6>::type,
typename Transform::template ReturnType<P7>::type, typename Transform::template ReturnType<P7,7>::type,
typename Transform::template ReturnType<P8>::type typename Transform::template ReturnType<P8,8>::type
); );
}; };
@ -189,15 +189,15 @@ template<typename Transform,
typename P9> typename P9>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8,P9), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8,P9), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type, typename Transform::template ReturnType<P5,5>::type,
typename Transform::template ReturnType<P6>::type, typename Transform::template ReturnType<P6,6>::type,
typename Transform::template ReturnType<P7>::type, typename Transform::template ReturnType<P7,7>::type,
typename Transform::template ReturnType<P8>::type, typename Transform::template ReturnType<P8,8>::type,
typename Transform::template ReturnType<P9>::type typename Transform::template ReturnType<P9,9>::type
); );
}; };
@ -215,16 +215,16 @@ template<typename Transform,
typename P10> typename P10>
struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8,P9,P10), Transform> { struct FunctionInterfaceStaticTransformType<R(P1,P2,P3,P4,P5,P6,P7,P8,P9,P10), Transform> {
typedef R(type)( typedef R(type)(
typename Transform::template ReturnType<P1>::type, typename Transform::template ReturnType<P1,1>::type,
typename Transform::template ReturnType<P2>::type, typename Transform::template ReturnType<P2,2>::type,
typename Transform::template ReturnType<P3>::type, typename Transform::template ReturnType<P3,3>::type,
typename Transform::template ReturnType<P4>::type, typename Transform::template ReturnType<P4,4>::type,
typename Transform::template ReturnType<P5>::type, typename Transform::template ReturnType<P5,5>::type,
typename Transform::template ReturnType<P6>::type, typename Transform::template ReturnType<P6,6>::type,
typename Transform::template ReturnType<P7>::type, typename Transform::template ReturnType<P7,7>::type,
typename Transform::template ReturnType<P8>::type, typename Transform::template ReturnType<P8,8>::type,
typename Transform::template ReturnType<P9>::type, typename Transform::template ReturnType<P9,9>::type,
typename Transform::template ReturnType<P10>::type typename Transform::template ReturnType<P10,10>::type
); );
}; };

@ -94,7 +94,7 @@ template<typename Transform,
struct FunctionInterfaceStaticTransformType<$signature(num_params), Transform> { struct FunctionInterfaceStaticTransformType<$signature(num_params), Transform> {
typedef $ptype(0)(type)( typedef $ptype(0)(type)(
$for(param_index in xrange(1, num_params+1))\ $for(param_index in xrange(1, num_params+1))\
typename Transform::template ReturnType<$ptype(param_index)>::type$comma_if(param_index<num_params) typename Transform::template ReturnType<$ptype(param_index),$(param_index)>::type$comma_if(param_index<num_params)
$endfor\ $endfor\
); );
}; };

@ -28,6 +28,7 @@
#endif #endif
#include <vtkm/Types.h> #include <vtkm/Types.h>
#include <vtkm/internal/IndexTag.h>
#include <boost/function_types/function_type.hpp> #include <boost/function_types/function_type.hpp>
#include <boost/mpl/at.hpp> #include <boost/mpl/at.hpp>
@ -2478,7 +2479,8 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Transform, template<typename Transform,
@ -2492,7 +2494,8 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Transform, template<typename Transform,
@ -2508,8 +2511,10 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter2 =
transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Transform, template<typename Transform,
@ -2525,8 +2530,10 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter2 =
transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Transform, template<typename Transform,
@ -2544,9 +2551,12 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Transform, template<typename Transform,
@ -2564,9 +2574,12 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Transform, template<typename Transform,
@ -2586,10 +2599,14 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Transform, template<typename Transform,
@ -2609,10 +2626,14 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Transform, template<typename Transform,
@ -2634,11 +2655,16 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Transform, template<typename Transform,
@ -2660,11 +2686,16 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Transform, template<typename Transform,
@ -2688,12 +2719,18 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Transform, template<typename Transform,
@ -2717,12 +2754,18 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Transform, template<typename Transform,
@ -2748,13 +2791,20 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Transform, template<typename Transform,
@ -2780,13 +2830,20 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Transform, template<typename Transform,
@ -2814,14 +2871,22 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transformedParameters.Parameter8 = transform(originalParameters.Parameter8); transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
transformedParameters.Parameter8 =
transform(originalParameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Transform, template<typename Transform,
@ -2849,14 +2914,22 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transformedParameters.Parameter8 = transform(originalParameters.Parameter8); transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
transformedParameters.Parameter8 =
transform(originalParameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Transform, template<typename Transform,
@ -2886,15 +2959,24 @@ void DoStaticTransformCont(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8,OriginalP9)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8,OriginalP9)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8,TransformedP9)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8,TransformedP9)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transformedParameters.Parameter8 = transform(originalParameters.Parameter8); transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter9 = transform(originalParameters.Parameter9); transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
transformedParameters.Parameter8 =
transform(originalParameters.Parameter8, vtkm::internal::IndexTag<8>());
transformedParameters.Parameter9 =
transform(originalParameters.Parameter9, vtkm::internal::IndexTag<9>());
} }
template<typename Transform, template<typename Transform,
@ -2924,15 +3006,24 @@ void DoStaticTransformExec(
const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8,OriginalP9)> &originalParameters, const ParameterContainer<OriginalR(OriginalP1,OriginalP2,OriginalP3,OriginalP4,OriginalP5,OriginalP6,OriginalP7,OriginalP8,OriginalP9)> &originalParameters,
ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8,TransformedP9)> &transformedParameters) ParameterContainer<TransformedR(TransformedP1,TransformedP2,TransformedP3,TransformedP4,TransformedP5,TransformedP6,TransformedP7,TransformedP8,TransformedP9)> &transformedParameters)
{ {
transformedParameters.Parameter1 = transform(originalParameters.Parameter1); transformedParameters.Parameter1 =
transformedParameters.Parameter2 = transform(originalParameters.Parameter2); transform(originalParameters.Parameter1, vtkm::internal::IndexTag<1>());
transformedParameters.Parameter3 = transform(originalParameters.Parameter3); transformedParameters.Parameter2 =
transformedParameters.Parameter4 = transform(originalParameters.Parameter4); transform(originalParameters.Parameter2, vtkm::internal::IndexTag<2>());
transformedParameters.Parameter5 = transform(originalParameters.Parameter5); transformedParameters.Parameter3 =
transformedParameters.Parameter6 = transform(originalParameters.Parameter6); transform(originalParameters.Parameter3, vtkm::internal::IndexTag<3>());
transformedParameters.Parameter7 = transform(originalParameters.Parameter7); transformedParameters.Parameter4 =
transformedParameters.Parameter8 = transform(originalParameters.Parameter8); transform(originalParameters.Parameter4, vtkm::internal::IndexTag<4>());
transformedParameters.Parameter9 = transform(originalParameters.Parameter9); transformedParameters.Parameter5 =
transform(originalParameters.Parameter5, vtkm::internal::IndexTag<5>());
transformedParameters.Parameter6 =
transform(originalParameters.Parameter6, vtkm::internal::IndexTag<6>());
transformedParameters.Parameter7 =
transform(originalParameters.Parameter7, vtkm::internal::IndexTag<7>());
transformedParameters.Parameter8 =
transform(originalParameters.Parameter8, vtkm::internal::IndexTag<8>());
transformedParameters.Parameter9 =
transform(originalParameters.Parameter9, vtkm::internal::IndexTag<9>());
} }
@ -2990,7 +3081,7 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1)> &parameters) const ParameterContainer<R(P1)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Functor, template<typename Functor,
@ -3001,7 +3092,7 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1)> &parameters) ParameterContainer<R(P1)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Functor, template<typename Functor,
@ -3012,7 +3103,7 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1)> &parameters) const ParameterContainer<R(P1)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Functor, template<typename Functor,
@ -3023,7 +3114,7 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1)> &parameters) ParameterContainer<R(P1)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
} }
template<typename Functor, template<typename Functor,
@ -3035,8 +3126,8 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2)> &parameters) const ParameterContainer<R(P1,P2)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Functor, template<typename Functor,
@ -3048,8 +3139,8 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2)> &parameters) ParameterContainer<R(P1,P2)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Functor, template<typename Functor,
@ -3061,8 +3152,8 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2)> &parameters) const ParameterContainer<R(P1,P2)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Functor, template<typename Functor,
@ -3074,8 +3165,8 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2)> &parameters) ParameterContainer<R(P1,P2)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
} }
template<typename Functor, template<typename Functor,
@ -3088,9 +3179,9 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3)> &parameters) const ParameterContainer<R(P1,P2,P3)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Functor, template<typename Functor,
@ -3103,9 +3194,9 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3)> &parameters) ParameterContainer<R(P1,P2,P3)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Functor, template<typename Functor,
@ -3118,9 +3209,9 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3)> &parameters) const ParameterContainer<R(P1,P2,P3)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Functor, template<typename Functor,
@ -3133,9 +3224,9 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3)> &parameters) ParameterContainer<R(P1,P2,P3)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
} }
template<typename Functor, template<typename Functor,
@ -3149,10 +3240,10 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4)> &parameters) const ParameterContainer<R(P1,P2,P3,P4)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Functor, template<typename Functor,
@ -3166,10 +3257,10 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4)> &parameters) ParameterContainer<R(P1,P2,P3,P4)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Functor, template<typename Functor,
@ -3183,10 +3274,10 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4)> &parameters) const ParameterContainer<R(P1,P2,P3,P4)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Functor, template<typename Functor,
@ -3200,10 +3291,10 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4)> &parameters) ParameterContainer<R(P1,P2,P3,P4)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
} }
template<typename Functor, template<typename Functor,
@ -3218,11 +3309,11 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Functor, template<typename Functor,
@ -3237,11 +3328,11 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Functor, template<typename Functor,
@ -3256,11 +3347,11 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Functor, template<typename Functor,
@ -3275,11 +3366,11 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
} }
template<typename Functor, template<typename Functor,
@ -3295,12 +3386,12 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Functor, template<typename Functor,
@ -3316,12 +3407,12 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Functor, template<typename Functor,
@ -3337,12 +3428,12 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Functor, template<typename Functor,
@ -3358,12 +3449,12 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
} }
template<typename Functor, template<typename Functor,
@ -3380,13 +3471,13 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Functor, template<typename Functor,
@ -3403,13 +3494,13 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Functor, template<typename Functor,
@ -3426,13 +3517,13 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Functor, template<typename Functor,
@ -3449,13 +3540,13 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
} }
template<typename Functor, template<typename Functor,
@ -3473,14 +3564,14 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Functor, template<typename Functor,
@ -3498,14 +3589,14 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Functor, template<typename Functor,
@ -3523,14 +3614,14 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Functor, template<typename Functor,
@ -3548,14 +3639,14 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
} }
template<typename Functor, template<typename Functor,
@ -3574,15 +3665,15 @@ void DoForEachCont(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
f(parameters.Parameter9); f(parameters.Parameter9, vtkm::internal::IndexTag<9>());
} }
template<typename Functor, template<typename Functor,
@ -3601,15 +3692,15 @@ void DoForEachCont(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
f(parameters.Parameter9); f(parameters.Parameter9, vtkm::internal::IndexTag<9>());
} }
template<typename Functor, template<typename Functor,
@ -3628,15 +3719,15 @@ void DoForEachExec(
const Functor &f, const Functor &f,
const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters) const ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
f(parameters.Parameter9); f(parameters.Parameter9, vtkm::internal::IndexTag<9>());
} }
template<typename Functor, template<typename Functor,
@ -3655,15 +3746,15 @@ void DoForEachExec(
const Functor &f, const Functor &f,
ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters) ParameterContainer<R(P1,P2,P3,P4,P5,P6,P7,P8,P9)> &parameters)
{ {
f(parameters.Parameter1); f(parameters.Parameter1, vtkm::internal::IndexTag<1>());
f(parameters.Parameter2); f(parameters.Parameter2, vtkm::internal::IndexTag<2>());
f(parameters.Parameter3); f(parameters.Parameter3, vtkm::internal::IndexTag<3>());
f(parameters.Parameter4); f(parameters.Parameter4, vtkm::internal::IndexTag<4>());
f(parameters.Parameter5); f(parameters.Parameter5, vtkm::internal::IndexTag<5>());
f(parameters.Parameter6); f(parameters.Parameter6, vtkm::internal::IndexTag<6>());
f(parameters.Parameter7); f(parameters.Parameter7, vtkm::internal::IndexTag<7>());
f(parameters.Parameter8); f(parameters.Parameter8, vtkm::internal::IndexTag<8>());
f(parameters.Parameter9); f(parameters.Parameter9, vtkm::internal::IndexTag<9>());
} }

@ -40,6 +40,7 @@ $# Ignore the following comment. It is meant for the generated file.
#endif #endif
#include <vtkm/Types.h> #include <vtkm/Types.h>
#include <vtkm/internal/IndexTag.h>
#include <boost/function_types/function_type.hpp> #include <boost/function_types/function_type.hpp>
#include <boost/mpl/at.hpp> #include <boost/mpl/at.hpp>
@ -228,7 +229,8 @@ $if(num_params < 1)\
(void)transformedParameters; (void)transformedParameters;
$else\ $else\
$for(param_index in xrange(1, num_params+1))\ $for(param_index in xrange(1, num_params+1))\
transformedParameters.Parameter$(param_index) = transform(originalParameters.Parameter$(param_index)); transformedParameters.Parameter$(param_index) =
transform(originalParameters.Parameter$(param_index), vtkm::internal::IndexTag<$(param_index)>());
$endfor\ $endfor\
$endif\ $endif\
} }
@ -255,7 +257,7 @@ $if(num_params < 1)\
(void)parameters; (void)parameters;
$else\ $else\
$for(param_index in xrange(1, num_params+1))\ $for(param_index in xrange(1, num_params+1))\
f(parameters.Parameter$(param_index)); f(parameters.Parameter$(param_index), vtkm::internal::IndexTag<$(param_index)>());
$endfor\ $endfor\
$endif\ $endif\
} }

46
vtkm/internal/IndexTag.h Normal file

@ -0,0 +1,46 @@
//============================================================================
// Copyright (c) Kitware, Inc.
// All rights reserved.
// See LICENSE.txt for details.
// This software is distributed WITHOUT ANY WARRANTY; without even
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
// PURPOSE. See the above copyright notice for more information.
//
// Copyright 2014 Sandia Corporation.
// Copyright 2014 UT-Battelle, LLC.
// Copyright 2014. Los Alamos National Security
//
// Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
// the U.S. Government retains certain rights in this software.
//
// Under the terms of Contract DE-AC52-06NA25396 with Los Alamos National
// Laboratory (LANL), the U.S. Government retains certain rights in
// this software.
//============================================================================
#ifndef vtk_m_internal_StaticIndex_h
#define vtk_m_internal_StaticIndex_h
#include <vtkm/Types.h>
namespace vtkm {
namespace internal {
/// \brief A convenience tag to represent static indices.
///
/// Some classes like \c FunctionInterface have a list of items that have
/// numeric indices that must be resolved at compile time. Typically these are
/// referenced with an integer template argument. However, such template
/// arguments have to be explicitly defined in the template. They cannot be
/// resolved through function or method arguments. In such cases, it is
/// convenient to use this tag to encapsulate the index.
///
template<vtkm::IdComponent Index>
struct IndexTag
{
static const vtkm::IdComponent INDEX = Index;
};
}
} // namespace vtkm::internal
#endif //vtk_m_internal_StaticIndex_h

@ -83,13 +83,13 @@ struct GetReferenceFunctor
}; };
struct PointerTransform { struct PointerTransform {
template<typename T> template<typename T, vtkm::IdComponent Index>
struct ReturnType { struct ReturnType {
typedef const T *type; typedef const T *type;
}; };
template<typename T> template<typename T, typename IndexTag>
const T *operator()(const T &x) const { const T *operator()(const T &x, IndexTag) const {
return &x; return &x;
} }
}; };
@ -216,15 +216,19 @@ struct ThreeArgStringFunctorWithReturn
struct DynamicTransformFunctor struct DynamicTransformFunctor
{ {
template<typename T, typename ContinueFunctor> template<typename T, typename ContinueFunctor, vtkm::IdComponent Index>
void operator()(const T &input, const ContinueFunctor continueFunc) const void operator()(const T &input,
const ContinueFunctor continueFunc,
vtkm::internal::IndexTag<Index>) const
{ {
continueFunc(input); continueFunc(input+T(Index));
continueFunc(ToString(input)); continueFunc(ToString(input+T(Index)));
} }
template<typename ContinueFunctor> template<typename ContinueFunctor, vtkm::IdComponent Index>
void operator()(const std::string &input, const ContinueFunctor continueFunc) const void operator()(const std::string &input,
const ContinueFunctor continueFunc,
vtkm::internal::IndexTag<Index>) const
{ {
continueFunc(input); continueFunc(input);
} }
@ -238,9 +242,9 @@ struct DynamicTransformFinish
void operator()(vtkm::internal::FunctionInterface<Signature> &funcInterface) const void operator()(vtkm::internal::FunctionInterface<Signature> &funcInterface) const
{ {
g_DynamicTransformFinishCalls++; g_DynamicTransformFinishCalls++;
VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<1>()) == ToString(Arg1), VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<1>()) == ToString(Arg1+1),
"Arg 1 incorrect"); "Arg 1 incorrect");
VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<2>()) == ToString(Arg2), VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<2>()) == ToString(Arg2+2),
"Arg 2 incorrect"); "Arg 2 incorrect");
VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<3>()) == ToString(Arg3), VTKM_TEST_ASSERT(ToString(funcInterface.template GetParameter<3>()) == ToString(Arg3),
"Arg 3 incorrect"); "Arg 3 incorrect");
@ -249,10 +253,17 @@ struct DynamicTransformFinish
struct ForEachFunctor struct ForEachFunctor
{ {
template<typename T> template<typename T, vtkm::IdComponent Index>
void operator()(T &x) const { x = T(2)*x; } void operator()(T &x, vtkm::internal::IndexTag<Index>) const {
x = T(Index)+x;
}
void operator()(std::string &x) const { x.append("*2"); } template<vtkm::IdComponent Index>
void operator()(std::string &x, vtkm::internal::IndexTag<Index>) const {
std::stringstream message;
message << x << "+" << Index;
x = message.str();
}
}; };
void TryFunctionInterface5( void TryFunctionInterface5(
@ -273,7 +284,7 @@ void TryFunctionInterface5(
std::cout << "Swizzling parameters with replace." << std::endl; std::cout << "Swizzling parameters with replace." << std::endl;
funcInterface.Replace<1>(Arg5) funcInterface.Replace<1>(Arg5)
.Replace<2>(Arg1) .Replace(Arg1, vtkm::internal::IndexTag<2>())
.Replace<5>(Arg2) .Replace<5>(Arg2)
.InvokeCont(FiveArgSwizzledFunctor()); .InvokeCont(FiveArgSwizzledFunctor());
} }
@ -288,7 +299,7 @@ void TestBasicFunctionInterface()
VTKM_TEST_ASSERT(funcInterface.GetArity() == 3, VTKM_TEST_ASSERT(funcInterface.GetArity() == 3,
"Got wrong number of parameters."); "Got wrong number of parameters.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == Arg1, "Arg 1 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == Arg1, "Arg 1 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() == Arg2, "Arg 2 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter(vtkm::internal::IndexTag<2>()) == Arg2, "Arg 2 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3, "Arg 3 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3, "Arg 3 incorrect.");
std::cout << "Checking invocation." << std::endl; std::cout << "Checking invocation." << std::endl;
@ -297,7 +308,7 @@ void TestBasicFunctionInterface()
std::cout << "Checking invocation with argument modification." << std::endl; std::cout << "Checking invocation with argument modification." << std::endl;
funcInterface.SetParameter<1>(Type1()); funcInterface.SetParameter<1>(Type1());
funcInterface.SetParameter<2>(Type2()); funcInterface.SetParameter(Type2(), vtkm::internal::IndexTag<2>());
funcInterface.SetParameter<3>(Type3()); funcInterface.SetParameter<3>(Type3());
VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() != Arg1, "Arg 1 not cleared."); VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() != Arg1, "Arg 1 not cleared.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() != Arg2, "Arg 2 not cleared."); VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() != Arg2, "Arg 2 not cleared.");
@ -440,18 +451,18 @@ void TestForEach()
VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == Arg5, "Arg 5 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == Arg5, "Arg 5 incorrect.");
funcInterface.ForEachCont(ForEachFunctor()); funcInterface.ForEachCont(ForEachFunctor());
VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == 2*Arg1, "Arg 1 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == Type1(1)+Arg1, "Arg 1 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() == 2*Arg2, "Arg 2 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() == Type2(2)+Arg2, "Arg 2 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3+"*2", "Arg 3 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3+"+3", "Arg 3 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<4>() == 2.0f*Arg4, "Arg 4 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<4>() == Type4(4)+Arg4, "Arg 4 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == 2*Arg5, "Arg 5 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == Type5(5)+Arg5, "Arg 5 incorrect.");
funcInterface.ForEachExec(ForEachFunctor()); funcInterface.ForEachExec(ForEachFunctor());
VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == 4*Arg1, "Arg 1 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<1>() == Type1(2)+Arg1, "Arg 1 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() == 4*Arg2, "Arg 2 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<2>() == Type2(4)+Arg2, "Arg 2 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3+"*2*2", "Arg 3 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<3>() == Arg3+"+3+3", "Arg 3 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<4>() == 4.0f*Arg4, "Arg 4 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<4>() == Type4(8)+Arg4, "Arg 4 incorrect.");
VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == 4*Arg5, "Arg 5 incorrect."); VTKM_TEST_ASSERT(funcInterface.GetParameter<5>() == Type5(10)+Arg5, "Arg 5 incorrect.");
} }
#ifdef TEST_INVOKE_TIME #ifdef TEST_INVOKE_TIME

@ -53,7 +53,7 @@ namespace detail {
// tag. Causes a compile error otherwise. // tag. Causes a compile error otherwise.
struct DispatcherBaseControlSignatureTagCheck struct DispatcherBaseControlSignatureTagCheck
{ {
template<typename ControlSignatureTag> template<typename ControlSignatureTag, vtkm::IdComponent Index>
struct ReturnType { struct ReturnType {
// If you get a compile error here, it means there is something that is // If you get a compile error here, it means there is something that is
// not a valid control signature tag in a worklet's ControlSignature. // not a valid control signature tag in a worklet's ControlSignature.
@ -66,7 +66,7 @@ struct DispatcherBaseControlSignatureTagCheck
// signature tag. Causes a compile error otherwise. // signature tag. Causes a compile error otherwise.
struct DispatcherBaseExecutionSignatureTagCheck struct DispatcherBaseExecutionSignatureTagCheck
{ {
template<typename ExecutionSignatureTag> template<typename ExecutionSignatureTag, vtkm::IdComponent Index>
struct ReturnType { struct ReturnType {
// If you get a compile error here, it means there is something that is not // If you get a compile error here, it means there is something that is not
// a valid execution signature tag in a worklet's ExecutionSignature. // a valid execution signature tag in a worklet's ExecutionSignature.
@ -77,16 +77,16 @@ struct DispatcherBaseExecutionSignatureTagCheck
// Used in the dynamic cast to check to make sure that the type passed into // Used in the dynamic cast to check to make sure that the type passed into
// the Invoke method matches the type accepted by the ControlSignature. // the Invoke method matches the type accepted by the ControlSignature.
template<typename ContinueFunctor, typename TypeCheckTag> template<typename ContinueFunctor,
typename TypeCheckTag,
vtkm::IdComponent Index>
struct DispatcherBaseTypeCheckFunctor struct DispatcherBaseTypeCheckFunctor
{ {
const ContinueFunctor &Continue; const ContinueFunctor &Continue;
vtkm::IdComponent ParameterIndex;
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
DispatcherBaseTypeCheckFunctor(const ContinueFunctor &continueFunc, DispatcherBaseTypeCheckFunctor(const ContinueFunctor &continueFunc)
vtkm::IdComponent parameterIndex) : Continue(continueFunc) { }
: Continue(continueFunc), ParameterIndex(parameterIndex) { }
template<typename T> template<typename T>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
@ -111,7 +111,7 @@ struct DispatcherBaseTypeCheckFunctor
{ {
std::stringstream message; std::stringstream message;
message << "Encountered bad type for parameter " message << "Encountered bad type for parameter "
<< this->ParameterIndex << Index
<< " when calling Invoke on a dispatcher."; << " when calling Invoke on a dispatcher.";
throw vtkm::cont::ErrorControlBadType(message.str()); throw vtkm::cont::ErrorControlBadType(message.str());
} }
@ -120,33 +120,27 @@ struct DispatcherBaseTypeCheckFunctor
// Uses vtkm::cont::internal::DynamicTransform and the DynamicTransformCont // Uses vtkm::cont::internal::DynamicTransform and the DynamicTransformCont
// method of FunctionInterface to convert all DynamicArrayHandles and any // method of FunctionInterface to convert all DynamicArrayHandles and any
// other arguments declaring themselves as dynamic to static versions. // other arguments declaring themselves as dynamic to static versions.
template<typename ControlInterface>
struct DispatcherBaseDynamicTransform struct DispatcherBaseDynamicTransform
{ {
vtkm::cont::internal::DynamicTransform BasicDynamicTransform; template<typename InputType,
vtkm::IdComponent *ParameterCounter; typename ContinueFunctor,
vtkm::IdComponent Index>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
DispatcherBaseDynamicTransform(vtkm::IdComponent *parameterCounter) void operator()(const InputType &input,
: ParameterCounter(parameterCounter) const ContinueFunctor &continueFunc,
vtkm::internal::IndexTag<Index> indexTag) const
{ {
*this->ParameterCounter = 0; typedef typename ControlInterface::template ParameterType<Index>::type
} ControlSignatureTag;
template<typename ControlSignatureTag,
typename InputType,
typename ContinueFunctor>
VTKM_CONT_EXPORT
void operator()(const vtkm::Pair<ControlSignatureTag, InputType> &input,
const ContinueFunctor &continueFunc) const
{
(*this->ParameterCounter)++;
typedef DispatcherBaseTypeCheckFunctor< typedef DispatcherBaseTypeCheckFunctor<
ContinueFunctor, typename ControlSignatureTag::TypeCheckTag> ContinueFunctor, typename ControlSignatureTag::TypeCheckTag, Index>
TypeCheckFunctor; TypeCheckFunctor;
this->BasicDynamicTransform(input.second,
TypeCheckFunctor(continueFunc, vtkm::cont::internal::DynamicTransform basicDynamicTransform;
*this->ParameterCounter));
basicDynamicTransform(input, TypeCheckFunctor(continueFunc), indexTag);
} }
}; };
@ -170,7 +164,7 @@ struct DispatcherBaseDynamicTransformHelper
// A functor used in a StaticCast of a FunctionInterface to transport arguments // A functor used in a StaticCast of a FunctionInterface to transport arguments
// from the control environment to the execution environment. // from the control environment to the execution environment.
template<typename Device> template<typename ControlInterface, typename Device>
struct DispatcherBaseTransportFunctor struct DispatcherBaseTransportFunctor
{ {
vtkm::Id NumInstances; vtkm::Id NumInstances;
@ -178,25 +172,28 @@ struct DispatcherBaseTransportFunctor
DispatcherBaseTransportFunctor(vtkm::Id numInstances) DispatcherBaseTransportFunctor(vtkm::Id numInstances)
: NumInstances(numInstances) { } : NumInstances(numInstances) { }
template<typename T> template<typename ControlParameter, vtkm::IdComponent Index>
struct InvokeTypes { struct InvokeTypes {
typedef typename T::FirstType::TransportTag TransportTag; typedef typename ControlInterface::template ParameterType<Index>::type
typedef typename T::SecondType ControlParameter; ControlSignatureTag;
typedef typename ControlSignatureTag::TransportTag TransportTag;
typedef vtkm::cont::arg::Transport<TransportTag,ControlParameter,Device> typedef vtkm::cont::arg::Transport<TransportTag,ControlParameter,Device>
TransportType; TransportType;
}; };
template<typename T> template<typename ControlParameter, vtkm::IdComponent Index>
struct ReturnType { struct ReturnType {
typedef typename InvokeTypes<T>::TransportType::ExecObjectType type; typedef typename InvokeTypes<ControlParameter, Index>::
TransportType::ExecObjectType type;
}; };
template<typename T> template<typename ControlParameter, vtkm::IdComponent Index>
VTKM_CONT_EXPORT VTKM_CONT_EXPORT
typename ReturnType<T>::type typename ReturnType<ControlParameter, Index>::type
operator()(const T &invokeData) const { operator()(const ControlParameter &invokeData,
typename InvokeTypes<T>::TransportType transport; vtkm::internal::IndexTag<Index>) const {
return transport(invokeData.second, this->NumInstances); typename InvokeTypes<ControlParameter, Index>::TransportType transport;
return transport(invokeData, this->NumInstances);
} }
}; };
@ -251,20 +248,13 @@ private:
// type against the TypeCheckTag in the ControlSignature tags. To do this, // type against the TypeCheckTag in the ControlSignature tags. To do this,
// the check needs access to both the parameter (in the parameters // the check needs access to both the parameter (in the parameters
// argument) and the ControlSignature tags (in the ControlInterface type). // argument) and the ControlSignature tags (in the ControlInterface type).
// To make this possible, we use the zip mechanism of FunctionInterface to // To make this possible, we call DynamicTransform with a functor containing
// combine these two separate function interfaces into a single // the control signature tags. It uses the index provided by the
// FunctionInterface with each parameter being a Pair containing both // dynamic transform mechanism to get the right tag and make sure that
// the ControlSignature tag and the control object itself. // the dynamic type is correct. (This prevents the compiler from expanding
typedef typename vtkm::internal::FunctionInterfaceZipType< // worklets with types that should not be.)
ControlInterface, ParameterInterface>::type ZippedInterface; parameters.DynamicTransformCont(
ZippedInterface zippedInterface = detail::DispatcherBaseDynamicTransform<ControlInterface>(),
vtkm::internal::make_FunctionInterfaceZip(ControlInterface(),
parameters);
vtkm::IdComponent parameterIndexCounter;
zippedInterface.DynamicTransformCont(
detail::DispatcherBaseDynamicTransform(&parameterIndexCounter),
detail::DispatcherBaseDynamicTransformHelper<MyType>(this)); detail::DispatcherBaseDynamicTransformHelper<MyType>(this));
} }
@ -308,38 +298,25 @@ private:
void InvokeTransportParameters(const Invocation &invocation, void InvokeTransportParameters(const Invocation &invocation,
vtkm::Id numInstances) const vtkm::Id numInstances) const
{ {
// The first step in invoking a worklet is transport the arguments to the // The first step in invoking a worklet is to transport the arguments to
// execution environment. The invocation object passed to this function // the execution environment. The invocation object passed to this function
// contains the parameters passed to Invoke in the control environment. We // contains the parameters passed to Invoke in the control environment. We
// will use the template magic in the FunctionInterface class to invoke the // will use the template magic in the FunctionInterface class to invoke the
// appropriate Transport class on each parameter to get a list of execution // appropriate Transport class on each parameter and get a list of
// objects (corresponding to the arguments of the Invoke in the control // execution objects (corresponding to the arguments of the Invoke in the
// environment) in a FunctionInterface. // control environment) in a FunctionInterface. Specifically, we use a
// static transform of the FunctionInterface to call the transport on each
// argument and return the corresponding execution environment object.
typedef typename Invocation::ParameterInterface ParameterInterfaceType;
const ParameterInterfaceType &parameters = invocation.Parameters;
// The Transport relies on both the ControlSignature tag and the control typedef detail::DispatcherBaseTransportFunctor<
// object itself. To make it easier to work with each parameter, use the typename Invocation::ControlInterface, Device> TransportFunctorType;
// zip mechanism of FunctionInterface to combine the separate function typedef typename ParameterInterfaceType::template StaticTransformType<
// interfaces of the ControlSignature and the parameters into one. This TransportFunctorType>::type ExecObjectParameters;
// will make a FunctionInterface with each parameter being a Pair
// containing both the ControlSignature tag and the control object itself.
typedef typename vtkm::internal::FunctionInterfaceZipType<
typename Invocation::ControlInterface,
typename Invocation::ParameterInterface>::type ZippedInterface;
ZippedInterface zippedInterface =
vtkm::internal::make_FunctionInterfaceZip(
typename Invocation::ControlInterface(), invocation.Parameters);
// Use the StaticTransform mechanism to run the
// DispatcherBaseTransportFunctor on each parameter of the zipped
// interface. This functor will in turn run the appropriate Transform on
// the parameter and return the associated execution object. The end result
// of the transform is a FunctionInterface containing execution objects
// corresponding to each Invoke argument.
typedef detail::DispatcherBaseTransportFunctor<Device> TransportFunctor;
typedef typename ZippedInterface::template StaticTransformType<
TransportFunctor>::type ExecObjectParameters;
ExecObjectParameters execObjectParameters = ExecObjectParameters execObjectParameters =
zippedInterface.StaticTransformCont(TransportFunctor(numInstances)); parameters.StaticTransformCont(TransportFunctorType(numInstances));
// Replace the parameters in the invocation with the execution object and // Replace the parameters in the invocation with the execution object and
// pass to next step of Invoke. // pass to next step of Invoke.