252 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 22; RUN: llc -mtriple=aarch64 < %s | FileCheck --check-prefixes CHECK-V8A %s3; RUN: llc -mtriple=aarch64 -mattr=v8.3a < %s | FileCheck --check-prefixes CHECK-V83A %s4; RUN: llc -mtriple=aarch64 -filetype=obj -o - <%s | llvm-dwarfdump -v - | FileCheck --check-prefix=CHECK-DUMP %s5 6@.str = private unnamed_addr constant [15 x i8] c"some exception\00", align 17@_ZTIPKc = external dso_local constant ptr8 9define dso_local i32 @_Z3fooi(i32 %x) #0 {10; CHECK-V8A-LABEL: _Z3fooi:11; CHECK-V8A: // %bb.0: // %entry12; CHECK-V8A-NEXT: hint #2513; CHECK-V8A-NEXT: .cfi_negate_ra_state14; CHECK-V8A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill15; CHECK-V8A-NEXT: .cfi_def_cfa_offset 1616; CHECK-V8A-NEXT: .cfi_offset w30, -1617; CHECK-V8A-NEXT: str w0, [sp, #8]18; CHECK-V8A-NEXT: mov w0, #8 // =0x819; CHECK-V8A-NEXT: bl __cxa_allocate_exception20; CHECK-V8A-NEXT: adrp x8, .L.str21; CHECK-V8A-NEXT: add x8, x8, :lo12:.L.str22; CHECK-V8A-NEXT: adrp x1, _ZTIPKc23; CHECK-V8A-NEXT: add x1, x1, :lo12:_ZTIPKc24; CHECK-V8A-NEXT: mov x2, xzr25; CHECK-V8A-NEXT: str x8, [x0]26; CHECK-V8A-NEXT: bl __cxa_throw27;28; CHECK-V83A-LABEL: _Z3fooi:29; CHECK-V83A: // %bb.0: // %entry30; CHECK-V83A-NEXT: paciasp31; CHECK-V83A-NEXT: .cfi_negate_ra_state32; CHECK-V83A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill33; CHECK-V83A-NEXT: .cfi_def_cfa_offset 1634; CHECK-V83A-NEXT: .cfi_offset w30, -1635; CHECK-V83A-NEXT: str w0, [sp, #8]36; CHECK-V83A-NEXT: mov w0, #8 // =0x837; CHECK-V83A-NEXT: bl __cxa_allocate_exception38; CHECK-V83A-NEXT: adrp x8, .L.str39; CHECK-V83A-NEXT: add x8, x8, :lo12:.L.str40; CHECK-V83A-NEXT: adrp x1, _ZTIPKc41; CHECK-V83A-NEXT: add x1, x1, :lo12:_ZTIPKc42; CHECK-V83A-NEXT: mov x2, xzr43; CHECK-V83A-NEXT: str x8, [x0]44; CHECK-V83A-NEXT: bl __cxa_throw45entry:46 %retval = alloca i32, align 447 %x.addr = alloca i32, align 448 store i32 %x, ptr %x.addr, align 449 %exception = call ptr @__cxa_allocate_exception(i64 8) #150 store ptr @.str, ptr %exception, align 1651 call void @__cxa_throw(ptr %exception, ptr @_ZTIPKc, ptr null) #252 unreachable53 54return: ; No predecessors!55 %0 = load i32, ptr %retval, align 456 ret i32 %057}58 59; For asynchronous unwind tables, we need to flip the value of RA_SIGN_STATE60; before and after the tail call. In the prolog, RA_SIGN_STATE is updated right61; after the corresponding 'PACIASP' instruction.62define hidden noundef i32 @baz_async(i32 noundef %a) #0 uwtable(async) {63; CHECK-V8A-LABEL: baz_async:64; CHECK-V8A: // %bb.0: // %entry65; CHECK-V8A-NEXT: hint #2566; CHECK-V8A-NEXT: .cfi_negate_ra_state67; CHECK-V8A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill68; CHECK-V8A-NEXT: .cfi_def_cfa_offset 1669; CHECK-V8A-NEXT: .cfi_offset w30, -1670; CHECK-V8A-NEXT: .cfi_remember_state71; CHECK-V8A-NEXT: cbz w0, .LBB1_272; CHECK-V8A-NEXT: // %bb.1: // %if.then73; CHECK-V8A-NEXT: mov w0, wzr74; CHECK-V8A-NEXT: bl _Z3bari75; CHECK-V8A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload76; CHECK-V8A-NEXT: .cfi_def_cfa_offset 077; CHECK-V8A-NEXT: .cfi_restore w3078; CHECK-V8A-NEXT: hint #2979; CHECK-V8A-NEXT: .cfi_negate_ra_state80; CHECK-V8A-NEXT: b _Z3bari81; CHECK-V8A-NEXT: .LBB1_2: // %if.else82; CHECK-V8A-NEXT: .cfi_restore_state83; CHECK-V8A-NEXT: bl _Z4quuxi84; CHECK-V8A-NEXT: add w0, w0, #185; CHECK-V8A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload86; CHECK-V8A-NEXT: .cfi_def_cfa_offset 087; CHECK-V8A-NEXT: .cfi_restore w3088; CHECK-V8A-NEXT: hint #2989; CHECK-V8A-NEXT: .cfi_negate_ra_state90; CHECK-V8A-NEXT: ret91;92; CHECK-V83A-LABEL: baz_async:93; CHECK-V83A: // %bb.0: // %entry94; CHECK-V83A-NEXT: paciasp95; CHECK-V83A-NEXT: .cfi_negate_ra_state96; CHECK-V83A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill97; CHECK-V83A-NEXT: .cfi_def_cfa_offset 1698; CHECK-V83A-NEXT: .cfi_offset w30, -1699; CHECK-V83A-NEXT: .cfi_remember_state100; CHECK-V83A-NEXT: cbz w0, .LBB1_2101; CHECK-V83A-NEXT: // %bb.1: // %if.then102; CHECK-V83A-NEXT: mov w0, wzr103; CHECK-V83A-NEXT: bl _Z3bari104; CHECK-V83A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload105; CHECK-V83A-NEXT: .cfi_def_cfa_offset 0106; CHECK-V83A-NEXT: .cfi_restore w30107; CHECK-V83A-NEXT: autiasp108; CHECK-V83A-NEXT: .cfi_negate_ra_state109; CHECK-V83A-NEXT: b _Z3bari110; CHECK-V83A-NEXT: .LBB1_2: // %if.else111; CHECK-V83A-NEXT: .cfi_restore_state112; CHECK-V83A-NEXT: bl _Z4quuxi113; CHECK-V83A-NEXT: add w0, w0, #1114; CHECK-V83A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload115; CHECK-V83A-NEXT: .cfi_def_cfa_offset 0116; CHECK-V83A-NEXT: .cfi_restore w30117; CHECK-V83A-NEXT: retaa118entry:119 %tobool.not = icmp eq i32 %a, 0120 br i1 %tobool.not, label %if.else, label %if.then121 122if.then: ; preds = %entry123 %call = tail call noundef i32 @_Z3bari(i32 noundef 0)124 %call1 = tail call noundef i32 @_Z3bari(i32 noundef %call)125 br label %return126 127if.else: ; preds = %entry128 %call2 = tail call noundef i32 @_Z4quuxi(i32 noundef 0)129 %add = add nsw i32 %call2, 1130 br label %return131 132return: ; preds = %if.else, %if.then133 %retval.0 = phi i32 [ %call1, %if.then ], [ %add, %if.else ]134 ret i32 %retval.0135}136 137; For synchronous unwind tables, we don't need to update the unwind tables138; around the tail call. The tail-called function might throw an exception, but139; at this point we are set up to return into baz's caller, so the unwinder will140; never see baz's unwind table for that exception.141; The '.cfi_negate_ra_state' instruction in the prolog can be bundled with other142; CFI instructions to avoid emitting superfluous DW_CFA_advance_loc.143define hidden noundef i32 @baz_sync(i32 noundef %a) #0 uwtable(sync) {144; CHECK-V8A-LABEL: baz_sync:145; CHECK-V8A: // %bb.0: // %entry146; CHECK-V8A-NEXT: hint #25147; CHECK-V8A-NEXT: .cfi_negate_ra_state148; CHECK-V8A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill149; CHECK-V8A-NEXT: .cfi_def_cfa_offset 16150; CHECK-V8A-NEXT: .cfi_offset w30, -16151; CHECK-V8A-NEXT: cbz w0, .LBB2_2152; CHECK-V8A-NEXT: // %bb.1: // %if.then153; CHECK-V8A-NEXT: mov w0, wzr154; CHECK-V8A-NEXT: bl _Z3bari155; CHECK-V8A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload156; CHECK-V8A-NEXT: hint #29157; CHECK-V8A-NEXT: b _Z3bari158; CHECK-V8A-NEXT: .LBB2_2: // %if.else159; CHECK-V8A-NEXT: bl _Z4quuxi160; CHECK-V8A-NEXT: add w0, w0, #1161; CHECK-V8A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload162; CHECK-V8A-NEXT: hint #29163; CHECK-V8A-NEXT: ret164;165; CHECK-V83A-LABEL: baz_sync:166; CHECK-V83A: // %bb.0: // %entry167; CHECK-V83A-NEXT: paciasp168; CHECK-V83A-NEXT: .cfi_negate_ra_state169; CHECK-V83A-NEXT: str x30, [sp, #-16]! // 8-byte Folded Spill170; CHECK-V83A-NEXT: .cfi_def_cfa_offset 16171; CHECK-V83A-NEXT: .cfi_offset w30, -16172; CHECK-V83A-NEXT: cbz w0, .LBB2_2173; CHECK-V83A-NEXT: // %bb.1: // %if.then174; CHECK-V83A-NEXT: mov w0, wzr175; CHECK-V83A-NEXT: bl _Z3bari176; CHECK-V83A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload177; CHECK-V83A-NEXT: autiasp178; CHECK-V83A-NEXT: b _Z3bari179; CHECK-V83A-NEXT: .LBB2_2: // %if.else180; CHECK-V83A-NEXT: bl _Z4quuxi181; CHECK-V83A-NEXT: add w0, w0, #1182; CHECK-V83A-NEXT: ldr x30, [sp], #16 // 8-byte Folded Reload183; CHECK-V83A-NEXT: retaa184entry:185 %tobool.not = icmp eq i32 %a, 0186 br i1 %tobool.not, label %if.else, label %if.then187 188if.then: ; preds = %entry189 %call = tail call noundef i32 @_Z3bari(i32 noundef 0)190 %call1 = tail call noundef i32 @_Z3bari(i32 noundef %call)191 br label %return192 193if.else: ; preds = %entry194 %call2 = tail call noundef i32 @_Z4quuxi(i32 noundef 0)195 %add = add nsw i32 %call2, 1196 br label %return197 198return: ; preds = %if.else, %if.then199 %retval.0 = phi i32 [ %call1, %if.then ], [ %add, %if.else ]200 ret i32 %retval.0201}202 203declare dso_local ptr @__cxa_allocate_exception(i64)204 205declare dso_local void @__cxa_throw(ptr, ptr, ptr)206 207declare dso_local noundef i32 @_Z3bari(i32 noundef) local_unnamed_addr208declare dso_local noundef i32 @_Z4quuxi(i32 noundef) local_unnamed_addr209 210attributes #0 = { "sign-return-address"="all" }211 212; foo213; CHECK-DUMP-LABEL: FDE214; CHECK-DUMP: DW_CFA_AARCH64_negate_ra_state:215; CHECK-DUMP-NOT: DW_CFA_AARCH64_negate_ra_state216; CHECK-DUMP-NOT: DW_CFA_remember_state217; CHECK-DUMP-NOT: DW_CFA_restore_state218 219; CHECK-DUMP: CFA=WSP{{$}}220; CHECK-DUMP: reg34=1221; CHECK-DUMP-NOT: reg34=0222 223; baz_async224; CHECK-DUMP-LABEL: FDE225; CHECK-DUMP: Format: DWARF32226; CHECK-DUMP: DW_CFA_AARCH64_negate_ra_state:227; CHECK-DUMP: DW_CFA_remember_state:228; CHECK-DUMP: DW_CFA_AARCH64_negate_ra_state:229; CHECK-DUMP: DW_CFA_restore_state:230; CHECK-DUMP: DW_CFA_AARCH64_negate_ra_state:231 232;; First DW_CFA_AARCH64_negate_ra_state:233; CHECK-DUMP: reg34=1234;; Second DW_CFA_AARCH64_negate_ra_state:235; CHECK-DUMP: reg34=0236;; DW_CFA_restore_state:237; CHECK-DUMP: reg34=1238;; Third DW_CFA_AARCH64_negate_ra_state:239; CHECK-DUMP: reg34=0240; CHECK-DUMP-NOT: reg34=1241 242; baz_sync243; CHECK-DUMP-LABEL: FDE244; CHECK-DUMP: DW_CFA_AARCH64_negate_ra_state:245; CHECK-DUMP-NOT: DW_CFA_AARCH64_negate_ra_state246; CHECK-DUMP-NOT: DW_CFA_remember_state247; CHECK-DUMP-NOT: DW_CFA_restore_state248 249; CHECK-DUMP: CFA=WSP{{$}}250; CHECK-DUMP: reg34=1251; CHECK-DUMP-NOT: reg34=0252