Index: src/AST/Pass.impl.hpp
===================================================================
--- src/AST/Pass.impl.hpp	(revision ee918356dcc048f90ed4b21640445b45bf2a0d4c)
+++ src/AST/Pass.impl.hpp	(revision c5af4f9989f40ba37062ed52f1c2f7fc73476a2e)
@@ -111,5 +111,4 @@
 		}
 
-
 		//------------------------------
 		/// Check if value was mutated, different for pointers and containers
@@ -125,9 +124,7 @@
 	}
 
-
-	template< typename core_t >
 	template< typename node_t >
 	template< typename object_t, typename super_t, typename field_t >
-	void ast::Pass< core_t >::result1< node_t >::apply(object_t * object, field_t super_t::* field) {
+	void __pass::result1< node_t >::apply( object_t * object, field_t super_t::* field ) {
 		object->*field = value;
 	}
@@ -136,11 +133,5 @@
 	template< typename node_t >
 	auto ast::Pass< core_t >::call_accept( const node_t * node )
-		-> typename std::enable_if<
-				!std::is_base_of<ast::Expr, node_t>::value &&
-				!std::is_base_of<ast::Stmt, node_t>::value
-			, ast::Pass< core_t >::result1<
-				typename std::remove_pointer< decltype( node->accept(*this) ) >::type
-			>
-		>::type
+		-> typename ast::Pass< core_t >::template generic_call_accept_result<node_t>::type
 	{
 		__pedantic_pass_assert( __visit_children() );
@@ -151,5 +142,5 @@
 
 		auto nval = node->accept( *this );
-		ast::Pass< core_t >::result1<
+		__pass::result1<
 			typename std::remove_pointer< decltype( node->accept(*this) ) >::type
 		> res;
@@ -160,5 +151,5 @@
 
 	template< typename core_t >
-	typename ast::Pass< core_t >::template result1<ast::Expr> ast::Pass< core_t >::call_accept( const ast::Expr * expr ) {
+	__pass::template result1<ast::Expr> ast::Pass< core_t >::call_accept( const ast::Expr * expr ) {
 		__pedantic_pass_assert( __visit_children() );
 		__pedantic_pass_assert( expr );
@@ -174,5 +165,5 @@
 
 	template< typename core_t >
-	typename ast::Pass< core_t >::template result1<ast::Stmt> ast::Pass< core_t >::call_accept( const ast::Stmt * stmt ) {
+	__pass::template result1<ast::Stmt> ast::Pass< core_t >::call_accept( const ast::Stmt * stmt ) {
 		__pedantic_pass_assert( __visit_children() );
 		__pedantic_pass_assert( stmt );
@@ -183,5 +174,5 @@
 
 	template< typename core_t >
-	typename ast::Pass< core_t >::template result1<ast::Stmt> ast::Pass< core_t >::call_accept_as_compound( const ast::Stmt * stmt ) {
+	__pass::template result1<ast::Stmt> ast::Pass< core_t >::call_accept_as_compound( const ast::Stmt * stmt ) {
 		__pedantic_pass_assert( __visit_children() );
 		__pedantic_pass_assert( stmt );
@@ -233,8 +224,7 @@
 	}
 
-	template< typename core_t >
 	template< template <class...> class container_t >
 	template< typename object_t, typename super_t, typename field_t >
-	void ast::Pass< core_t >::resultNstmt<container_t>::apply(object_t * object, field_t super_t::* field) {
+	void __pass::resultNstmt<container_t>::apply(object_t * object, field_t super_t::* field) {
 		auto & container = object->*field;
 		__pedantic_pass_assert( container.size() <= values.size() );
@@ -243,20 +233,48 @@
 
 		container_t<ptr<Stmt>> nvals;
-		for(delta & d : values) {
-			if( d.is_old ) {
+		for (delta & d : values) {
+			if ( d.is_old ) {
 				__pedantic_pass_assert( cit.idx <= d.old_idx );
 				std::advance( cit, d.old_idx - cit.idx );
 				nvals.push_back( std::move( (*cit).val) );
 			} else {
-				nvals.push_back( std::move(d.nval) );
+				nvals.push_back( std::move(d.new_val) );
 			}
 		}
 
-		object->*field = std::move(nvals);
+		container = std::move(nvals);
+	}
+
+	template< template <class...> class container_t >
+	template< template <class...> class incontainer_t >
+	void __pass::resultNstmt< container_t >::take_all( incontainer_t<ptr<Stmt>> * stmts ) {
+		if (!stmts || stmts->empty()) return;
+
+		std::transform(stmts->begin(), stmts->end(), std::back_inserter( values ),
+			[](ast::ptr<ast::Stmt>& stmt) -> delta {
+				return delta( stmt.release(), -1, false );
+			});
+		stmts->clear();
+		differs = true;
+	}
+
+	template< template<class...> class container_t >
+	template< template<class...> class incontainer_t >
+	void __pass::resultNstmt< container_t >::take_all( incontainer_t<ptr<Decl>> * decls ) {
+		if (!decls || decls->empty()) return;
+
+		std::transform(decls->begin(), decls->end(), std::back_inserter( values ),
+			[](ast::ptr<ast::Decl>& decl) -> delta {
+				auto loc = decl->location;
+				auto stmt = new DeclStmt( loc, decl.release() );
+				return delta( stmt, -1, false );
+			});
+		decls->clear();
+		differs = true;
 	}
 
 	template< typename core_t >
 	template< template <class...> class container_t >
-	typename ast::Pass< core_t >::template resultNstmt<container_t> ast::Pass< core_t >::call_accept( const container_t< ptr<Stmt> > & statements ) {
+	__pass::template resultNstmt<container_t> ast::Pass< core_t >::call_accept( const container_t< ptr<Stmt> > & statements ) {
 		__pedantic_pass_assert( __visit_children() );
 		if( statements.empty() ) return {};
@@ -285,5 +303,5 @@
 		pass_visitor_stats.avg->push(pass_visitor_stats.depth);
 
-		resultNstmt<container_t> new_kids;
+		__pass::resultNstmt<container_t> new_kids;
 		for( auto value : enumerate( statements ) ) {
 			try {
@@ -327,8 +345,7 @@
 	}
 
-	template< typename core_t >
 	template< template <class...> class container_t, typename node_t >
 	template< typename object_t, typename super_t, typename field_t >
-	void ast::Pass< core_t >::resultN<container_t, node_t>::apply(object_t * object, field_t super_t::* field) {
+	void __pass::resultN<container_t, node_t>::apply(object_t * object, field_t super_t::* field) {
 		auto & container = object->*field;
 		__pedantic_pass_assert( container.size() == values.size() );
@@ -346,5 +363,5 @@
 	template< typename core_t >
 	template< template <class...> class container_t, typename node_t >
-	typename ast::Pass< core_t >::template resultN<container_t, node_t> ast::Pass< core_t >::call_accept( const container_t< ast::ptr<node_t> > & container ) {
+	__pass::template resultN<container_t, node_t> ast::Pass< core_t >::call_accept( const container_t< ast::ptr<node_t> > & container ) {
 		__pedantic_pass_assert( __visit_children() );
 		if( container.empty() ) return {};
@@ -378,5 +395,5 @@
 		if ( ! errors.isEmpty() ) { throw errors; }
 
-		return ast::Pass< core_t >::resultN<container_t, node_t>{ mutated,  new_kids };
+		return ast::__pass::resultN<container_t, node_t>{ mutated, new_kids };
 	}
 
