[MC] Parse end-of-line for .cfi_* directives

Otherwise MCAsmStreamer will emit duplicate newlines.
This commit is contained in:
Fangrui Song 2021-03-06 16:20:55 -08:00
parent dd9a641184
commit fd785f98aa
14 changed files with 92 additions and 52 deletions

View File

@ -4140,7 +4140,7 @@ bool AsmParser::parseDirectiveCFIDefCfa(SMLoc DirectiveLoc) {
int64_t Register = 0, Offset = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::Comma, "unexpected token in directive") ||
parseAbsoluteExpression(Offset))
parseAbsoluteExpression(Offset) || parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIDefCfa(Register, Offset);
@ -4151,7 +4151,7 @@ bool AsmParser::parseDirectiveCFIDefCfa(SMLoc DirectiveLoc) {
/// ::= .cfi_def_cfa_offset offset
bool AsmParser::parseDirectiveCFIDefCfaOffset() {
int64_t Offset = 0;
if (parseAbsoluteExpression(Offset))
if (parseAbsoluteExpression(Offset) || parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIDefCfaOffset(Offset);
@ -4164,7 +4164,8 @@ bool AsmParser::parseDirectiveCFIRegister(SMLoc DirectiveLoc) {
int64_t Register1 = 0, Register2 = 0;
if (parseRegisterOrRegisterNumber(Register1, DirectiveLoc) ||
parseToken(AsmToken::Comma, "unexpected token in directive") ||
parseRegisterOrRegisterNumber(Register2, DirectiveLoc))
parseRegisterOrRegisterNumber(Register2, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIRegister(Register1, Register2);
@ -4174,6 +4175,8 @@ bool AsmParser::parseDirectiveCFIRegister(SMLoc DirectiveLoc) {
/// parseDirectiveCFIWindowSave
/// ::= .cfi_window_save
bool AsmParser::parseDirectiveCFIWindowSave() {
if (parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIWindowSave();
return false;
}
@ -4182,7 +4185,8 @@ bool AsmParser::parseDirectiveCFIWindowSave() {
/// ::= .cfi_adjust_cfa_offset adjustment
bool AsmParser::parseDirectiveCFIAdjustCfaOffset() {
int64_t Adjustment = 0;
if (parseAbsoluteExpression(Adjustment))
if (parseAbsoluteExpression(Adjustment) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIAdjustCfaOffset(Adjustment);
@ -4193,7 +4197,8 @@ bool AsmParser::parseDirectiveCFIAdjustCfaOffset() {
/// ::= .cfi_def_cfa_register register
bool AsmParser::parseDirectiveCFIDefCfaRegister(SMLoc DirectiveLoc) {
int64_t Register = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc))
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIDefCfaRegister(Register);
@ -4208,7 +4213,7 @@ bool AsmParser::parseDirectiveCFIOffset(SMLoc DirectiveLoc) {
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::Comma, "unexpected token in directive") ||
parseAbsoluteExpression(Offset))
parseAbsoluteExpression(Offset) || parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIOffset(Register, Offset);
@ -4222,7 +4227,7 @@ bool AsmParser::parseDirectiveCFIRelOffset(SMLoc DirectiveLoc) {
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::Comma, "unexpected token in directive") ||
parseAbsoluteExpression(Offset))
parseAbsoluteExpression(Offset) || parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIRelOffset(Register, Offset);
@ -4265,7 +4270,8 @@ bool AsmParser::parseDirectiveCFIPersonalityOrLsda(bool IsPersonality) {
StringRef Name;
if (check(!isValidEncoding(Encoding), "unsupported encoding.") ||
parseToken(AsmToken::Comma, "unexpected token in directive") ||
check(parseIdentifier(Name), "expected identifier in directive"))
check(parseIdentifier(Name), "expected identifier in directive") ||
parseToken(AsmToken::EndOfStatement))
return true;
MCSymbol *Sym = getContext().getOrCreateSymbol(Name);
@ -4280,6 +4286,8 @@ bool AsmParser::parseDirectiveCFIPersonalityOrLsda(bool IsPersonality) {
/// parseDirectiveCFIRememberState
/// ::= .cfi_remember_state
bool AsmParser::parseDirectiveCFIRememberState() {
if (parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIRememberState();
return false;
}
@ -4287,6 +4295,8 @@ bool AsmParser::parseDirectiveCFIRememberState() {
/// parseDirectiveCFIRestoreState
/// ::= .cfi_remember_state
bool AsmParser::parseDirectiveCFIRestoreState() {
if (parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIRestoreState();
return false;
}
@ -4296,7 +4306,8 @@ bool AsmParser::parseDirectiveCFIRestoreState() {
bool AsmParser::parseDirectiveCFISameValue(SMLoc DirectiveLoc) {
int64_t Register = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc))
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFISameValue(Register);
@ -4307,7 +4318,8 @@ bool AsmParser::parseDirectiveCFISameValue(SMLoc DirectiveLoc) {
/// ::= .cfi_restore register
bool AsmParser::parseDirectiveCFIRestore(SMLoc DirectiveLoc) {
int64_t Register = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc))
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIRestore(Register);
@ -4341,7 +4353,8 @@ bool AsmParser::parseDirectiveCFIEscape() {
/// ::= .cfi_return_column register
bool AsmParser::parseDirectiveCFIReturnColumn(SMLoc DirectiveLoc) {
int64_t Register = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc))
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIReturnColumn(Register);
return false;
@ -4363,7 +4376,8 @@ bool AsmParser::parseDirectiveCFISignalFrame() {
bool AsmParser::parseDirectiveCFIUndefined(SMLoc DirectiveLoc) {
int64_t Register = 0;
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc))
if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) ||
parseToken(AsmToken::EndOfStatement))
return true;
getStreamer().emitCFIUndefined(Register);

View File

@ -1,26 +1,23 @@
// RUN: llvm-mc -triple aarch64-- -o - %s | FileCheck %s
fun:
// CHECK: .cfi_startproc
// CHECK-NEXT: stp
.cfi_startproc
// CHECK: .cfi_startproc
stp x29, x30, [sp, #-16]!
.Lcfi0:
// CHECK: .cfi_offset w29, -16
// CHECK-NEXT: .cfi_offset w30, -8
.cfi_offset w29, -16
// CHECK: .cfi_offset w29, -16
.Lcfi1:
.cfi_offset w30, -8
// CHECK: .cfi_offset w30, -8
mov x29, sp
.Lcfi2:
// CHECK: .cfi_def_cfa w29, 16
// CHECK-NEXT: .cfi_restore w30
// CHECK-NEXT: ldr
// CHECK-NEXT: .cfi_restore w29
.cfi_def_cfa w29, 16
// CHECK: .cfi_def_cfa w29, 16
.Lcfi3:
.cfi_restore w30
// CHECK: .cfi_restore w30
ldr x29, [sp], #16
.Lcfi4:
.cfi_restore w29
// CHECK: .cfi_restore w29
ret
.cfi_endproc
// CHECK: .cfi_endproc

View File

@ -1,15 +0,0 @@
# RUN: llvm-mc -filetype=asm -triple x86_64-pc-linux-gnu <%s | FileCheck %s
# Should use SPARC as the target to test this. However, SPARC does not support
# asm parsing yet.
# CHECK: .cfi_window_save
f:
.cfi_startproc
nop
.cfi_window_save
nop
.cfi_endproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_def_cfa_offset 16{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_def_cfa_register %rbp{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_escape 0x15, 0x07, 0x7f{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_register %rbp, %rax{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,10 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_rel_offset %rbp, 16{{$}}
# ASM-NEXT: nop
# ASM: .cfi_rel_offset %rbp, 0{{$}}
# ASM-NEXT: .cfi_endproc
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_remember_state{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,5 +1,5 @@
// REQUIRES: x86-registered-target
// RUN: llvm-mc -triple i686-unknown-linux-gnu -filetype asm -o - %s | FileCheck %s -check-prefix CHECK-ASM-ROUNDTRIP
// RUN: llvm-mc -triple i686 %s | FileCheck %s --check-prefix=ASM
// RUN: llvm-mc -triple i686-unknown-linux-gnu -filetype obj -o - %s | llvm-objdump --dwarf=frames - | FileCheck %s --check-prefix=CHECK-EH_FRAME
.text
@ -28,10 +28,10 @@ h:
.cfi_return_column 65
.cfi_endproc
// CHECK-ASM-ROUNDTRIP-LABEL: f:
// CHECK-ASM-ROUNDTRIP: .cfi_startproc
// CHECK-ASM-ROUNDTRIP-NEXT: .cfi_return_column %eax
// CHECK-ASM-ROUNDTRIP: .cfi_endproc
// ASM-LABEL: f:
// ASM: .cfi_startproc
// ASM-NEXT: .cfi_return_column %eax
// ASM-NEXT: .cfi_endproc
// CHECK-EH_FRAME: 00000000 00000014 00000000 CIE
// CHECK-EH_FRAME: Return address column: 0

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_same_value %rbp{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_undefined %rbp{{$}}
# ASM-NEXT: nop
f:
.cfi_startproc

View File

@ -1,4 +1,8 @@
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
# RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
# RUN: llvm-mc -filetype=obj -triple x86_64 %s | llvm-readobj -S --sr --sd - | FileCheck %s
# ASM: .cfi_window_save{{$}}
# ASM-NEXT: nop
# Should use SPARC as the target to test this. However, SPARC does not
# use MC yet.

View File

@ -1,6 +1,12 @@
// RUN: llvm-mc -triple x86_64 %s | FileCheck %s --check-prefix=ASM
// RUN: llvm-mc -filetype=obj -triple x86_64-pc-linux-gnu %s -o - | llvm-readobj -S --sr --sd - | FileCheck %s
// RUN: not llvm-mc -triple=x86_64 -o - -defsym=ERR=1 %s 2>&1 | FileCheck %s --check-prefix=ERR
// ASM: .cfi_lsda 3, bar
// ASM-NEXT: nop
// ASM: .cfi_personality 0, foo
// ASM-NEXT: .cfi_lsda 3, bar
f1:
.cfi_startproc
.cfi_lsda 0x3, bar