From 1f02c8910a4d9388e69d909b203e537509bed7d2 Mon Sep 17 00:00:00 2001 From: Chris Lattner Date: Thu, 9 May 2002 20:14:10 +0000 Subject: [PATCH] * Clean up how PHI nodes are handled * Correct global variable references * Fix loads & stores with zero indices * Do not emit an else part of a branch if there is no code (no phi node and a fallthrough branch), makes code more readable to get: if (l2_cond240) { goto l13_bb10; } with no else{} branch git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@2583 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/CBackend/CBackend.cpp | 125 ++++++++++++++++++------------- lib/Target/CBackend/Writer.cpp | 125 ++++++++++++++++++------------- 2 files changed, 144 insertions(+), 106 deletions(-) diff --git a/lib/Target/CBackend/CBackend.cpp b/lib/Target/CBackend/CBackend.cpp index 5da8367a11a..77aef4603ac 100644 --- a/lib/Target/CBackend/CBackend.cpp +++ b/lib/Target/CBackend/CBackend.cpp @@ -176,6 +176,8 @@ static string calcTypeNameVar(const Type *Ty, case Type::IntTyID: return "int " + NameSoFar; case Type::ULongTyID: return "unsigned long long " + NameSoFar; case Type::LongTyID: return "signed long long " + NameSoFar; + case Type::FloatTyID: return "float " + NameSoFar; + case Type::DoubleTyID: return "double " + NameSoFar; default : cerr << "Unknown primitive type: " << Ty << "\n"; abort(); @@ -330,7 +332,8 @@ namespace { ostream &Out; void outputLValue(Instruction *); - void printPhiFromNextBlock(TerminatorInst *tI, int indx); + void printBranchToBlock(BasicBlock *CurBlock, BasicBlock *SuccBlock, + unsigned Indent); void printIndexingExpr(MemAccessInst *MAI); public: @@ -361,26 +364,6 @@ void CInstPrintVisitor::outputLValue(Instruction *I) { Out << " " << CW.getValueName(I) << " = "; } -void CInstPrintVisitor::printPhiFromNextBlock(TerminatorInst *tI, int indx) { - BasicBlock *bb = tI->getSuccessor(indx); - BasicBlock::const_iterator insIt = bb->begin(); - while (insIt != bb->end()) { - if (PHINode *pI = dyn_cast(*insIt)) { - //Its a phinode! - //Calculate the incoming index for this - int incindex = pI->getBasicBlockIndex(tI->getParent()); - if (incindex != -1) { - //now we have to do the printing - outputLValue(pI); - CW.writeOperand(pI->getIncomingValue(incindex)); - Out << ";\n"; - } - } - else break; - insIt++; - } -} - // Implement all "other" instructions, except for PHINode void CInstPrintVisitor::visitCastInst(CastInst *I) { outputLValue(I); @@ -418,6 +401,11 @@ void CInstPrintVisitor::visitCallInst(CallInst *I) { // neccesary because we use the instruction classes as opaque types... // void CInstPrintVisitor::visitReturnInst(ReturnInst *I) { + // Don't output a void return if this is the last basic block in the function + if (I->getNumOperands() == 0 && + *(I->getParent()->getParent()->end()-1) == I->getParent()) + return; + Out << " return"; if (I->getNumOperands()) { Out << " "; @@ -434,39 +422,62 @@ static bool BBFollowsBB(BasicBlock *BB1, BasicBlock *BB2) { return *(I+1) == BB2; } +static bool isGotoCodeNeccessary(BasicBlock *From, BasicBlock *To) { + // If PHI nodes need copies, we need the copy code... + if (isa(To->front()) || + !BBFollowsBB(From, To)) // Not directly successor, need goto + return true; + + // Otherwise we don't need the code. + return false; +} + +void CInstPrintVisitor::printBranchToBlock(BasicBlock *CurBB, BasicBlock *Succ, + unsigned Indent) { + for (BasicBlock::iterator I = Succ->begin(); + PHINode *PN = dyn_cast(*I); ++I) { + // now we have to do the printing + Out << string(Indent, ' '); + outputLValue(PN); + CW.writeOperand(PN->getIncomingValue(PN->getBasicBlockIndex(CurBB))); + Out << "; /* for PHI node */\n"; + } + + if (!BBFollowsBB(CurBB, Succ)) { + Out << string(Indent, ' ') << " goto "; + CW.writeOperand(Succ); + Out << ";\n"; + } +} + // Brach instruction printing - Avoid printing out a brach to a basic block that // immediately succeeds the current one. // void CInstPrintVisitor::visitBranchInst(BranchInst *I) { - TerminatorInst *tI = cast(I); if (I->isConditional()) { - Out << " if ("; - CW.writeOperand(I->getCondition()); - Out << ") {\n"; - printPhiFromNextBlock(tI,0); + if (isGotoCodeNeccessary(I->getParent(), I->getSuccessor(0))) { + Out << " if ("; + CW.writeOperand(I->getCondition()); + Out << ") {\n"; + + printBranchToBlock(I->getParent(), I->getSuccessor(0), 2); + + if (isGotoCodeNeccessary(I->getParent(), I->getSuccessor(1))) { + Out << " } else {\n"; + printBranchToBlock(I->getParent(), I->getSuccessor(1), 2); + } + } else { + // First goto not neccesary, assume second one is... + Out << " if (!"; + CW.writeOperand(I->getCondition()); + Out << ") {\n"; - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(0)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(0)); - Out << ";\n"; + printBranchToBlock(I->getParent(), I->getSuccessor(1), 2); } - Out << " } else {\n"; - printPhiFromNextBlock(tI,1); - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(1)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(1)); - Out << ";\n"; - } Out << " }\n"; } else { - printPhiFromNextBlock(tI,0); - - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(0)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(0)); - Out << ";\n"; - } + printBranchToBlock(I->getParent(), I->getSuccessor(0), 0); } Out << "\n"; } @@ -508,16 +519,19 @@ void CInstPrintVisitor::visitAllocaInst(AllocaInst *I) { Out << ");\n"; } -void CInstPrintVisitor::visitFreeInst(FreeInst *I) { - Out << "free("; +void CInstPrintVisitor::visitFreeInst(FreeInst *I) { + Out << " free("; CW.writeOperand(I->getOperand(0)); Out << ");\n"; } void CInstPrintVisitor::printIndexingExpr(MemAccessInst *MAI) { + MemAccessInst::op_iterator I = MAI->idx_begin(), E = MAI->idx_end(); + if (I == E) + Out << "*"; // Implicit zero first argument: '*x' is equivalent to 'x[0]' + CW.writeOperand(MAI->getPointerOperand()); - MemAccessInst::op_iterator I = MAI->idx_begin(), E = MAI->idx_end(); if (I == E) return; // Print out the -> operator if possible... @@ -705,9 +719,12 @@ void CWriter::printSymbolTable(const SymbolTable &ST) { for (; I != End; ++I) { const Value *V = I->second; if (const Type *Ty = dyn_cast(V)) { - Out << "typedef "; string Name = "l_" + I->first; - if (isa(Ty)) Name = "struct " + Name; + if (isa(Ty)) + Name = "struct " + Name; + else + Out << "typedef "; + Out << calcTypeNameVar(Ty, TypeNames, Name, true) << ";\n"; } } @@ -730,7 +747,7 @@ void CWriter::printFunctionSignature(const Function *F) { // Print out the return type and name... printType(F->getReturnType()); - Out << " " << getValueName(F) << "("; + Out << getValueName(F) << "("; if (!F->isExternal()) { if (!F->getArgumentList().empty()) { @@ -830,9 +847,11 @@ void CWriter::writeOperand(const Value *Operand) { if (Operand->hasName()) { Out << getValueName(Operand); } else if (const Constant *CPV = dyn_cast(Operand)) { - if (isa(CPV)) - Out << "NULL"; - else + if (isa(CPV)) { + Out << "(("; + printTypeVar(CPV->getType(), ""); + Out << ")NULL)"; + } else Out << getConstStrValue(CPV); } else { int Slot = Table.getValSlot(Operand); diff --git a/lib/Target/CBackend/Writer.cpp b/lib/Target/CBackend/Writer.cpp index 5da8367a11a..77aef4603ac 100644 --- a/lib/Target/CBackend/Writer.cpp +++ b/lib/Target/CBackend/Writer.cpp @@ -176,6 +176,8 @@ static string calcTypeNameVar(const Type *Ty, case Type::IntTyID: return "int " + NameSoFar; case Type::ULongTyID: return "unsigned long long " + NameSoFar; case Type::LongTyID: return "signed long long " + NameSoFar; + case Type::FloatTyID: return "float " + NameSoFar; + case Type::DoubleTyID: return "double " + NameSoFar; default : cerr << "Unknown primitive type: " << Ty << "\n"; abort(); @@ -330,7 +332,8 @@ namespace { ostream &Out; void outputLValue(Instruction *); - void printPhiFromNextBlock(TerminatorInst *tI, int indx); + void printBranchToBlock(BasicBlock *CurBlock, BasicBlock *SuccBlock, + unsigned Indent); void printIndexingExpr(MemAccessInst *MAI); public: @@ -361,26 +364,6 @@ void CInstPrintVisitor::outputLValue(Instruction *I) { Out << " " << CW.getValueName(I) << " = "; } -void CInstPrintVisitor::printPhiFromNextBlock(TerminatorInst *tI, int indx) { - BasicBlock *bb = tI->getSuccessor(indx); - BasicBlock::const_iterator insIt = bb->begin(); - while (insIt != bb->end()) { - if (PHINode *pI = dyn_cast(*insIt)) { - //Its a phinode! - //Calculate the incoming index for this - int incindex = pI->getBasicBlockIndex(tI->getParent()); - if (incindex != -1) { - //now we have to do the printing - outputLValue(pI); - CW.writeOperand(pI->getIncomingValue(incindex)); - Out << ";\n"; - } - } - else break; - insIt++; - } -} - // Implement all "other" instructions, except for PHINode void CInstPrintVisitor::visitCastInst(CastInst *I) { outputLValue(I); @@ -418,6 +401,11 @@ void CInstPrintVisitor::visitCallInst(CallInst *I) { // neccesary because we use the instruction classes as opaque types... // void CInstPrintVisitor::visitReturnInst(ReturnInst *I) { + // Don't output a void return if this is the last basic block in the function + if (I->getNumOperands() == 0 && + *(I->getParent()->getParent()->end()-1) == I->getParent()) + return; + Out << " return"; if (I->getNumOperands()) { Out << " "; @@ -434,39 +422,62 @@ static bool BBFollowsBB(BasicBlock *BB1, BasicBlock *BB2) { return *(I+1) == BB2; } +static bool isGotoCodeNeccessary(BasicBlock *From, BasicBlock *To) { + // If PHI nodes need copies, we need the copy code... + if (isa(To->front()) || + !BBFollowsBB(From, To)) // Not directly successor, need goto + return true; + + // Otherwise we don't need the code. + return false; +} + +void CInstPrintVisitor::printBranchToBlock(BasicBlock *CurBB, BasicBlock *Succ, + unsigned Indent) { + for (BasicBlock::iterator I = Succ->begin(); + PHINode *PN = dyn_cast(*I); ++I) { + // now we have to do the printing + Out << string(Indent, ' '); + outputLValue(PN); + CW.writeOperand(PN->getIncomingValue(PN->getBasicBlockIndex(CurBB))); + Out << "; /* for PHI node */\n"; + } + + if (!BBFollowsBB(CurBB, Succ)) { + Out << string(Indent, ' ') << " goto "; + CW.writeOperand(Succ); + Out << ";\n"; + } +} + // Brach instruction printing - Avoid printing out a brach to a basic block that // immediately succeeds the current one. // void CInstPrintVisitor::visitBranchInst(BranchInst *I) { - TerminatorInst *tI = cast(I); if (I->isConditional()) { - Out << " if ("; - CW.writeOperand(I->getCondition()); - Out << ") {\n"; - printPhiFromNextBlock(tI,0); + if (isGotoCodeNeccessary(I->getParent(), I->getSuccessor(0))) { + Out << " if ("; + CW.writeOperand(I->getCondition()); + Out << ") {\n"; + + printBranchToBlock(I->getParent(), I->getSuccessor(0), 2); + + if (isGotoCodeNeccessary(I->getParent(), I->getSuccessor(1))) { + Out << " } else {\n"; + printBranchToBlock(I->getParent(), I->getSuccessor(1), 2); + } + } else { + // First goto not neccesary, assume second one is... + Out << " if (!"; + CW.writeOperand(I->getCondition()); + Out << ") {\n"; - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(0)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(0)); - Out << ";\n"; + printBranchToBlock(I->getParent(), I->getSuccessor(1), 2); } - Out << " } else {\n"; - printPhiFromNextBlock(tI,1); - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(1)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(1)); - Out << ";\n"; - } Out << " }\n"; } else { - printPhiFromNextBlock(tI,0); - - if (!BBFollowsBB(I->getParent(), cast(I->getOperand(0)))) { - Out << " goto "; - CW.writeOperand(I->getOperand(0)); - Out << ";\n"; - } + printBranchToBlock(I->getParent(), I->getSuccessor(0), 0); } Out << "\n"; } @@ -508,16 +519,19 @@ void CInstPrintVisitor::visitAllocaInst(AllocaInst *I) { Out << ");\n"; } -void CInstPrintVisitor::visitFreeInst(FreeInst *I) { - Out << "free("; +void CInstPrintVisitor::visitFreeInst(FreeInst *I) { + Out << " free("; CW.writeOperand(I->getOperand(0)); Out << ");\n"; } void CInstPrintVisitor::printIndexingExpr(MemAccessInst *MAI) { + MemAccessInst::op_iterator I = MAI->idx_begin(), E = MAI->idx_end(); + if (I == E) + Out << "*"; // Implicit zero first argument: '*x' is equivalent to 'x[0]' + CW.writeOperand(MAI->getPointerOperand()); - MemAccessInst::op_iterator I = MAI->idx_begin(), E = MAI->idx_end(); if (I == E) return; // Print out the -> operator if possible... @@ -705,9 +719,12 @@ void CWriter::printSymbolTable(const SymbolTable &ST) { for (; I != End; ++I) { const Value *V = I->second; if (const Type *Ty = dyn_cast(V)) { - Out << "typedef "; string Name = "l_" + I->first; - if (isa(Ty)) Name = "struct " + Name; + if (isa(Ty)) + Name = "struct " + Name; + else + Out << "typedef "; + Out << calcTypeNameVar(Ty, TypeNames, Name, true) << ";\n"; } } @@ -730,7 +747,7 @@ void CWriter::printFunctionSignature(const Function *F) { // Print out the return type and name... printType(F->getReturnType()); - Out << " " << getValueName(F) << "("; + Out << getValueName(F) << "("; if (!F->isExternal()) { if (!F->getArgumentList().empty()) { @@ -830,9 +847,11 @@ void CWriter::writeOperand(const Value *Operand) { if (Operand->hasName()) { Out << getValueName(Operand); } else if (const Constant *CPV = dyn_cast(Operand)) { - if (isa(CPV)) - Out << "NULL"; - else + if (isa(CPV)) { + Out << "(("; + printTypeVar(CPV->getType(), ""); + Out << ")NULL)"; + } else Out << getConstStrValue(CPV); } else { int Slot = Table.getValSlot(Operand);