Index: src/SynTree/Expression.cc
===================================================================
--- src/SynTree/Expression.cc	(revision d5631b3ed1950913233bb5192a0e073e7b47bc77)
+++ src/SynTree/Expression.cc	(revision cd6a6ffee16b2e0915b5be3211ed86e60fd011e9)
@@ -72,9 +72,7 @@
 
 	if ( result ) {
-		if (!deterministic_output) {
-			os << std::endl << indent << "with resolved type:" << std::endl;
-			os << (indent+1);
-			result->print( os, indent+1 );
-		}
+		os << std::endl << indent << "with resolved type:" << std::endl;
+		os << (indent+1);
+		result->print( os, indent+1 );
 	}
 
Index: src/SynTree/NamedTypeDecl.cc
===================================================================
--- src/SynTree/NamedTypeDecl.cc	(revision d5631b3ed1950913233bb5192a0e073e7b47bc77)
+++ src/SynTree/NamedTypeDecl.cc	(revision cd6a6ffee16b2e0915b5be3211ed86e60fd011e9)
@@ -22,4 +22,5 @@
 #include "LinkageSpec.h"         // for Spec, Cforall, linkageName
 #include "Type.h"                // for Type, Type::StorageClasses
+#include "CompilationState.h"
 
 NamedTypeDecl::NamedTypeDecl( const std::string &name, Type::StorageClasses scs, Type *base )
@@ -41,5 +42,8 @@
 	using namespace std;
 
-	if ( name != "" ) os << name << ": ";
+	if ( ! name.empty() ) {
+		if( deterministic_output && isUnboundType(name) ) os << "[unbound]:";
+		else os << name << ": ";
+	}
 
 	if ( linkage != LinkageSpec::Cforall ) {
Index: src/SynTree/ReferenceToType.cc
===================================================================
--- src/SynTree/ReferenceToType.cc	(revision d5631b3ed1950913233bb5192a0e073e7b47bc77)
+++ src/SynTree/ReferenceToType.cc	(revision cd6a6ffee16b2e0915b5be3211ed86e60fd011e9)
@@ -24,4 +24,5 @@
 #include "Type.h"             // for TypeInstType, StructInstType, UnionInstType
 #include "TypeSubstitution.h" // for TypeSubstitution
+#include "CompilationState.h"
 
 class Attribute;
@@ -205,5 +206,9 @@
 
 	Type::print( os, indent );
-	os << "instance of " << typeString() << " " << get_name() << " (" << ( isFtype ? "" : "not" ) << " function type)";
+	os << "instance of " << typeString() << " ";
+	const auto & name_ = get_name();
+	if( deterministic_output && isUnboundType(name) ) os << "[unbound]";
+	else os << name;
+	os << " (" << ( isFtype ? "" : "not" ) << " function type)";
 	if ( ! parameters.empty() ) {
 		os << endl << indent << "... with parameters" << endl;
Index: src/SynTree/Type.cc
===================================================================
--- src/SynTree/Type.cc	(revision d5631b3ed1950913233bb5192a0e073e7b47bc77)
+++ src/SynTree/Type.cc	(revision cd6a6ffee16b2e0915b5be3211ed86e60fd011e9)
@@ -156,4 +156,26 @@
 const Type::Qualifiers noQualifiers;
 
+bool isUnboundType(const Type * type) {
+	if (auto typeInst = dynamic_cast<const TypeInstType *>(type)) {
+		// xxx - look for a type name produced by renameTyVars.
+
+		// TODO: once TypeInstType representation is updated, it should properly check
+		// if the context id is filled. this is a temporary hack for now
+		return isUnboundType(typeInst->name);
+	}
+	return false;
+}
+
+bool isUnboundType(const std::string & tname) {
+	// xxx - look for a type name produced by renameTyVars.
+
+	// TODO: once TypeInstType representation is updated, it should properly check
+	// if the context id is filled. this is a temporary hack for now
+	if (std::count(tname.begin(), tname.end(), '_') >= 3) {
+		return true;
+	}
+	return false;
+}
+
 // Local Variables: //
 // tab-width: 4 //
Index: src/SynTree/Type.h
===================================================================
--- src/SynTree/Type.h	(revision d5631b3ed1950913233bb5192a0e073e7b47bc77)
+++ src/SynTree/Type.h	(revision cd6a6ffee16b2e0915b5be3211ed86e60fd011e9)
@@ -733,4 +733,8 @@
 };
 
+
+bool isUnboundType(const Type * type);
+bool isUnboundType(const std::string & tname);
+
 // Local Variables: //
 // tab-width: 4 //
