Contains definition of the proto::make<> and proto::protect<> transforms. A type annotation in an ObjectTransform which instructs Proto not to look for a nested ::type within T after type substitution. ObjectTransforms are evaluated by proto::make<>, which finds all nested transforms and replaces them with the result of their applications. If any substitutions are performed, the result is first assumed to be a metafunction to be applied; that is, Proto checks to see if the result has a nested ::type typedef. If it does, that becomes the result. The purpose of proto::noinvoke<> is to prevent Proto from looking for a nested ::type typedef in these situations. Example: struct Test : proto::when< _ , proto::noinvoke< // This remove_pointer invocation is bloked by noinvoke boost::remove_pointer< // This add_pointer invocation is *not* blocked by noinvoke boost::add_pointer<_> > >() > {}; void test_noinvoke() { typedef proto::terminal<int>::type Int; BOOST_MPL_ASSERT(( boost::is_same< boost::result_of<Test(Int)>::type , boost::remove_pointer<Int *> > )); Int i = {42}; boost::remove_pointer<Int *> t = Test()(i); } proto::transform< protect<PrimitiveTransform> > A PrimitiveTransform which prevents another PrimitiveTransform from being applied in an ObjectTransform. When building higher order transforms with proto::make<> or proto::lazy<> , you sometimes would like to build types that are parameterized with Proto transforms. In such lambda-style transforms, Proto will unhelpfully find all nested transforms and apply them, even if you don't want them to be applied. Consider the following transform, which will replace the proto::_ in Bar<proto::_>() with proto::terminal<int>::type: template<typename T> struct Bar {}; struct Foo : proto::when<proto::_, Bar<proto::_>() > {}; proto::terminal<int>::type i = {0}; int main() { Foo()(i); std::cout << typeid(Foo()(i)).name() << std::endl; } If you actually wanted to default-construct an object of type Bar<proto::_>, you would have to protect the _ to prevent it from being applied. You can use proto::protect<> as follows: // OK: replace anything with Bar<_>() struct Foo : proto::when<proto::_, Bar<proto::protect<proto::_> >() > {}; PrimitiveTransform proto::transform< make<T> > A PrimitiveTransform that computes a type by evaluating any nested transforms and then constructs an object of that type. The purpose of proto::make<> is to annotate a transform as an ObjectTransform so that proto::when<> knows how to apply it. For the full description of the behavior of the proto::make<> transform, see the documentation for the nested proto::make::impl<> class template. proto::transform_impl< Expr, State, Data > see-below proto::make<T>::impl<Expr, State, Data>::result_type is computed as follows: If T is an ObjectTransform of the form Object(A0,…An) or Object(A0,…An ...), then let O be the return type Object. Otherwise, let O be T. The result_type typedef is then computed as follows: If proto::is_transform<O>::value is true, then let the result type be boost::result_of<proto::when<_, O>(Expr, State, Data)>::type . Note that a substitution took place. If O is a template like proto::noinvoke<S<X0,…Xn> >, then the result type is calculated as follows: For each i in [0,n], let Xi' be boost::result_of<proto::make<Xi>(Expr, State, Data)>::type (which evaluates this procedure recursively). Note that a substitution took place. (In this case, Proto merely assumes that a substitution took place for the sake of compile-time efficiency. There would be no reason to use proto::noinvoke<> otherwise.) The result type is S<X0',…Xn'> . If O is a template like S<X0,…Xn>, then the result type is calculated as follows: For each i in [0,n], let Xi' be boost::result_of<proto::make<Xi>(Expr, State, Data)>::type (which evaluates this procedure recursively). Note whether any substitutions took place during this operation. If any substitutions took place in the above step and S<X0',…Xn'> has a nested type typedef, the result type is S<X0',…Xn'>::type . Otherwise, the result type is S<X0',…Xn'> . Otherwise, the result type is O, and note that no substitution took place. Note that proto::when<> is implemented in terms of proto::call<> and proto::make<>, so the above procedure is evaluated recursively. result_type typename impl::expr_param typename impl::state_param typename impl::data_param proto::make<T>::impl<Expr,State,Data>::operator() behaves as follows: If T is of the form O(A0,…An), then: If proto::is_aggregate<result_type>::value is true, then construct and return an object that as follows: result_type that = { proto::when<_, A0>()(expr, state, data), … proto::when<_, An>()(expr, state, data) }; Otherwise, construct and return an object that as follows: result_type that( proto::when<_, A0>()(expr, state, data), … proto::when<_, An>()(expr, state, data) ); If T is of the form O(A0,…An ...), then let T' be O(A0,…An-1, S), where S is a type sequence computed from the unpacking expression An as described in the reference for proto::pack. Then, return: proto::make<T'>()(expr, state, data) Otherwise, construct and return an object that as follows: result_type that = result_type();