Index: src/Parser/ExpressionNode.cc
===================================================================
--- src/Parser/ExpressionNode.cc	(revision a3323db19a224d716f0e5bae4165484cef7febdb)
+++ src/Parser/ExpressionNode.cc	(revision c0bf94ec8b5f4f0f6a4ac9de014bc1d596f29233)
@@ -211,11 +211,11 @@
 	if ( Unsigned && size < 2 ) {						// hh or h, less than int ?
 		// int i = -1uh => 65535 not -1, so cast is necessary for unsigned, which unfortunately eliminates warnings for large values.
-		ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[Unsigned][size] ) );
+		ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[Unsigned][size] ), false );
 	} else if ( lnth != -1 ) {							// explicit length ?
 		if ( lnth == 5 ) {								// int128 ?
 			size = 5;
-			ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[Unsigned][size] ) );
+			ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[Unsigned][size] ), false );
 		} else {
-			ret = new CastExpr( ret, new TypeInstType( Type::Qualifiers(), lnthsInt[Unsigned][lnth], false ) );
+			ret = new CastExpr( ret, new TypeInstType( Type::Qualifiers(), lnthsInt[Unsigned][lnth], false ), false );
 		} // if
 	} // if
@@ -285,5 +285,5 @@
 	Expression * ret = new ConstantExpr( Constant( new BasicType( noQualifiers, kind[complx][size] ), str, v ) );
 	if ( lnth != -1 ) {									// explicit length ?
-		ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[complx][size] ) );
+		ret = new CastExpr( ret, new BasicType( Type::Qualifiers(), kind[complx][size] ), false );
 	} // if
 
@@ -408,7 +408,7 @@
 	if ( dynamic_cast< VoidType * >( targetType ) ) {
 		delete targetType;
-		return new CastExpr( maybeMoveBuild< Expression >(expr_node) );
+		return new CastExpr( maybeMoveBuild< Expression >(expr_node), false );
 	} else {
-		return new CastExpr( maybeMoveBuild< Expression >(expr_node), targetType );
+		return new CastExpr( maybeMoveBuild< Expression >(expr_node), targetType, false );
 	} // if
 } // build_cast
Index: src/ResolvExpr/AlternativeFinder.cc
===================================================================
--- src/ResolvExpr/AlternativeFinder.cc	(revision a3323db19a224d716f0e5bae4165484cef7febdb)
+++ src/ResolvExpr/AlternativeFinder.cc	(revision c0bf94ec8b5f4f0f6a4ac9de014bc1d596f29233)
@@ -1247,5 +1247,5 @@
 	}
 
-	Expression * restructureCast( Expression * argExpr, Type * toType ) {
+	Expression * restructureCast( Expression * argExpr, Type * toType, bool isGenerated ) {
 		if ( argExpr->get_result()->size() > 1 && ! toType->isVoid() && ! dynamic_cast<ReferenceType *>( toType ) ) {
 			// Argument expression is a tuple and the target type is not void and not a reference type.
@@ -1262,5 +1262,5 @@
 				// cast each component
 				TupleIndexExpr * idx = new TupleIndexExpr( argExpr->clone(), i );
-				componentExprs.push_back( restructureCast( idx, toType->getComponent( i ) ) );
+				componentExprs.push_back( restructureCast( idx, toType->getComponent( i ), isGenerated ) );
 			}
 			delete argExpr;
@@ -1270,5 +1270,7 @@
 		} else {
 			// handle normally
-			return new CastExpr( argExpr, toType->clone() );
+			CastExpr * ret = new CastExpr( argExpr, toType->clone() );
+			ret->isGenerated = isGenerated;
+			return ret;
 		}
 	}
@@ -1314,5 +1316,5 @@
 				// count one safe conversion for each value that is thrown away
 				thisCost.incSafe( discardedValues );
-				Alternative newAlt( restructureCast( alt.expr->clone(), toType ), alt.env,
+				Alternative newAlt( restructureCast( alt.expr->clone(), toType, castExpr->isGenerated ), alt.env,
 					alt.cost, thisCost );
 				inferParameters( needAssertions, haveAssertions, newAlt, openVars,
@@ -1730,5 +1732,5 @@
 					// count one safe conversion for each value that is thrown away
 					thisCost.incSafe( discardedValues );
-					Alternative newAlt( new InitExpr( restructureCast( alt.expr->clone(), toType ), initAlt.designation->clone() ), newEnv, alt.cost, thisCost );
+					Alternative newAlt( new InitExpr( restructureCast( alt.expr->clone(), toType, true ), initAlt.designation->clone() ), newEnv, alt.cost, thisCost );
 					inferParameters( needAssertions, haveAssertions, newAlt, openVars, back_inserter( candidates ) );
 				}
Index: src/SynTree/Expression.cc
===================================================================
--- src/SynTree/Expression.cc	(revision a3323db19a224d716f0e5bae4165484cef7febdb)
+++ src/SynTree/Expression.cc	(revision c0bf94ec8b5f4f0f6a4ac9de014bc1d596f29233)
@@ -271,13 +271,13 @@
 }
 
-CastExpr::CastExpr( Expression *arg_, Type *toType ) : Expression(), arg(arg_) {
+CastExpr::CastExpr( Expression *arg, Type *toType, bool isGenerated ) : Expression(), arg(arg), isGenerated( isGenerated ) {
 	set_result(toType);
 }
 
-CastExpr::CastExpr( Expression *arg_ ) : Expression(), arg(arg_) {
+CastExpr::CastExpr( Expression *arg, bool isGenerated ) : Expression(), arg(arg), isGenerated( isGenerated ) {
 	set_result( new VoidType( Type::Qualifiers() ) );
 }
 
-CastExpr::CastExpr( const CastExpr &other ) : Expression( other ), arg( maybeClone( other.arg ) ) {
+CastExpr::CastExpr( const CastExpr &other ) : Expression( other ), arg( maybeClone( other.arg ) ), isGenerated( other.isGenerated ) {
 }
 
Index: src/SynTree/Expression.h
===================================================================
--- src/SynTree/Expression.h	(revision a3323db19a224d716f0e5bae4165484cef7febdb)
+++ src/SynTree/Expression.h	(revision c0bf94ec8b5f4f0f6a4ac9de014bc1d596f29233)
@@ -188,7 +188,8 @@
   public:
 	Expression * arg;
-
-	CastExpr( Expression * arg );
-	CastExpr( Expression * arg, Type * toType );
+	bool isGenerated = true; // whether this cast appeared in the source program
+
+	CastExpr( Expression * arg, bool isGenerated = true );
+	CastExpr( Expression * arg, Type * toType, bool isGenerated = true );
 	CastExpr( const CastExpr & other );
 	virtual ~CastExpr();
