[midend-GVN]修复GVN中部分逻辑问题,LICM有bug待修复
This commit is contained in:
@ -59,6 +59,9 @@ private:
|
||||
// 检查两个load指令之间是否有store指令修改了相同的内存位置
|
||||
bool hasInterveningStore(LoadInst* earlierLoad, LoadInst* laterLoad, Value* ptr);
|
||||
|
||||
// 使受store指令影响的load指令失效
|
||||
void invalidateLoadsAffectedByStore(StoreInst* storeInst);
|
||||
|
||||
// 生成表达式的标准化字符串
|
||||
std::string getCanonicalExpression(Instruction* inst);
|
||||
};
|
||||
|
||||
@ -301,8 +301,14 @@ Value *GVNContext::getValueNumber(LoadInst *inst) {
|
||||
if (ptr == loadPtr && inst->getType() == load->getType()) {
|
||||
// 检查两次load之间是否有store指令修改了内存
|
||||
if (hasInterveningStore(load, inst, ptr)) {
|
||||
if (DEBUG) {
|
||||
std::cout << " Found intervening store, cannot reuse load value" << std::endl;
|
||||
}
|
||||
continue; // 如果有store指令,不能复用之前的load
|
||||
}
|
||||
if (DEBUG) {
|
||||
std::cout << " No intervening store found, can reuse load value" << std::endl;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
}
|
||||
@ -345,6 +351,11 @@ void GVNContext::visitInstruction(Instruction *inst) {
|
||||
return;
|
||||
}
|
||||
|
||||
// 如果是store指令,需要清理hashtable中可能被影响的load指令
|
||||
if (auto storeInst = dynamic_cast<StoreInst*>(inst)) {
|
||||
invalidateLoadsAffectedByStore(storeInst);
|
||||
}
|
||||
|
||||
if (DEBUG) {
|
||||
std::cout << " Visiting instruction: " << inst->getName()
|
||||
<< " (kind: " << static_cast<int>(inst->getKind()) << ")" << std::endl;
|
||||
@ -490,6 +501,36 @@ bool GVNContext::hasInterveningStore(LoadInst* earlierLoad, LoadInst* laterLoad,
|
||||
return false; // 没有找到会修改内存的指令
|
||||
}
|
||||
|
||||
void GVNContext::invalidateLoadsAffectedByStore(StoreInst* storeInst) {
|
||||
auto storePtr = checkHashtable(storeInst->getPointer());
|
||||
|
||||
if (DEBUG) {
|
||||
std::cout << " Invalidating loads affected by store to address" << std::endl;
|
||||
}
|
||||
|
||||
// 查找hashtable中所有可能被这个store影响的load指令
|
||||
std::vector<Value*> toRemove;
|
||||
|
||||
for (auto& [key, value] : hashtable) {
|
||||
if (auto loadInst = dynamic_cast<LoadInst*>(key)) {
|
||||
auto loadPtr = checkHashtable(loadInst->getPointer());
|
||||
|
||||
// 如果load的地址与store的地址相同,则需要从hashtable中移除
|
||||
if (loadPtr == storePtr) {
|
||||
toRemove.push_back(key);
|
||||
if (DEBUG) {
|
||||
std::cout << " Invalidating load from same address: " << loadInst->getName() << std::endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 从hashtable中移除被影响的load指令
|
||||
for (auto key : toRemove) {
|
||||
hashtable.erase(key);
|
||||
}
|
||||
}
|
||||
|
||||
std::string GVNContext::getCanonicalExpression(Instruction *inst) {
|
||||
std::ostringstream oss;
|
||||
|
||||
|
||||
@ -132,7 +132,6 @@ void PassManager::runOptimizationPipeline(Module* moduleIR, IRBuilder* builderIR
|
||||
printPasses();
|
||||
}
|
||||
|
||||
// 添加GVN优化遍
|
||||
this->clearPasses();
|
||||
this->addPass(&GVN::ID);
|
||||
this->run();
|
||||
@ -154,14 +153,14 @@ void PassManager::runOptimizationPipeline(Module* moduleIR, IRBuilder* builderIR
|
||||
this->clearPasses();
|
||||
this->addPass(&LoopNormalizationPass::ID);
|
||||
this->addPass(&InductionVariableElimination::ID);
|
||||
this->addPass(&LICM::ID);
|
||||
// this->addPass(&LICM::ID);
|
||||
this->addPass(&LoopStrengthReduction::ID);
|
||||
this->run();
|
||||
|
||||
if(DEBUG) {
|
||||
std::cout << "=== IR After Loop Normalization, LICM, and Strength Reduction Optimizations ===\n";
|
||||
printPasses();
|
||||
}
|
||||
// if(DEBUG) {
|
||||
// std::cout << "=== IR After Loop Normalization, LICM, and Strength Reduction Optimizations ===\n";
|
||||
// printPasses();
|
||||
// }
|
||||
|
||||
// this->clearPasses();
|
||||
// this->addPass(&Reg2Mem::ID);
|
||||
|
||||
Reference in New Issue
Block a user