diff --git a/test/TableGen/MultiClassDefName.td b/test/TableGen/MultiClassDefName.td new file mode 100644 index 00000000000..2e71f7d0616 --- /dev/null +++ b/test/TableGen/MultiClassDefName.td @@ -0,0 +1,12 @@ +// RUN: tblgen %s | grep WorldHelloCC | count 1 + +class C { + string name = n; +} + +multiclass Names { + def CC : C; + def World#NAME#CC : C; +} + +defm Hello : Names<"hello", "world">; diff --git a/utils/TableGen/TGLexer.cpp b/utils/TableGen/TGLexer.cpp index f2ea7a15171..8eb219b66b4 100644 --- a/utils/TableGen/TGLexer.cpp +++ b/utils/TableGen/TGLexer.cpp @@ -98,7 +98,7 @@ tgtok::TokKind TGLexer::LexToken() { switch (CurChar) { default: // Handle letters: [a-zA-Z_] - if (isalpha(CurChar) || CurChar == '_') + if (isalpha(CurChar) || CurChar == '_' || CurChar == '#') return LexIdentifier(); // Unknown character, emit an error. @@ -220,8 +220,20 @@ tgtok::TokKind TGLexer::LexIdentifier() { const char *IdentStart = TokStart; // Match the rest of the identifier regex: [0-9a-zA-Z_]* - while (isalpha(*CurPtr) || isdigit(*CurPtr) || *CurPtr == '_') - ++CurPtr; + while (isalpha(*CurPtr) || isdigit(*CurPtr) || *CurPtr == '_' + || *CurPtr == '#') { + // If this contains a '#', make sure it's value + if (*CurPtr == '#') { + if (strncmp(CurPtr, "#NAME#", 6) != 0) { + return tgtok::Error; + } + CurPtr += 6; + } + else { + ++CurPtr; + } + } + // Check to see if this identifier is a keyword. unsigned Len = CurPtr-IdentStart; diff --git a/utils/TableGen/TGParser.cpp b/utils/TableGen/TGParser.cpp index 2e2ec3118b0..ba181533c11 100644 --- a/utils/TableGen/TGParser.cpp +++ b/utils/TableGen/TGParser.cpp @@ -1609,9 +1609,18 @@ bool TGParser::ParseDefm() { for (unsigned i = 0, e = MC->DefPrototypes.size(); i != e; ++i) { Record *DefProto = MC->DefPrototypes[i]; - // Add the suffix to the defm name to get the new name. - Record *CurRec = new Record(DefmPrefix + DefProto->getName(), - DefmPrefixLoc); + // Add in the defm name + std::string DefName = DefProto->getName(); + std::string::size_type idx = DefName.find("#NAME#"); + if (idx != std::string::npos) { + DefName.replace(idx, 6, DefmPrefix); + } + else { + // Add the suffix to the defm name to get the new name. + DefName = DefmPrefix + DefName; + } + + Record *CurRec = new Record(DefName, DefmPrefixLoc); SubClassReference Ref; Ref.RefLoc = DefmPrefixLoc;