Skip to content

Commit

Permalink
Refactor 'expressionSemanticDone' logic into a function
Browse files Browse the repository at this point in the history
  • Loading branch information
Dennis Korpel committed Dec 24, 2024
1 parent 2c5638e commit 5c285c8
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 17 deletions.
7 changes: 6 additions & 1 deletion compiler/src/dmd/expression.d
Original file line number Diff line number Diff line change
Expand Up @@ -293,7 +293,12 @@ enum WANTexpand = 1; // expand const/immutable variables if possible
*/
extern (C++) abstract class Expression : ASTNode
{
Type type; // !=null means that semantic() has been run
/// Usually, this starts out as `null` and gets set to the final expression type by
/// `expressionSemantic`. However, for some expressions (such as `TypeExp`,`RealExp`,
/// `VarExp`), the field can get set to an assigned type before running semantic.
/// See `expressionSemanticDone`
Type type;

Loc loc; // file location
const EXP op; // to minimize use of dynamic_cast
bool parens; // if this is a parenthesized expression
Expand Down
31 changes: 15 additions & 16 deletions compiler/src/dmd/expressionsem.d
Original file line number Diff line number Diff line change
Expand Up @@ -14010,25 +14010,24 @@ Expression binSemanticProp(BinExp e, Scope* sc)
return null;
}

/// Returns: whether expressionSemantic() has been run on expression `e`
private bool expressionSemanticDone(Expression e)
{
// Usually, Expression.type gets set by expressionSemantic and is `null` beforehand
// There are some exceptions however:
return e.type !is null && !(
e.isRealExp() // type sometimes gets set already before semantic
|| e.isTypeExp() // stores its type in the Expression.type field
|| e.isCompoundLiteralExp() // stores its `(type) {}` in type field, gets rewritten to struct literal
|| e.isVarExp() // type sometimes gets set already before semantic
);
}

// entrypoint for semantic ExpressionSemanticVisitor
Expression expressionSemantic(Expression e, Scope* sc)
{
if (e.type)
{
// When the expression has a type, it usually means that semantic
// has already been run yet.
// For these expressions, expressionsemantic is not idempotent yet,
// and the test suite fails without these. TODO: fix the code/tests
// so that it doesn't rely on semantic running multiple times anymore.
if (!e.isRealExp()
&& !e.isCompoundLiteralExp()
&& !e.isTypeExp()
&& !e.isVarExp()
)
{
return e;
}
}
if (e.expressionSemanticDone)
return e;

scope v = new ExpressionSemanticVisitor(sc);
e.accept(v);
Expand Down

0 comments on commit 5c285c8

Please sign in to comment.