Fix crash with const access to zero size array

This commit is contained in:
drmortalwombat 2024-10-05 14:01:58 +02:00
parent dadd8eb41c
commit a15125d6af
2 changed files with 85 additions and 72 deletions

View File

@ -1809,7 +1809,7 @@ static InterOperand OperandConstantFolding(InterOperator oper, InterOperand op1,
return dop; return dop;
} }
static void LoadConstantFold(InterInstruction* ins, InterInstruction* ains, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray&staticProcs) void InterCodeBasicBlock::LoadConstantFold(InterInstruction* ins, InterInstruction* ains, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray&staticProcs)
{ {
const uint8* data; const uint8* data;
@ -1830,6 +1830,8 @@ static void LoadConstantFold(InterInstruction* ins, InterInstruction* ains, cons
} }
if (offset >= 0 && offset * stride * (InterTypeSize[ins->mDst.mType] - 1) < lobj->mSize)
{
data = lobj->mData + offset; data = lobj->mData + offset;
switch (ins->mDst.mType) switch (ins->mDst.mType)
@ -1896,6 +1898,16 @@ static void LoadConstantFold(InterInstruction* ins, InterInstruction* ains, cons
ins->mConst.mFloatConst = cc.f; ins->mConst.mFloatConst = cc.f;
} break; } break;
} }
}
else
{
ins->mConst.mIntConst = 0;
ins->mConst.mFloatConst = 0;
ins->mConst.mMemory = IM_ABSOLUTE;
ins->mConst.mLinkerObject = nullptr;
mProc->mModule->mErrors->Error(ins->mLocation, EWARN_INDEX_OUT_OF_BOUNDS, "Constant index out of bounds");
}
ins->mCode = IC_CONSTANT; ins->mCode = IC_CONSTANT;
ins->mConst.mType = ins->mDst.mType; ins->mConst.mType = ins->mDst.mType;
@ -2590,7 +2602,7 @@ bool InterInstruction::IsEqualSource(const InterInstruction* ins) const
void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrArray& tvalue, const NumberSet& aliasedLocals, const NumberSet& aliasedParams, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray& staticProcs) void ValueSet::UpdateValue(InterCodeBasicBlock * block, InterInstruction * ins, const GrowingInstructionPtrArray& tvalue, const NumberSet& aliasedLocals, const NumberSet& aliasedParams, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray& staticProcs)
{ {
int i, temp; int i, temp;
@ -2673,7 +2685,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
} }
else if (ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONSTANT && tvalue[ins->mSrc[0].mTemp]->mConst.mMemory == IM_GLOBAL && (tvalue[ins->mSrc[0].mTemp]->mConst.mLinkerObject->mFlags & LOBJF_CONST)) else if (ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONSTANT && tvalue[ins->mSrc[0].mTemp]->mConst.mMemory == IM_GLOBAL && (tvalue[ins->mSrc[0].mTemp]->mConst.mLinkerObject->mFlags & LOBJF_CONST))
{ {
LoadConstantFold(ins, tvalue[ins->mSrc[0].mTemp], staticVars, staticProcs); block->LoadConstantFold(ins, tvalue[ins->mSrc[0].mTemp], staticVars, staticProcs);
InsertValue(ins); InsertValue(ins);
} }
else else
@ -2875,7 +2887,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2895,7 +2907,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mNumOperands = 1; ins->mNumOperands = 1;
assert(ins->mSrc[0].mTemp >= 0); assert(ins->mSrc[0].mTemp >= 0);
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2908,7 +2920,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2921,7 +2933,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mType = IT_NONE; ins->mSrc[1].mType = IT_NONE;
ins->mNumOperands = 1; ins->mNumOperands = 1;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2937,7 +2949,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mNumOperands = 1; ins->mNumOperands = 1;
assert(ins->mSrc[0].mTemp >= 0); assert(ins->mSrc[0].mTemp >= 0);
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2951,7 +2963,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2963,7 +2975,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mType = IT_NONE; ins->mSrc[1].mType = IT_NONE;
ins->mNumOperands = 1; ins->mNumOperands = 1;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2974,7 +2986,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 1; ins->mNumOperands = 1;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -2990,7 +3002,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -3001,7 +3013,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mNumOperands = 1; ins->mNumOperands = 1;
assert(ins->mSrc[0].mTemp >= 0); assert(ins->mSrc[0].mTemp >= 0);
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
return; return;
} }
@ -3229,7 +3241,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
break; break;
case IT_POINTER: case IT_POINTER:
@ -3245,7 +3257,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
else if (ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONVERSION_OPERATOR && else if (ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONVERSION_OPERATOR &&
ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONVERSION_OPERATOR && ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONVERSION_OPERATOR &&
@ -3260,7 +3272,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mType = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mType; ins->mSrc[1].mType = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mType;
ins->mSrc[1].mTemp = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mTemp; ins->mSrc[1].mTemp = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mTemp;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
else if (ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONVERSION_OPERATOR && else if (ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONVERSION_OPERATOR &&
ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONSTANT && ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONSTANT &&
@ -3513,7 +3525,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mTemp; ins->mSrc[1].mTemp = tvalue[ins->mSrc[1].mTemp]->mSrc[0].mTemp;
} }
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
else if (ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONVERSION_OPERATOR && else if (ins->mSrc[0].mTemp >= 0 && tvalue[ins->mSrc[0].mTemp] && tvalue[ins->mSrc[0].mTemp]->mCode == IC_CONVERSION_OPERATOR &&
ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONSTANT && ins->mSrc[1].mTemp >= 0 && tvalue[ins->mSrc[1].mTemp] && tvalue[ins->mSrc[1].mTemp]->mCode == IC_CONSTANT &&
@ -3716,7 +3728,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[0].mTemp = tvalue[ins->mSrc[0].mTemp]->mSrc[0].mTemp; ins->mSrc[0].mTemp = tvalue[ins->mSrc[0].mTemp]->mSrc[0].mTemp;
} }
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
else if (ins->mSrc[1].mTemp == ins->mSrc[0].mTemp) else if (ins->mSrc[1].mTemp == ins->mSrc[0].mTemp)
{ {
@ -3744,7 +3756,7 @@ void ValueSet::UpdateValue(InterInstruction * ins, const GrowingInstructionPtrAr
ins->mSrc[1].mTemp = -1; ins->mSrc[1].mTemp = -1;
ins->mNumOperands = 0; ins->mNumOperands = 0;
UpdateValue(ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); UpdateValue(block, ins, tvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
} }
break; break;
} }
@ -11966,7 +11978,7 @@ void InterCodeBasicBlock::PerformValueForwarding(const GrowingInstructionPtrArra
} }
#endif #endif
lvalues.UpdateValue(mInstructions[i], ltvalue, aliasedLocals, aliasedParams, staticVars, staticProcs); lvalues.UpdateValue(this, mInstructions[i], ltvalue, aliasedLocals, aliasedParams, staticVars, staticProcs);
mInstructions[i]->PerformValueForwarding(ltvalue, tvalid); mInstructions[i]->PerformValueForwarding(ltvalue, tvalid);
} }

View File

@ -220,7 +220,7 @@ public:
void RemoveValue(int index); void RemoveValue(int index);
void InsertValue(InterInstruction * ins); void InsertValue(InterInstruction * ins);
void UpdateValue(InterInstruction * ins, const GrowingInstructionPtrArray& tvalue, const NumberSet& aliasedLocals, const NumberSet& aliasedParams, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray& staticProcs); void UpdateValue(InterCodeBasicBlock* block, InterInstruction * ins, const GrowingInstructionPtrArray& tvalue, const NumberSet& aliasedLocals, const NumberSet& aliasedParams, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray& staticProcs);
void Intersect(ValueSet& set); void Intersect(ValueSet& set);
}; };
@ -435,6 +435,7 @@ public:
bool MergeSameConditionTraces(void); bool MergeSameConditionTraces(void);
void LocalToTemp(int vindex, int temp); void LocalToTemp(int vindex, int temp);
void LoadConstantFold(InterInstruction* ins, InterInstruction* ains, const GrowingVariableArray& staticVars, const GrowingInterCodeProcedurePtrArray& staticProcs);
void CollectAllUsedDefinedTemps(NumberSet& defined, NumberSet& used); void CollectAllUsedDefinedTemps(NumberSet& defined, NumberSet& used);