Index: src/ResolvExpr/TypeEnvironment.cc
===================================================================
--- src/ResolvExpr/TypeEnvironment.cc	(revision 4d2d45f9b4c716c8a4e67b648f440e533b7ee2b2)
+++ src/ResolvExpr/TypeEnvironment.cc	(revision 7a63486c789eef4cd4e6838a7b116bf5ae8d58fc)
@@ -386,5 +386,7 @@
 	}
 
-	bool TypeEnvironment::bindVarToVar( TypeInstType *var1, TypeInstType *var2, const TypeDecl::Data & data, AssertionSet &need, AssertionSet &have, const OpenVarSet &openVars, WidenMode widenMode, const SymTab::Indexer &indexer ) {
+	bool TypeEnvironment::bindVarToVar( TypeInstType *var1, TypeInstType *var2, 
+			TypeDecl::Data && data, AssertionSet &need, AssertionSet &have, 
+			const OpenVarSet &openVars, WidenMode widenMode, const SymTab::Indexer &indexer ) {
 
 		auto class1 = internal_lookup( var1->get_name() );
@@ -428,4 +430,5 @@
 					class1->set_type( common );
 				}
+				class1->data.isComplete = data.isComplete;
 				env.erase( class2 );
 			} else return false;
@@ -435,8 +438,10 @@
 				class1->vars.insert( class2->vars.begin(), class2->vars.end() );
 				class1->allowWidening = widen1;
+				class1->data.isComplete = data.isComplete;
 				env.erase( class2 );
 			} else {
 				class2->vars.insert( class1->vars.begin(), class1->vars.end() );
 				class2->allowWidening = widen2;
+				class2->data.isComplete = data.isComplete;
 				env.erase( class1 );
 			} // if
@@ -445,8 +450,10 @@
 			class1->vars.insert( var2->get_name() );
 			class1->allowWidening = widen1;
+			class1->data.isComplete = data.isComplete;
 		} else if ( class2 != env.end() ) {
 			// var1 unbound, add to class2
 			class2->vars.insert( var1->get_name() );
 			class2->allowWidening = widen2;
+			class2->data.isComplete = data.isComplete;
 		} else {
 			// neither var bound, create new class
Index: src/ResolvExpr/TypeEnvironment.h
===================================================================
--- src/ResolvExpr/TypeEnvironment.h	(revision 4d2d45f9b4c716c8a4e67b648f440e533b7ee2b2)
+++ src/ResolvExpr/TypeEnvironment.h	(revision 7a63486c789eef4cd4e6838a7b116bf5ae8d58fc)
@@ -139,5 +139,5 @@
 		/// Binds the type classes represented by `var1` and `var2` together; will add 
 		/// one or both classes if needed. Returns false on failure.
-		bool bindVarToVar( TypeInstType *var1, TypeInstType *var2, const TypeDecl::Data & data, AssertionSet &need, AssertionSet &have, const OpenVarSet &openVars, WidenMode widenMode, const SymTab::Indexer &indexer );
+		bool bindVarToVar( TypeInstType *var1, TypeInstType *var2, TypeDecl::Data && data, AssertionSet &need, AssertionSet &have, const OpenVarSet &openVars, WidenMode widenMode, const SymTab::Indexer &indexer );
 
 		/// Disallows widening for all bindings in the environment
Index: src/ResolvExpr/Unify.cc
===================================================================
--- src/ResolvExpr/Unify.cc	(revision 4d2d45f9b4c716c8a4e67b648f440e533b7ee2b2)
+++ src/ResolvExpr/Unify.cc	(revision 7a63486c789eef4cd4e6838a7b116bf5ae8d58fc)
@@ -172,6 +172,12 @@
 		bool isopen2 = var2 && ( entry2 != openVars.end() );
 
-		if ( isopen1 && isopen2 && entry1->second == entry2->second ) {
-			result = env.bindVarToVar( var1, var2, entry1->second, needAssertions, haveAssertions, openVars, widenMode, indexer );
+		if ( isopen1 && isopen2 ) {
+			if ( entry1->second.kind != entry2->second.kind ) {
+				result = false;
+			} else {
+				result = env.bindVarToVar( 
+					var1, var2, TypeDecl::Data{ entry1->second, entry2->second }, needAssertions, 
+					haveAssertions, openVars, widenMode, indexer );
+			}
 		} else if ( isopen1 ) {
 			result = env.bindVar( var1, type2, entry1->second, needAssertions, haveAssertions, openVars, widenMode, indexer );
Index: src/SynTree/Declaration.h
===================================================================
--- src/SynTree/Declaration.h	(revision 4d2d45f9b4c716c8a4e67b648f440e533b7ee2b2)
+++ src/SynTree/Declaration.h	(revision 7a63486c789eef4cd4e6838a7b116bf5ae8d58fc)
@@ -211,7 +211,11 @@
 		TypeDecl::Kind kind;
 		bool isComplete;
+		
 		Data() : kind( (TypeDecl::Kind)-1 ), isComplete( false ) {}
 		Data( TypeDecl * typeDecl ) : Data( typeDecl->get_kind(), typeDecl->isComplete() ) {}
 		Data( Kind kind, bool isComplete ) : kind( kind ), isComplete( isComplete ) {}
+		Data( const Data& d1, const Data& d2 ) 
+		: kind( d1.kind ), isComplete ( d1.isComplete || d2.isComplete ) {}
+
 		bool operator==(const Data & other) const { return kind == other.kind && isComplete == other.isComplete; }
 		bool operator!=(const Data & other) const { return !(*this == other);}
