Index: src/AST/Decl.hpp
===================================================================
--- src/AST/Decl.hpp	(revision e0115286f6b607d6d384675b446d21bc73745a4b)
+++ src/AST/Decl.hpp	(revision 6d51bd7cd93d2958aac506ca3e6ef1f91b13168b)
@@ -57,7 +57,7 @@
 	static readonly<Decl> fromId( UniqueId id );
 
-	virtual Decl* accept( Visitor& v ) override = 0;
-private:
-	virtual Decl* clone() const override = 0;
+	virtual const Decl * accept( Visitor & v ) const override = 0;
+private:
+	virtual Decl * clone() const override = 0;
 };
 
@@ -85,11 +85,11 @@
 
 	/// Get type of this declaration. May be generated by subclass
-	virtual const Type* get_type() const = 0;
+	virtual const Type * get_type() const = 0;
 	/// Set type of this declaration. May be verified by subclass
 	virtual void set_type(Type*) = 0;
 
-	virtual DeclWithType* accept( Visitor& v ) override = 0;
-private:
-	virtual DeclWithType* clone() const override = 0;
+	virtual const DeclWithType * accept( Visitor & v ) const override = 0;
+private:
+	virtual DeclWithType * clone() const override = 0;
 };
 
@@ -110,7 +110,11 @@
 	void set_type( Type* ty ) override { type = ty; }
 
-	DeclWithType* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	ObjectDecl* clone() const override { return new ObjectDecl{ *this }; }
+	virtual const DeclWithType * accept( Visitor& v ) const override { return v.visit( this ); }
+private:
+	virtual ObjectDecl * clone() const override { return new ObjectDecl{ *this }; }
+
+	/// Must be copied in ALL derived classes
+	template<typename node_t>
+	friend auto mutate(const node_t * node);
 };
 
@@ -166,7 +170,7 @@
 	std::string genTypeString() const;
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	TypeDecl* clone() const override { return new TypeDecl{ *this }; }
+	virtual const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
+private:
+	virtual TypeDecl * clone() const override { return new TypeDecl{ *this }; }
 };
 
@@ -180,7 +184,7 @@
 	std::string typeString() const override { return "typedef"; }
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	TypedefDecl* clone() const override { return new TypedefDecl{ *this }; }
+	virtual const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
+private:
+	virtual TypedefDecl * clone() const override { return new TypedefDecl{ *this }; }
 };
 
@@ -220,7 +224,7 @@
 	bool is_thread() { return kind == DeclarationNode::Thread; }
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	StructDecl* clone() const override { return new StructDecl{ *this }; }
+	virtual const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
+private:
+	virtual StructDecl * clone() const override { return new StructDecl{ *this }; }
 
 	std::string typeString() const override { return "struct"; }
@@ -234,7 +238,7 @@
 	: AggregateDecl( loc, name, std::move(attrs), linkage ) {}
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	UnionDecl* clone() const override { return new UnionDecl{ *this }; }
+	virtual const Decl * accept( Visitor& v ) const override { return v.visit( this ); }
+private:
+	virtual UnionDecl * clone() const override { return new UnionDecl{ *this }; }
 
 	std::string typeString() const override { return "union"; }
@@ -251,7 +255,7 @@
 	bool valueOf( Decl* enumerator, long long& value ) const;
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	EnumDecl* clone() const override { return new EnumDecl{ *this }; }
+	virtual const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
+private:
+	virtual EnumDecl * clone() const override { return new EnumDecl{ *this }; }
 
 	std::string typeString() const override { return "enum"; }
@@ -268,7 +272,7 @@
 	: AggregateDecl( loc, name, std::move(attrs), linkage ) {}
 
-	Decl* accept( Visitor& v ) override { return v.visit( this ); }
-private:
-	TraitDecl* clone() const override { return new TraitDecl{ *this }; }
+	virtual const Decl * accept( Visitor & v ) const override { return v.visit( this ); }
+private:
+	virtual TraitDecl * clone() const override { return new TraitDecl{ *this }; }
 
 	std::string typeString() const override { return "trait"; }
@@ -287,6 +291,6 @@
 inline void increment( const class ObjectDecl * node, Node::ref_type ref ) { node->increment(ref); }
 inline void decrement( const class ObjectDecl * node, Node::ref_type ref ) { node->decrement(ref); }
-inline void increment( const class FunctionDecl * node, Node::ref_type ref ) { node->increment(ref); }
-inline void decrement( const class FunctionDecl * node, Node::ref_type ref ) { node->decrement(ref); }
+// inline void increment( const class FunctionDecl * node, Node::ref_type ref ) { node->increment(ref); }
+// inline void decrement( const class FunctionDecl * node, Node::ref_type ref ) { node->decrement(ref); }
 inline void increment( const class AggregateDecl * node, Node::ref_type ref ) { node->increment(ref); }
 inline void decrement( const class AggregateDecl * node, Node::ref_type ref ) { node->decrement(ref); }
@@ -303,14 +307,14 @@
 inline void increment( const class TypeDecl * node, Node::ref_type ref ) { node->increment(ref); }
 inline void decrement( const class TypeDecl * node, Node::ref_type ref ) { node->decrement(ref); }
-inline void increment( const class FtypeDecl * node, Node::ref_type ref ) { node->increment(ref); }
-inline void decrement( const class FtypeDecl * node, Node::ref_type ref ) { node->decrement(ref); }
-inline void increment( const class DtypeDecl * node, Node::ref_type ref ) { node->increment(ref); }
-inline void decrement( const class DtypeDecl * node, Node::ref_type ref ) { node->decrement(ref); }
+// inline void increment( const class FtypeDecl * node, Node::ref_type ref ) { node->increment(ref); }
+// inline void decrement( const class FtypeDecl * node, Node::ref_type ref ) { node->decrement(ref); }
+// inline void increment( const class DtypeDecl * node, Node::ref_type ref ) { node->increment(ref); }
+// inline void decrement( const class DtypeDecl * node, Node::ref_type ref ) { node->decrement(ref); }
 inline void increment( const class TypedefDecl * node, Node::ref_type ref ) { node->increment(ref); }
 inline void decrement( const class TypedefDecl * node, Node::ref_type ref ) { node->decrement(ref); }
-inline void increment( const class AsmDecl * node, Node::ref_type ref ) { node->increment(ref); }
-inline void decrement( const class AsmDecl * node, Node::ref_type ref ) { node->decrement(ref); }
-inline void increment( const class StaticAssertDecl * node, Node::ref_type ref ) { node->increment(ref); }
-inline void decrement( const class StaticAssertDecl * node, Node::ref_type ref ) { node->decrement(ref); }
+// inline void increment( const class AsmDecl * node, Node::ref_type ref ) { node->increment(ref); }
+// inline void decrement( const class AsmDecl * node, Node::ref_type ref ) { node->decrement(ref); }
+// inline void increment( const class StaticAssertDecl * node, Node::ref_type ref ) { node->increment(ref); }
+// inline void decrement( const class StaticAssertDecl * node, Node::ref_type ref ) { node->decrement(ref); }
 
 }
