diff options
Diffstat (limited to 'llvm/lib/CodeGen/MIRParser')
| -rw-r--r-- | llvm/lib/CodeGen/MIRParser/MILexer.cpp | 37 | ||||
| -rw-r--r-- | llvm/lib/CodeGen/MIRParser/MILexer.h | 1 | ||||
| -rw-r--r-- | llvm/lib/CodeGen/MIRParser/MIParser.cpp | 48 |
3 files changed, 63 insertions, 23 deletions
diff --git a/llvm/lib/CodeGen/MIRParser/MILexer.cpp b/llvm/lib/CodeGen/MIRParser/MILexer.cpp index d94d6a5e6be..1f1ce6e8d72 100644 --- a/llvm/lib/CodeGen/MIRParser/MILexer.cpp +++ b/llvm/lib/CodeGen/MIRParser/MILexer.cpp @@ -424,19 +424,6 @@ static bool isValidHexFloatingPointPrefix(char C) { return C == 'H' || C == 'K' || C == 'L' || C == 'M'; } -static Cursor maybeLexHexFloatingPointLiteral(Cursor C, MIToken &Token) { - if (C.peek() != '0' || C.peek(1) != 'x') - return None; - Cursor Range = C; - C.advance(2); // Skip '0x' - if (isValidHexFloatingPointPrefix(C.peek())) - C.advance(); - while (isxdigit(C.peek())) - C.advance(); - Token.reset(MIToken::FloatingPointLiteral, Range.upto(C)); - return C; -} - static Cursor lexFloatingPointLiteral(Cursor Range, Cursor C, MIToken &Token) { C.advance(); // Skip over [0-9]*([eE][-+]?[0-9]+)? @@ -453,6 +440,28 @@ static Cursor lexFloatingPointLiteral(Cursor Range, Cursor C, MIToken &Token) { return C; } +static Cursor maybeLexHexadecimalLiteral(Cursor C, MIToken &Token) { + if (C.peek() != '0' || (C.peek(1) != 'x' && C.peek(1) != 'X')) + return None; + Cursor Range = C; + C.advance(2); + unsigned PrefLen = 2; + if (isValidHexFloatingPointPrefix(C.peek())) { + C.advance(); + PrefLen++; + } + while (isxdigit(C.peek())) + C.advance(); + StringRef StrVal = Range.upto(C); + if (StrVal.size() <= PrefLen) + return None; + if (PrefLen == 2) + Token.reset(MIToken::HexLiteral, Range.upto(C)); + else // It must be 3, which means that there was a floating-point prefix. + Token.reset(MIToken::FloatingPointLiteral, Range.upto(C)); + return C; +} + static Cursor maybeLexNumericalLiteral(Cursor C, MIToken &Token) { if (!isdigit(C.peek()) && (C.peek() != '-' || !isdigit(C.peek(1)))) return None; @@ -609,7 +618,7 @@ StringRef llvm::lexMIToken(StringRef Source, MIToken &Token, return R.remaining(); if (Cursor R = maybeLexExternalSymbol(C, Token, ErrorCallback)) return R.remaining(); - if (Cursor R = maybeLexHexFloatingPointLiteral(C, Token)) + if (Cursor R = maybeLexHexadecimalLiteral(C, Token)) return R.remaining(); if (Cursor R = maybeLexNumericalLiteral(C, Token)) return R.remaining(); diff --git a/llvm/lib/CodeGen/MIRParser/MILexer.h b/llvm/lib/CodeGen/MIRParser/MILexer.h index 6911700b4c8..edba749b5fc 100644 --- a/llvm/lib/CodeGen/MIRParser/MILexer.h +++ b/llvm/lib/CodeGen/MIRParser/MILexer.h @@ -118,6 +118,7 @@ struct MIToken { // Other tokens IntegerLiteral, FloatingPointLiteral, + HexLiteral, VirtualRegister, ConstantPoolItem, JumpTableIndex, diff --git a/llvm/lib/CodeGen/MIRParser/MIParser.cpp b/llvm/lib/CodeGen/MIRParser/MIParser.cpp index 74394d49703..02443ce15cc 100644 --- a/llvm/lib/CodeGen/MIRParser/MIParser.cpp +++ b/llvm/lib/CodeGen/MIRParser/MIParser.cpp @@ -36,6 +36,7 @@ #include "llvm/Target/TargetInstrInfo.h" #include "llvm/Target/TargetIntrinsicInfo.h" #include "llvm/Target/TargetSubtargetInfo.h" +#include <cctype> using namespace llvm; @@ -453,8 +454,19 @@ bool MIParser::parseBasicBlockLiveins(MachineBasicBlock &MBB) { unsigned Reg = 0; if (parseNamedRegister(Reg)) return true; - MBB.addLiveIn(Reg); lex(); + LaneBitmask Mask = ~LaneBitmask(0); + if (consumeIfPresent(MIToken::colon)) { + // Parse lane mask. + if (Token.isNot(MIToken::IntegerLiteral) && + Token.isNot(MIToken::HexLiteral)) + return error("expected a lane mask"); + static_assert(sizeof(LaneBitmask) == sizeof(unsigned), ""); + if (getUnsigned(Mask)) + return error("invalid lane mask value"); + lex(); + } + MBB.addLiveIn(Reg, Mask); } while (consumeIfPresent(MIToken::comma)); return false; } @@ -1107,7 +1119,8 @@ bool MIParser::parseTypedImmediateOperand(MachineOperand &Dest) { bool MIParser::parseFPImmediateOperand(MachineOperand &Dest) { auto Loc = Token.location(); lex(); - if (Token.isNot(MIToken::FloatingPointLiteral)) + if (Token.isNot(MIToken::FloatingPointLiteral) && + Token.isNot(MIToken::HexLiteral)) return error("expected a floating point literal"); const Constant *C = nullptr; if (parseIRConstant(Loc, C)) @@ -1117,13 +1130,30 @@ bool MIParser::parseFPImmediateOperand(MachineOperand &Dest) { } bool MIParser::getUnsigned(unsigned &Result) { - assert(Token.hasIntegerValue() && "Expected a token with an integer value"); - const uint64_t Limit = uint64_t(std::numeric_limits<unsigned>::max()) + 1; - uint64_t Val64 = Token.integerValue().getLimitedValue(Limit); - if (Val64 == Limit) - return error("expected 32-bit integer (too large)"); - Result = Val64; - return false; + if (Token.hasIntegerValue()) { + const uint64_t Limit = uint64_t(std::numeric_limits<unsigned>::max()) + 1; + uint64_t Val64 = Token.integerValue().getLimitedValue(Limit); + if (Val64 == Limit) + return error("expected 32-bit integer (too large)"); + Result = Val64; + return false; + } + if (Token.is(MIToken::HexLiteral)) { + StringRef S = Token.range(); + assert(S[0] == '0' && tolower(S[1]) == 'x'); + // This could be a floating point literal with a special prefix. + if (!isxdigit(S[2])) + return true; + StringRef V = S.substr(2); + unsigned BW = std::min<unsigned>(V.size()*4, 32); + APInt A(BW, V, 16); + APInt Limit = APInt(BW, std::numeric_limits<unsigned>::max()); + if (A.ugt(Limit)) + return error("expected 32-bit integer (too large)"); + Result = A.getZExtValue(); + return false; + } + return true; } bool MIParser::parseMBBReference(MachineBasicBlock *&MBB) { |

