Skip to content

Commit 4323da9

Browse files
committed
[MC][AsmParser] Diagnose improperly nested .cfi frames
This showed up when simplifying some large testcase, where the cfi directives became out of sync with the proc's they enclose. rdar://111459507 Differential revision: https://reviews.llvm.org/D155245 This reverts commit 4172fcc.
1 parent 7939ce3 commit 4323da9

File tree

3 files changed

+36
-2
lines changed

3 files changed

+36
-2
lines changed

lld/test/COFF/gc-dwarf-eh.s

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,9 @@
1313
.def _main; .scl 2; .type 32; .endef
1414
.section .text,"xr",one_only,_main
1515
.globl _main
16+
_main:
1617
.cfi_startproc
1718
.cfi_personality 0, ___gxx_personality_v0
18-
_main:
1919
xorl %eax, %eax
2020
ret
2121
.cfi_endproc
@@ -29,8 +29,8 @@ ___gxx_personality_v0:
2929
.def _unused; .scl 2; .type 32; .endef
3030
.section .text,"xr",one_only,_unused
3131
.globl _unused
32+
_unused:
3233
.cfi_startproc
3334
.cfi_personality 0, ___gxx_personality_v0
34-
_unused:
3535
ret
3636
.cfi_endproc

llvm/lib/MC/MCParser/AsmParser.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,7 @@ class AsmParser : public MCAsmParser {
125125
void *SavedDiagContext;
126126
std::unique_ptr<MCAsmParserExtension> PlatformParser;
127127
SMLoc StartTokLoc;
128+
std::optional<SMLoc> CFIStartProcLoc;
128129

129130
/// This is the current buffer index we're lexing from as managed by the
130131
/// SourceMgr object.
@@ -1949,6 +1950,11 @@ bool AsmParser::parseStatement(ParseStatementInfo &Info,
19491950
Lex();
19501951
}
19511952

1953+
if (CFIStartProcLoc && Sym->isExternal())
1954+
return Error(StartTokLoc, "non-private labels cannot appear between "
1955+
".cfi_startproc / .cfi_endproc pairs") &&
1956+
Error(*CFIStartProcLoc, "previous .cfi_startproc was here");
1957+
19521958
if (discardLTOSymbol(IDVal))
19531959
return false;
19541960

@@ -4193,6 +4199,8 @@ bool AsmParser::parseDirectiveCFISections() {
41934199
/// parseDirectiveCFIStartProc
41944200
/// ::= .cfi_startproc [simple]
41954201
bool AsmParser::parseDirectiveCFIStartProc() {
4202+
CFIStartProcLoc = StartTokLoc;
4203+
41964204
StringRef Simple;
41974205
if (!parseOptionalToken(AsmToken::EndOfStatement)) {
41984206
if (check(parseIdentifier(Simple) || Simple != "simple",
@@ -4213,8 +4221,11 @@ bool AsmParser::parseDirectiveCFIStartProc() {
42134221
/// parseDirectiveCFIEndProc
42144222
/// ::= .cfi_endproc
42154223
bool AsmParser::parseDirectiveCFIEndProc() {
4224+
CFIStartProcLoc = std::nullopt;
4225+
42164226
if (parseEOL())
42174227
return true;
4228+
42184229
getStreamer().emitCFIEndProc();
42194230
return false;
42204231
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
; RUN: not llvm-mc -triple arm64-apple-darwin %s -filetype=obj -o /dev/null 2>&1 | FileCheck %s
2+
3+
; REQUIRES: aarch64-registered-target
4+
5+
.section __TEXT,locomotive,regular,pure_instructions
6+
7+
.globl _locomotive
8+
.p2align 2
9+
_locomotive:
10+
.cfi_startproc
11+
ret
12+
13+
; It is invalid to have a non-private label between .cfi_startproc / .cfi_endproc
14+
.section __TEXT,__text,regular,pure_instructions
15+
.globl _caboose
16+
.p2align 2
17+
_caboose:
18+
; CHECK: [[#@LINE-1]]:1: error: non-private labels cannot appear between .cfi_startproc / .cfi_endproc pairs
19+
; CHECK: [[#@LINE-9]]:2: error: previous .cfi_startproc was here
20+
ret
21+
.cfi_endproc
22+
23+
.subsections_via_symbols

0 commit comments

Comments
 (0)