Skip to content

Commit a8eb030

Browse files
committed
[CIR] Handle __asm labels on function declarations
This updates the CIR direct callee builder code to handle the case of calls to functions that were declared with an assembly label using `__asm`. The implementation doesn't actually have any explicit handling of the AsmLabelAttr. It is handled by the name mangler. See https://reviews.llvm.org/D137073 and https://reviews.llvm.org/D134362 for details on how this was implemented in classic codegen. The test here is copied from https://reviews.llvm.org/D134362 because the test in https://reviews.llvm.org/D134362 requires a target that isn't yet supported in CIR.
1 parent 518b38c commit a8eb030

File tree

2 files changed

+59
-5
lines changed

2 files changed

+59
-5
lines changed

clang/lib/CIR/CodeGen/CIRGenExpr.cpp

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1768,11 +1768,7 @@ CIRGenCallee CIRGenFunction::emitDirectCallee(const GlobalDecl &gd) {
17681768
const auto *fd = cast<FunctionDecl>(gd.getDecl());
17691769

17701770
if (unsigned builtinID = fd->getBuiltinID()) {
1771-
if (fd->getAttr<AsmLabelAttr>()) {
1772-
cgm.errorNYI("AsmLabelAttr");
1773-
}
1774-
1775-
StringRef ident = fd->getName();
1771+
StringRef ident = cgm.getMangledName(gd);
17761772
std::string fdInlineName = (ident + ".inline").str();
17771773

17781774
bool isPredefinedLibFunction =
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
// RUN: %clang_cc1 -triple x86_64 -fclangir -emit-cir -disable-llvm-passes -o %t-cir.cir %s
2+
// RUN: FileCheck --input-file=%t-cir.cir %s --check-prefix=CIR
3+
// RUN: %clang_cc1 -triple x86_64 -fclangir -emit-llvm -disable-llvm-passes -o %t-cir.ll %s
4+
// RUN: FileCheck --input-file=%t-cir.ll %s --check-prefix=LLVM
5+
// RUN: %clang_cc1 -triple x86_64 -emit-llvm -disable-llvm-passes -o %t.ll %s
6+
// RUN: FileCheck --input-file=%t.ll %s --check-prefix=OGCG
7+
8+
9+
// Verifies that clang-generated *.inline carry the same name at call and callee
10+
// site, in spite of asm labels.
11+
12+
typedef struct _IO_FILE FILE;
13+
extern FILE *stdout;
14+
extern int vprintf (const char *__restrict __format, __builtin_va_list __arg);
15+
extern int __vfprintf_chk (FILE *__restrict __stream, int __flag,
16+
const char *__restrict __format, __builtin_va_list __ap);
17+
extern int __vprintf_chk (int __flag, const char *__restrict __format,
18+
__builtin_va_list __ap);
19+
20+
extern __typeof (vprintf) vprintf __asm ("__vprintfieee128");
21+
extern __typeof (__vfprintf_chk) __vfprintf_chk __asm ("__vfprintf_chkieee128");
22+
extern __typeof (__vprintf_chk) __vprintf_chk __asm ("__vprintf_chkieee128");
23+
24+
extern __inline __attribute__ ((__always_inline__)) __attribute__ ((__gnu_inline__)) __attribute__ ((__artificial__)) int
25+
vprintf (const char *__restrict __fmt, __builtin_va_list __ap)
26+
{
27+
return __vfprintf_chk (stdout, 2 - 1, __fmt, __ap);
28+
}
29+
30+
void test(const char *fmt, __builtin_va_list ap) {
31+
vprintf(fmt, ap);
32+
}
33+
34+
// CIR: cir.func internal private @__vprintfieee128.inline({{.*}}) -> !s32i inline(always)
35+
// CIR: cir.call @__vfprintf_chkieee128(%{{.*}}, %{{.*}}, %{{.*}}, %{{.*}})
36+
//
37+
// CIR: cir.func {{.*}} @test({{.*}})
38+
// CIR: cir.call @__vprintfieee128.inline(%{{.*}}, %{{.*}})
39+
40+
41+
// LLVM: define internal i32 @__vprintfieee128.inline({{.*}}) #[[ALWAYS_INLINE_ATTR:.*]] {
42+
// LLVM: call i32 @__vfprintf_chkieee128(ptr %{{.*}}, i32 1, ptr %{{.*}}, ptr %{{.*}})
43+
//
44+
// LLVM: define {{.*}} void @test{{.*}}
45+
// LLVM: call i32 @__vprintfieee128.inline(ptr %{{.*}}, ptr %{{.*}})
46+
//
47+
// LLVM: attributes #[[ALWAYS_INLINE_ATTR]] = { alwaysinline }
48+
49+
// Note: OGCG emits these in the opposite order, but the content is the same.
50+
51+
52+
// OGCG: define {{.*}} void @test{{.*}}
53+
// OGCG: call i32 @__vprintfieee128.inline(ptr noundef %{{.*}}, ptr noundef %{{.*}})
54+
//
55+
// OGCG: define internal i32 @__vprintfieee128.inline({{.*}}) #[[ALWAYS_INLINE_ATTR:.*]] {
56+
// OGCG: call i32 @__vfprintf_chkieee128(ptr noundef %{{.*}}, i32 noundef 1, ptr noundef %{{.*}}, ptr noundef %{{.*}})
57+
//
58+
// OGCG: attributes #[[ALWAYS_INLINE_ATTR]] = { alwaysinline {{.*}} }

0 commit comments

Comments
 (0)