Simplify TGParser::ProcessForEachDefs.

Use static type checking.

llvm-svn: 157430
This commit is contained in:
Jakob Stoklund Olesen 2012-05-24 22:17:33 +00:00
parent 79d3eecbb4
commit 8a120b10bd
2 changed files with 77 additions and 108 deletions

View File

@ -292,37 +292,26 @@ bool TGParser::AddSubMultiClass(MultiClass *CurMC,
/// ProcessForeachDefs - Given a record, apply all of the variable /// ProcessForeachDefs - Given a record, apply all of the variable
/// values in all surrounding foreach loops, creating new records for /// values in all surrounding foreach loops, creating new records for
/// each combination of values. /// each combination of values.
bool TGParser::ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass, bool TGParser::ProcessForeachDefs(Record *CurRec, SMLoc Loc) {
SMLoc Loc) { if (Loops.empty())
return false;
// We want to instantiate a new copy of CurRec for each combination // We want to instantiate a new copy of CurRec for each combination
// of nested loop iterator values. We don't want top instantiate // of nested loop iterator values. We don't want top instantiate
// any copies until we have values for each loop iterator. // any copies until we have values for each loop iterator.
IterSet IterVals; IterSet IterVals;
for (LoopVector::iterator Loop = Loops.begin(), LoopEnd = Loops.end(); return ProcessForeachDefs(CurRec, Loc, IterVals);
Loop != LoopEnd;
++Loop) {
// Process this loop.
if (ProcessForeachDefs(CurRec, CurMultiClass, Loc,
IterVals, *Loop, Loop+1)) {
Error(Loc,
"Could not process loops for def " + CurRec->getNameInitAsString());
return true;
}
}
return false;
} }
/// ProcessForeachDefs - Given a record, a loop and a loop iterator, /// ProcessForeachDefs - Given a record, a loop and a loop iterator,
/// apply each of the variable values in this loop and then process /// apply each of the variable values in this loop and then process
/// subloops. /// subloops.
bool TGParser::ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass, bool TGParser::ProcessForeachDefs(Record *CurRec, SMLoc Loc, IterSet &IterVals){
SMLoc Loc, IterSet &IterVals, // Recursively build a tuple of iterator values.
ForeachLoop &CurLoop, if (IterVals.size() != Loops.size()) {
LoopVector::iterator NextLoop) { assert(IterVals.size() < Loops.size());
Init *IterVar = CurLoop.IterVar; ForeachLoop &CurLoop = Loops[IterVals.size()];
ListInit *List = dynamic_cast<ListInit *>(CurLoop.ListValue); ListInit *List = dynamic_cast<ListInit *>(CurLoop.ListValue);
if (List == 0) { if (List == 0) {
Error(Loc, "Loop list is not a list"); Error(Loc, "Loop list is not a list");
return true; return true;
@ -331,25 +320,23 @@ bool TGParser::ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass,
// Process each value. // Process each value.
for (int64_t i = 0; i < List->getSize(); ++i) { for (int64_t i = 0; i < List->getSize(); ++i) {
Init *ItemVal = List->resolveListElementReference(*CurRec, 0, i); Init *ItemVal = List->resolveListElementReference(*CurRec, 0, i);
IterVals.push_back(IterRecord(IterVar, ItemVal)); IterVals.push_back(IterRecord(CurLoop.IterVar, ItemVal));
if (ProcessForeachDefs(CurRec, Loc, IterVals))
return true;
IterVals.pop_back();
}
return false;
}
if (IterVals.size() == Loops.size()) { // This is the bottom of the recursion. We have all of the iterator values
// Ok, we have all of the iterator values for this point in the // for this point in the iteration space. Instantiate a new record to
// iteration space. Instantiate a new record to reflect this // reflect this combination of values.
// combination of values.
Record *IterRec = new Record(*CurRec); Record *IterRec = new Record(*CurRec);
// Set the iterator values now. // Set the iterator values now.
for (IterSet::iterator i = IterVals.begin(), iend = IterVals.end(); for (unsigned i = 0, e = IterVals.size(); i != e; ++i) {
i != iend; VarInit *IterVar = IterVals[i].IterVar;
++i) { TypedInit *IVal = dynamic_cast<TypedInit *>(IterVals[i].IterValue);
VarInit *IterVar = dynamic_cast<VarInit *>(i->IterVar);
if (IterVar == 0) {
Error(Loc, "foreach iterator is unresolved");
return true;
}
TypedInit *IVal = dynamic_cast<TypedInit *>(i->IterValue);
if (IVal == 0) { if (IVal == 0) {
Error(Loc, "foreach iterator value is untyped"); Error(Loc, "foreach iterator value is untyped");
return true; return true;
@ -377,22 +364,6 @@ bool TGParser::ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass,
Records.addDef(IterRec); Records.addDef(IterRec);
IterRec->resolveReferences(); IterRec->resolveReferences();
}
if (NextLoop != Loops.end()) {
// Process nested loops.
if (ProcessForeachDefs(CurRec, CurMultiClass, Loc, IterVals, *NextLoop,
NextLoop+1)) {
Error(Loc,
"Could not process loops for def " +
CurRec->getNameInitAsString());
return true;
}
}
// We're done with this iterator.
IterVals.pop_back();
}
return false; return false;
} }
@ -1728,7 +1699,7 @@ Init *TGParser::ParseDeclaration(Record *CurRec,
/// ///
/// ForeachDeclaration ::= ID '=' Value /// ForeachDeclaration ::= ID '=' Value
/// ///
Init *TGParser::ParseForeachDeclaration(Init *&ForeachListValue) { VarInit *TGParser::ParseForeachDeclaration(ListInit *&ForeachListValue) {
if (Lex.getCode() != tgtok::Id) { if (Lex.getCode() != tgtok::Id) {
TokError("Expected identifier in foreach declaration"); TokError("Expected identifier in foreach declaration");
return 0; return 0;
@ -1745,15 +1716,15 @@ Init *TGParser::ParseForeachDeclaration(Init *&ForeachListValue) {
Lex.Lex(); // Eat the '=' Lex.Lex(); // Eat the '='
// Expect a list initializer. // Expect a list initializer.
ForeachListValue = ParseValue(0, 0, ParseForeachMode); Init *List = ParseSimpleValue(0, 0, ParseForeachMode);
TypedInit *TypedList = dynamic_cast<TypedInit *>(ForeachListValue); ForeachListValue = dynamic_cast<ListInit*>(List);
if (TypedList == 0) { if (ForeachListValue == 0) {
TokError("Value list is untyped"); TokError("Expected a Value list");
return 0; return 0;
} }
RecTy *ValueType = TypedList->getType(); RecTy *ValueType = ForeachListValue->getType();
ListRecTy *ListType = dynamic_cast<ListRecTy *>(ValueType); ListRecTy *ListType = dynamic_cast<ListRecTy *>(ValueType);
if (ListType == 0) { if (ListType == 0) {
TokError("Value list is not of list type"); TokError("Value list is not of list type");
@ -1978,7 +1949,7 @@ bool TGParser::ParseDef(MultiClass *CurMultiClass) {
} }
} }
if (ProcessForeachDefs(CurRec, CurMultiClass, DefLoc)) { if (ProcessForeachDefs(CurRec, DefLoc)) {
Error(DefLoc, Error(DefLoc,
"Could not process loops for def" + CurRec->getNameInitAsString()); "Could not process loops for def" + CurRec->getNameInitAsString());
return true; return true;
@ -1999,8 +1970,8 @@ bool TGParser::ParseForeach(MultiClass *CurMultiClass) {
// Make a temporary object to record items associated with the for // Make a temporary object to record items associated with the for
// loop. // loop.
Init *ListValue = 0; ListInit *ListValue = 0;
Init *IterName = ParseForeachDeclaration(ListValue); VarInit *IterName = ParseForeachDeclaration(ListValue);
if (IterName == 0) if (IterName == 0)
return TokError("expected declaration in for"); return TokError("expected declaration in for");

View File

@ -45,10 +45,11 @@ namespace llvm {
/// ForeachLoop - Record the iteration state associated with a for loop. /// ForeachLoop - Record the iteration state associated with a for loop.
/// This is used to instantiate items in the loop body. /// This is used to instantiate items in the loop body.
struct ForeachLoop { struct ForeachLoop {
Init *IterVar; VarInit *IterVar;
Init *ListValue; ListInit *ListValue;
ForeachLoop(Init *IVar, Init *LValue) : IterVar(IVar), ListValue(LValue) {} ForeachLoop(VarInit *IVar, ListInit *LValue)
: IterVar(IVar), ListValue(LValue) {}
}; };
class TGParser { class TGParser {
@ -113,20 +114,17 @@ private: // Semantic analysis methods.
// IterRecord: Map an iterator name to a value. // IterRecord: Map an iterator name to a value.
struct IterRecord { struct IterRecord {
Init *IterVar; VarInit *IterVar;
Init *IterValue; Init *IterValue;
IterRecord(Init *Var, Init *Val) : IterVar(Var), IterValue(Val) {} IterRecord(VarInit *Var, Init *Val) : IterVar(Var), IterValue(Val) {}
}; };
// IterSet: The set of all iterator values at some point in the // IterSet: The set of all iterator values at some point in the
// iteration space. // iteration space.
typedef std::vector<IterRecord> IterSet; typedef std::vector<IterRecord> IterSet;
bool ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass, bool ProcessForeachDefs(Record *CurRec, SMLoc Loc);
SMLoc Loc); bool ProcessForeachDefs(Record *CurRec, SMLoc Loc, IterSet &IterVals);
bool ProcessForeachDefs(Record *CurRec, MultiClass *CurMultiClass,
SMLoc Loc, IterSet &IterVals, ForeachLoop &CurLoop,
LoopVector::iterator NextLoop);
private: // Parser methods. private: // Parser methods.
bool ParseObjectList(MultiClass *MC = 0); bool ParseObjectList(MultiClass *MC = 0);
@ -160,7 +158,7 @@ private: // Parser methods.
bool ParseTemplateArgList(Record *CurRec); bool ParseTemplateArgList(Record *CurRec);
Init *ParseDeclaration(Record *CurRec, bool ParsingTemplateArgs); Init *ParseDeclaration(Record *CurRec, bool ParsingTemplateArgs);
Init *ParseForeachDeclaration(Init *&ForeachListValue); VarInit *ParseForeachDeclaration(ListInit *&ForeachListValue);
SubClassReference ParseSubClassReference(Record *CurRec, bool isDefm); SubClassReference ParseSubClassReference(Record *CurRec, bool isDefm);
SubMultiClassReference ParseSubMultiClassReference(MultiClass *CurMC); SubMultiClassReference ParseSubMultiClassReference(MultiClass *CurMC);