@@ -545,11 +545,13 @@ fn fn_abi_new_uncached<'tcx>(
545
545
instance : Option < ty:: Instance < ' tcx > > ,
546
546
) -> Result < & ' tcx FnAbi < ' tcx , Ty < ' tcx > > , & ' tcx FnAbiError < ' tcx > > {
547
547
let tcx = cx. tcx ( ) ;
548
- let ( caller_location, fn_def_id, is_virtual_call) = if let Some ( instance) = instance {
548
+ let ( caller_location, determined_fn_def_id, is_virtual_call) = if let Some ( instance) = instance
549
+ {
550
+ let is_virtual_call = matches ! ( instance. def, ty:: InstanceKind :: Virtual ( ..) ) ;
549
551
(
550
552
instance. def . requires_caller_location ( tcx) . then ( || tcx. caller_location_ty ( ) ) ,
551
- Some ( instance. def_id ( ) ) ,
552
- matches ! ( instance . def , ty :: InstanceKind :: Virtual ( .. ) ) ,
553
+ if is_virtual_call { None } else { Some ( instance. def_id ( ) ) } ,
554
+ is_virtual_call ,
553
555
)
554
556
} else {
555
557
( None , None , false )
@@ -579,7 +581,7 @@ fn fn_abi_new_uncached<'tcx>(
579
581
} ;
580
582
581
583
let is_drop_in_place =
582
- fn_def_id . is_some_and ( |def_id| tcx. is_lang_item ( def_id, LangItem :: DropInPlace ) ) ;
584
+ determined_fn_def_id . is_some_and ( |def_id| tcx. is_lang_item ( def_id, LangItem :: DropInPlace ) ) ;
583
585
584
586
let arg_of = |ty : Ty < ' tcx > , arg_idx : Option < usize > | -> Result < _ , & ' tcx FnAbiError < ' tcx > > {
585
587
let span = tracing:: debug_span!( "arg_of" ) ;
@@ -635,7 +637,12 @@ fn fn_abi_new_uncached<'tcx>(
635
637
c_variadic : sig. c_variadic ,
636
638
fixed_count : inputs. len ( ) as u32 ,
637
639
conv,
638
- can_unwind : fn_can_unwind ( cx. tcx ( ) , fn_def_id, sig. abi ) ,
640
+ can_unwind : fn_can_unwind (
641
+ tcx,
642
+ // Since `#[rustc_nounwind]` can change unwinding, we cannot infer unwinding by `fn_def_id` for a virtual call.
643
+ determined_fn_def_id,
644
+ sig. abi ,
645
+ ) ,
639
646
} ;
640
647
fn_abi_adjust_for_abi (
641
648
cx,
@@ -644,7 +651,7 @@ fn fn_abi_new_uncached<'tcx>(
644
651
// If this is a virtual call, we cannot pass the `fn_def_id`, as it might call other
645
652
// functions from vtable. Internally, `deduced_param_attrs` attempts to infer attributes by
646
653
// visit the function body.
647
- fn_def_id . filter ( |_| !is_virtual_call ) ,
654
+ determined_fn_def_id ,
648
655
) ;
649
656
debug ! ( "fn_abi_new_uncached = {:?}" , fn_abi) ;
650
657
fn_abi_sanity_check ( cx, & fn_abi, sig. abi ) ;
0 commit comments