Added global constant propagation
This commit is contained in:
parent
8de4bef436
commit
9647cdb828
|
@ -1118,6 +1118,49 @@ static void PerformTempDefineForwarding(int temp, TempForwardingTable& forwardin
|
|||
}
|
||||
}
|
||||
|
||||
bool InterInstruction::PropagateConstTemps(const GrowingInstructionPtrArray& ctemps)
|
||||
{
|
||||
switch (mCode)
|
||||
{
|
||||
case IC_LOAD:
|
||||
if (mSTemp[0] >= 0 && ctemps[mSTemp[0]])
|
||||
{
|
||||
InterInstruction* ains = ctemps[mSTemp[0]];
|
||||
mSIntConst[0] = ains->mIntValue;
|
||||
mVarIndex = ains->mVarIndex;
|
||||
mMemory = ains->mMemory;
|
||||
mSTemp[0] = -1;
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
case IC_STORE:
|
||||
if (mSTemp[1] >= 0 && ctemps[mSTemp[1]])
|
||||
{
|
||||
InterInstruction* ains = ctemps[mSTemp[1]];
|
||||
mSIntConst[1] = ains->mIntValue;
|
||||
mVarIndex = ains->mVarIndex;
|
||||
mMemory = ains->mMemory;
|
||||
mSTemp[1] = -1;
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
case IC_LOAD_TEMPORARY:
|
||||
if (mSTemp[0] >= 0 && ctemps[mSTemp[0]])
|
||||
{
|
||||
InterInstruction* ains = ctemps[mSTemp[0]];
|
||||
mCode = IC_CONSTANT;
|
||||
mIntValue = ains->mIntValue;
|
||||
mFloatValue = ains->mFloatValue;
|
||||
mVarIndex = ains->mVarIndex;
|
||||
mMemory = ains->mMemory;
|
||||
mSTemp[0] = -1;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void InterInstruction::PerformTempForwarding(TempForwardingTable& forwardingTable)
|
||||
{
|
||||
PerformTempUseForwarding(mSTemp[0], forwardingTable);
|
||||
|
@ -2187,6 +2230,60 @@ void InterCodeBasicBlock::MarkAliasedLocalTemps(const GrowingIntArray& localTabl
|
|||
}
|
||||
}
|
||||
|
||||
void InterCodeBasicBlock::CollectConstTemps(GrowingInstructionPtrArray& ctemps, NumberSet& assignedTemps)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (!mVisited)
|
||||
{
|
||||
mVisited = true;
|
||||
|
||||
for (i = 0; i < mInstructions.Size(); i++)
|
||||
{
|
||||
int ttemp = mInstructions[i].mTTemp;
|
||||
if (ttemp >= 0)
|
||||
{
|
||||
if (assignedTemps[ttemp])
|
||||
ctemps[ttemp] = nullptr;
|
||||
else
|
||||
{
|
||||
assignedTemps += ttemp;
|
||||
if (mInstructions[i].mCode == IC_CONSTANT)
|
||||
ctemps[ttemp] = &(mInstructions[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (mTrueJump) mTrueJump->CollectConstTemps(ctemps, assignedTemps);
|
||||
if (mFalseJump) mFalseJump->CollectConstTemps(ctemps, assignedTemps);
|
||||
}
|
||||
}
|
||||
|
||||
bool InterCodeBasicBlock::PropagateConstTemps(const GrowingInstructionPtrArray& ctemps)
|
||||
{
|
||||
bool changed = false;
|
||||
|
||||
int i;
|
||||
|
||||
if (!mVisited)
|
||||
{
|
||||
mVisited = true;
|
||||
|
||||
for (i = 0; i < mInstructions.Size(); i++)
|
||||
{
|
||||
if (mInstructions[i].PropagateConstTemps(ctemps))
|
||||
changed = true;
|
||||
}
|
||||
|
||||
if (mTrueJump && mTrueJump->PropagateConstTemps(ctemps))
|
||||
changed = true;
|
||||
if (mFalseJump && mFalseJump->PropagateConstTemps(ctemps))
|
||||
changed = true;
|
||||
}
|
||||
|
||||
return changed;
|
||||
}
|
||||
|
||||
void InterCodeBasicBlock::BuildLocalTempSets(int num, int numFixed)
|
||||
{
|
||||
int i;
|
||||
|
@ -3472,6 +3569,8 @@ void InterCodeProcedure::Close(void)
|
|||
ResetVisited();
|
||||
mBlocks[0]->PerformMachineSpecificValueUsageCheck(mValueForwardingTable, tvalidSet);
|
||||
|
||||
GlobalConstantPropagation();
|
||||
|
||||
DisassembleDebug("machine value forwarding");
|
||||
|
||||
//
|
||||
|
@ -3575,7 +3674,9 @@ void InterCodeProcedure::Close(void)
|
|||
|
||||
RenameTemporaries();
|
||||
|
||||
TempForwarding();
|
||||
do {
|
||||
TempForwarding();
|
||||
} while (GlobalConstantPropagation());
|
||||
|
||||
//
|
||||
// Now remove unused instructions
|
||||
|
@ -3635,6 +3736,20 @@ void InterCodeProcedure::MapVariables(void)
|
|||
}
|
||||
}
|
||||
|
||||
bool InterCodeProcedure::GlobalConstantPropagation(void)
|
||||
{
|
||||
|
||||
NumberSet assignedTemps(mTemporaries.Size());
|
||||
GrowingInstructionPtrArray ctemps(nullptr);
|
||||
|
||||
|
||||
ResetVisited();
|
||||
mBlocks[0]->CollectConstTemps(ctemps, assignedTemps);
|
||||
|
||||
ResetVisited();
|
||||
return mBlocks[0]->PropagateConstTemps(ctemps);
|
||||
}
|
||||
|
||||
void InterCodeProcedure::ReduceTemporaries(void)
|
||||
{
|
||||
NumberSet* collisionSet;
|
||||
|
|
|
@ -293,6 +293,7 @@ public:
|
|||
void GlobalRenameRegister(const GrowingIntArray& renameTable, GrowingTypeArray& temporaries);
|
||||
|
||||
void PerformTempForwarding(TempForwardingTable& forwardingTable);
|
||||
bool PropagateConstTemps(const GrowingInstructionPtrArray& ctemps);
|
||||
|
||||
void BuildCollisionTable(NumberSet& liveTemps, NumberSet* collisionSets);
|
||||
void ReduceTemporaries(const GrowingIntArray& renameTable, GrowingTypeArray& temporaries);
|
||||
|
@ -385,6 +386,9 @@ public:
|
|||
void CollectLocalAddressTemps(GrowingIntArray& localTable, GrowingIntArray& paramTable);
|
||||
void MarkAliasedLocalTemps(const GrowingIntArray& localTable, NumberSet& aliasedLocals, const GrowingIntArray& paramTable, NumberSet& aliasedParams);
|
||||
|
||||
void CollectConstTemps(GrowingInstructionPtrArray& ctemps, NumberSet& assignedTemps);
|
||||
bool PropagateConstTemps(const GrowingInstructionPtrArray& ctemps);
|
||||
|
||||
void BuildLocalTempSets(int num, int numFixed);
|
||||
void BuildGlobalProvidedTempSet(NumberSet fromProvidedTemps);
|
||||
bool BuildGlobalRequiredTempSet(NumberSet& fromRequiredTemps);
|
||||
|
@ -478,6 +482,7 @@ protected:
|
|||
void RenameTemporaries(void);
|
||||
void TempForwarding(void);
|
||||
void RemoveUnusedInstructions(void);
|
||||
bool GlobalConstantPropagation(void);
|
||||
|
||||
void DisassembleDebug(const char* name);
|
||||
};
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
#pragma once
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
typedef unsigned __int32 uint32;
|
||||
|
||||
class NumberSet
|
||||
|
@ -35,6 +37,7 @@ public:
|
|||
|
||||
__forceinline NumberSet& NumberSet::operator+=(int elem)
|
||||
{
|
||||
assert(elem >= 0 && elem < size);
|
||||
bits[elem >> 5] |= (1UL << (elem & 31));
|
||||
|
||||
return *this;
|
||||
|
@ -42,6 +45,7 @@ __forceinline NumberSet& NumberSet::operator+=(int elem)
|
|||
|
||||
__forceinline NumberSet& NumberSet::operator-=(int elem)
|
||||
{
|
||||
assert(elem >= 0 && elem < size);
|
||||
bits[elem >> 5] &= ~(1UL << (elem & 31));
|
||||
|
||||
return *this;
|
||||
|
@ -49,6 +53,7 @@ __forceinline NumberSet& NumberSet::operator-=(int elem)
|
|||
|
||||
__forceinline bool NumberSet::operator[](int elem) const
|
||||
{
|
||||
assert(elem >= 0 && elem < size);
|
||||
return (bits[elem >> 5] & (1UL << (elem & 31))) != 0;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue