Fix continue/break for unrolled loops

This commit is contained in:
drmortalwombat 2025-05-18 14:04:14 +02:00
parent c86dc364b1
commit 6f1da4335b
6 changed files with 67 additions and 6 deletions

View File

@ -274,6 +274,9 @@ void Expression::Dump(int ident) const
case EX_FOR:
printf("FOR");
break;
case EX_FORBODY:
printf("FORBODY");
break;
case EX_DO:
printf("DO");
break;
@ -3106,6 +3109,7 @@ Declaration* TheVoidFunctionTypeDeclaration, * TheConstVoidValueDeclaration;
Declaration* TheCharPointerTypeDeclaration, * TheConstCharPointerTypeDeclaration;
Expression* TheVoidExpression;
Declaration* TheNullptrConstDeclaration, * TheZeroIntegerConstDeclaration, * TheZeroFloatConstDeclaration, * TheNullPointerTypeDeclaration;
Declaration* TheTrueConstDeclaration, * TheFalseConstDeclaration;
void InitDeclarations(void)
{
@ -3207,4 +3211,13 @@ void InitDeclarations(void)
TheZeroFloatConstDeclaration->mBase = TheFloatTypeDeclaration;
TheZeroFloatConstDeclaration->mSize = 4;
TheTrueConstDeclaration = new Declaration(noloc, DT_CONST_INTEGER);
TheTrueConstDeclaration->mBase = TheBoolTypeDeclaration;
TheTrueConstDeclaration->mSize = 1;
TheTrueConstDeclaration->mInteger = 1;
TheFalseConstDeclaration = new Declaration(noloc, DT_CONST_INTEGER);
TheFalseConstDeclaration->mBase = TheBoolTypeDeclaration;
TheFalseConstDeclaration->mSize = 1;
TheFalseConstDeclaration->mInteger = 0;
}

View File

@ -218,6 +218,7 @@ enum ExpressionType
EX_IF,
EX_ELSE,
EX_FOR,
EX_FORBODY,
EX_DO,
EX_SCOPE,
EX_BREAK,
@ -385,5 +386,6 @@ extern Declaration* TheBoolTypeDeclaration, * TheFloatTypeDeclaration, * TheVoid
extern Declaration* TheVoidFunctionTypeDeclaration, * TheConstVoidValueDeclaration;
extern Declaration* TheCharPointerTypeDeclaration, * TheConstCharPointerTypeDeclaration;
extern Declaration* TheNullptrConstDeclaration, * TheZeroIntegerConstDeclaration, * TheZeroFloatConstDeclaration, * TheNullPointerTypeDeclaration;
extern Declaration* TheTrueConstDeclaration, * TheFalseConstDeclaration;
extern Expression* TheVoidExpression;

View File

@ -1141,6 +1141,11 @@ Declaration * GlobalAnalyzer::Analyze(Expression* exp, Declaration* procDec, boo
if (exp->mLeft->mLeft->mRight)
ldec = Analyze(exp->mLeft->mLeft->mRight, procDec, false, false);
break;
case EX_FORBODY:
ldec = Analyze(exp->mLeft, procDec, false, false);
if (exp->mRight)
Analyze(exp->mRight, procDec, false, false);
break;
case EX_DO:
procDec->mComplexity += 20;

View File

@ -974,6 +974,11 @@ Declaration* GlobalOptimizer::Analyze(Expression* exp, Declaration* procDec, uin
if (exp->mLeft->mLeft->mRight)
ldec = Analyze(exp->mLeft->mLeft->mRight, procDec, 0);
break;
case EX_FORBODY:
ldec = Analyze(exp->mLeft, procDec, 0);
if (exp->mRight)
rdec = Analyze(exp->mRight, procDec, 0);
break;
case EX_DO:
ldec = Analyze(exp->mRight, procDec, 0);
rdec = Analyze(exp->mLeft, procDec, ANAFL_RHS);

View File

@ -5455,6 +5455,37 @@ InterCodeGenerator::ExValue InterCodeGenerator::TranslateExpression(Declaration*
return ExValue(TheVoidTypeDeclaration);
}
case EX_FORBODY:
{
DestructStack* odestack = destack;
InterInstruction* jins0 = new InterInstruction(MapLocation(exp, inlineMapper), IC_JUMP);
InterInstruction* jins1 = new InterInstruction(MapLocation(exp, inlineMapper), IC_JUMP);
InterCodeBasicBlock* lblock = new InterCodeBasicBlock(proc);
InterCodeBasicBlock* cblock = new InterCodeBasicBlock(proc);
block->Append(jins0);
block->Close(lblock, nullptr);
DestructStack* idestack = destack;
vr = TranslateExpression(procType, proc, lblock, exp->mLeft, destack, gotos, breakBlock, BranchTarget(cblock, idestack), inlineMapper);
lblock->Append(jins1);
lblock->Close(cblock, nullptr);
UnwindDestructStack(procType, proc, cblock, destack, idestack, inlineMapper);
destack = idestack;
block = cblock;
exp = exp->mRight;
if (!exp)
return ExValue(TheVoidTypeDeclaration);
} break;
case EX_FOR:
{
DestructStack* odestack = destack;

View File

@ -10712,7 +10712,7 @@ Expression* Parser::ParseStatement(void)
}
conditionExp->mRight->mDecValue->mInteger = endValue;
Expression* unrollBody = new Expression(mScanner->mLocation, EX_SEQUENCE);
Expression* unrollBody = new Expression(mScanner->mLocation, EX_FORBODY);
unrollBody->mLeft = bodyExp;
Expression* bexp = unrollBody;
if ((endValue - startValue) * stepValue > 0)
@ -10722,7 +10722,7 @@ Expression* Parser::ParseStatement(void)
bexp->mRight = new Expression(mScanner->mLocation, EX_SEQUENCE);
bexp = bexp->mRight;
bexp->mLeft = iterateExp;
bexp->mRight = new Expression(mScanner->mLocation, EX_SEQUENCE);
bexp->mRight = new Expression(mScanner->mLocation, EX_FORBODY);
bexp = bexp->mRight;
bexp->mLeft = bodyExp;
}
@ -10732,16 +10732,21 @@ Expression* Parser::ParseStatement(void)
if (remain)
{
finalExp = new Expression(mScanner->mLocation, EX_SEQUENCE);
finalExp->mLeft = bodyExp;
Expression* bexp = finalExp;
finalExp = new Expression(mScanner->mLocation, EX_DO);
finalExp->mLeft = new Expression(mScanner->mLocation, EX_CONSTANT);
finalExp->mLeft->mDecType = TheBoolTypeDeclaration;
finalExp->mLeft->mDecValue = TheFalseConstDeclaration;
finalExp->mRight = new Expression(mScanner->mLocation, EX_FORBODY);
finalExp->mRight->mLeft = bodyExp;
Expression* bexp = finalExp->mRight;
for (int i = 1; i < remain; i++)
{
bexp->mRight = new Expression(mScanner->mLocation, EX_SEQUENCE);
bexp = bexp->mRight;
bexp->mLeft = iterateExp;
bexp->mRight = new Expression(mScanner->mLocation, EX_SEQUENCE);
bexp->mRight = new Expression(mScanner->mLocation, EX_FORBODY);
bexp = bexp->mRight;
bexp->mLeft = bodyExp;
}