MIR Serialization: Serialize the external symbol machine operands.

Reviewers: Duncan P. N. Exon Smith


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@242806 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Alex Lorenz 2015-07-21 16:59:53 +00:00
parent 5769e19790
commit 65671bf628
7 changed files with 128 additions and 1 deletions

View File

@ -475,6 +475,9 @@ public:
extractStoreMemRefs(MachineInstr::mmo_iterator Begin,
MachineInstr::mmo_iterator End);
/// Allocate a string and populate it with the given external symbol name.
const char *createExternalSymbolName(StringRef Name);
//===--------------------------------------------------------------------===//
// Label Manipulation.
//

View File

@ -271,6 +271,36 @@ static Cursor maybeLexGlobalValue(
return C;
}
static Cursor lexName(
Cursor C, MIToken &Token, MIToken::TokenKind Type,
MIToken::TokenKind QuotedType, unsigned PrefixLength,
function_ref<void(StringRef::iterator Loc, const Twine &)> ErrorCallback) {
auto Range = C;
C.advance(PrefixLength);
if (C.peek() == '"') {
if (Cursor R = lexStringConstant(C, ErrorCallback)) {
Token = MIToken(QuotedType, Range.upto(R), PrefixLength);
return R;
}
Token = MIToken(MIToken::Error, Range.remaining());
return Range;
}
while (isIdentifierChar(C.peek()))
C.advance();
Token = MIToken(Type, Range.upto(C), PrefixLength);
return C;
}
static Cursor maybeLexExternalSymbol(
Cursor C, MIToken &Token,
function_ref<void(StringRef::iterator Loc, const Twine &)> ErrorCallback) {
if (C.peek() != '$')
return None;
return lexName(C, Token, MIToken::ExternalSymbol,
MIToken::QuotedExternalSymbol,
/*PrefixLength=*/1, ErrorCallback);
}
static Cursor maybeLexIntegerLiteral(Cursor C, MIToken &Token) {
if (!isdigit(C.peek()) && (C.peek() != '-' || !isdigit(C.peek(1))))
return None;
@ -331,6 +361,8 @@ StringRef llvm::lexMIToken(
return R.remaining();
if (Cursor R = maybeLexGlobalValue(C, Token, ErrorCallback))
return R.remaining();
if (Cursor R = maybeLexExternalSymbol(C, Token, ErrorCallback))
return R.remaining();
if (Cursor R = maybeLexIntegerLiteral(C, Token))
return R.remaining();
if (Cursor R = maybeLexSymbol(C, Token))

View File

@ -54,6 +54,8 @@ struct MIToken {
NamedGlobalValue,
QuotedNamedGlobalValue,
GlobalValue,
ExternalSymbol,
QuotedExternalSymbol,
// Other tokens
IntegerLiteral,
@ -96,7 +98,9 @@ public:
StringRef::iterator location() const { return Range.begin(); }
bool isStringValueQuoted() const { return Kind == QuotedNamedGlobalValue; }
bool isStringValueQuoted() const {
return Kind == QuotedNamedGlobalValue || Kind == QuotedExternalSymbol;
}
/// Return the token's raw string value.
///

View File

@ -110,6 +110,7 @@ public:
bool parseGlobalAddressOperand(MachineOperand &Dest);
bool parseConstantPoolIndexOperand(MachineOperand &Dest);
bool parseJumpTableIndexOperand(MachineOperand &Dest);
bool parseExternalSymbolOperand(MachineOperand &Dest);
bool parseMachineOperand(MachineOperand &Dest);
private:
@ -560,6 +561,17 @@ bool MIParser::parseJumpTableIndexOperand(MachineOperand &Dest) {
return false;
}
bool MIParser::parseExternalSymbolOperand(MachineOperand &Dest) {
assert(Token.is(MIToken::ExternalSymbol) ||
Token.is(MIToken::QuotedExternalSymbol));
StringValueUtility Name(Token);
const char *Symbol = MF.createExternalSymbolName(Name);
lex();
// TODO: Parse the target flags.
Dest = MachineOperand::CreateES(Symbol);
return false;
}
bool MIParser::parseMachineOperand(MachineOperand &Dest) {
switch (Token.kind()) {
case MIToken::kw_implicit:
@ -587,6 +599,9 @@ bool MIParser::parseMachineOperand(MachineOperand &Dest) {
return parseConstantPoolIndexOperand(Dest);
case MIToken::JumpTableIndex:
return parseJumpTableIndexOperand(Dest);
case MIToken::ExternalSymbol:
case MIToken::QuotedExternalSymbol:
return parseExternalSymbolOperand(Dest);
case MIToken::Error:
return true;
case MIToken::Identifier:

View File

@ -21,6 +21,7 @@
#include "llvm/CodeGen/MIRYamlMapping.h"
#include "llvm/IR/BasicBlock.h"
#include "llvm/IR/Instructions.h"
#include "llvm/IR/IRPrintingPasses.h"
#include "llvm/IR/Module.h"
#include "llvm/IR/ModuleSlotTracker.h"
#include "llvm/Support/MemoryBuffer.h"
@ -430,6 +431,11 @@ void MIPrinter::print(const MachineOperand &Op, const TargetRegisterInfo *TRI) {
OS << "%jump-table." << Op.getIndex();
// TODO: Print target flags.
break;
case MachineOperand::MO_ExternalSymbol:
OS << '$';
printLLVMNameWithoutPrefix(OS, Op.getSymbolName());
// TODO: Print the target flags.
break;
case MachineOperand::MO_GlobalAddress:
Op.getGlobal()->printAsOperand(OS, /*PrintType=*/false, MST);
// TODO: Print offset and target flags.

View File

@ -322,6 +322,13 @@ MachineFunction::extractStoreMemRefs(MachineInstr::mmo_iterator Begin,
return std::make_pair(Result, Result + Num);
}
const char *MachineFunction::createExternalSymbolName(StringRef Name) {
char *Dest = Allocator.Allocate<char>(Name.size() + 1);
std::copy(Name.begin(), Name.end(), Dest);
Dest[Name.size()] = 0;
return Dest;
}
#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
void MachineFunction::dump() const {
print(dbgs());

View File

@ -0,0 +1,60 @@
# RUN: llc -march=x86-64 -start-after branch-folder -stop-after branch-folder -o /dev/null %s | FileCheck %s
# This test ensures that the MIR parser parses the external symbol machine
# operands correctly.
--- |
@__stack_chk_guard = external global i8*
define i32 @test(i32 %n) #0 {
entry:
%StackGuardSlot = alloca i8*
%StackGuard = load i8*, i8** @__stack_chk_guard
call void @llvm.stackprotector(i8* %StackGuard, i8** %StackGuardSlot)
%a = alloca [128 x i32], align 16
%idxprom = sext i32 %n to i64
%arrayidx = getelementptr inbounds [128 x i32], [128 x i32]* %a, i64 0, i64 %idxprom
%0 = load i32, i32* %arrayidx, align 4
call void @llvm.stackprotectorcheck(i8** @__stack_chk_guard)
ret i32 %0
}
declare void @llvm.stackprotector(i8*, i8**) #1
declare void @llvm.stackprotectorcheck(i8**) #1
attributes #0 = { ssp "stack-protector-buffer-size"="8" }
attributes #1 = { nounwind }
...
---
name: test
tracksRegLiveness: true
body:
- id: 0
name: entry
successors: [ '%bb.1.entry', '%bb.2.entry' ]
instructions:
- '%rsp = SUB64ri32 %rsp, 520, implicit-def %eflags'
- '%rcx = LOAD_STACK_GUARD'
- 'MOV64mr %rsp, 1, _, 512, _, %rcx'
- '%rax = MOVSX64rr32 %edi'
- '%eax = MOV32rm %rsp, 4, %rax, 0, _'
- 'CMP64rm %rcx, %rsp, 1, _, 512, _, implicit-def %eflags'
- 'JNE_1 %bb.2.entry, implicit %eflags'
- id: 1
name: entry
instructions:
- '%rsp = ADD64ri32 %rsp, 520, implicit-def %eflags'
- 'RETQ %eax'
- id: 2
name: entry
instructions:
# CHECK: CALL64pcrel32 $__stack_chk_fail,
# CHECK-NEXT: CALL64pcrel32 $__stack_chk_fail.09-_,
# CHECK-NEXT: CALL64pcrel32 $"__stack_chk_fail$",
# CHECK-NEXT: CALL64pcrel32 $"$Quoted \09 External symbol \11 ",
- 'CALL64pcrel32 $__stack_chk_fail, csr_64, implicit %rsp, implicit-def %rsp'
- 'CALL64pcrel32 $__stack_chk_fail.09-_, csr_64, implicit %rsp, implicit-def %rsp'
- 'CALL64pcrel32 $__stack_chk_fail$, csr_64, implicit %rsp, implicit-def %rsp'
- 'CALL64pcrel32 $"$Quoted \09 External symbol \11 ", csr_64, implicit %rsp, implicit-def %rsp'
...