Skip to content

Commit 0792cdd

Browse files
committed
[PAC] Include discriminator in FnAbi, add llvm.ptrauth.resign
This patch introduces the following: * Extends `FnAbi` (`callconv`) with a `ptrauth_type_discriminator` field. This field is only used when emitting pointer authentication call bundles. It is stored in `FnAbi` because the call site is not guaranteed to have access to an `Instance`, so the discriminator cannot always be computed on demand. * Adds support for `llvm.ptrauth.resign`. This intrinsic will be used when support for semantic transmute is added. * Performs a minor API redesign as groundwork for allowing call sites to modify schemas in place.
1 parent 8cf67b9 commit 0792cdd

29 files changed

Lines changed: 169 additions & 18 deletions

compiler/rustc_codegen_gcc/src/builder.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1843,6 +1843,17 @@ impl<'a, 'gcc, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'gcc, 'tcx> {
18431843
fn fptosi_sat(&mut self, val: RValue<'gcc>, dest_ty: Type<'gcc>) -> RValue<'gcc> {
18441844
self.fptoint_sat(true, val, dest_ty)
18451845
}
1846+
1847+
fn ptrauth_resign(
1848+
&mut self,
1849+
_value: Self::Value,
1850+
_old_key: u32,
1851+
_old_discriminator: u64,
1852+
_new_key: u32,
1853+
_new_discriminator: u64,
1854+
) -> Self::Value {
1855+
bug!("Resigning of pointers not implemented");
1856+
}
18461857
}
18471858

18481859
impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {

compiler/rustc_codegen_gcc/src/common.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,7 @@ impl<'gcc, 'tcx> ConstCodegenMethods for CodegenCx<'gcc, 'tcx> {
247247
cv: Scalar,
248248
layout: abi::Scalar,
249249
ty: Type<'gcc>,
250-
_schema: Option<&PointerAuthSchema>,
250+
_schema: Option<PointerAuthSchema>,
251251
) -> RValue<'gcc> {
252252
let bitsize = if layout.is_bool() { 1 } else { layout.size(self).bits() };
253253
match cv {

compiler/rustc_codegen_gcc/src/context.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -401,7 +401,7 @@ impl<'gcc, 'tcx> MiscCodegenMethods<'tcx> for CodegenCx<'gcc, 'tcx> {
401401
fn get_fn_addr(
402402
&self,
403403
instance: Instance<'tcx>,
404-
_pointer_auth_schema: Option<&PointerAuthSchema>,
404+
_pointer_auth_schema: Option<PointerAuthSchema>,
405405
) -> RValue<'gcc> {
406406
let func_name = self.tcx.symbol_name(instance).name;
407407

compiler/rustc_codegen_gcc/src/int.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -375,6 +375,7 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
375375
fixed_count: 3,
376376
conv: CanonAbi::C,
377377
can_unwind: false,
378+
ptrauth_type_discriminator: 0,
378379
};
379380
fn_abi.adjust_for_foreign_abi(self.cx, ExternAbi::C { unwind: false });
380381

compiler/rustc_codegen_llvm/src/builder.rs

Lines changed: 32 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1542,6 +1542,30 @@ impl<'a, 'll, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'll, 'tcx> {
15421542
let cold_inline = llvm::AttributeKind::Cold.create_attr(self.llcx);
15431543
attributes::apply_to_callsite(llret, llvm::AttributePlace::Function, &[cold_inline]);
15441544
}
1545+
1546+
fn ptrauth_resign(
1547+
&mut self,
1548+
value: &'ll Value,
1549+
old_key: u32,
1550+
old_discriminator: u64,
1551+
new_key: u32,
1552+
new_discriminator: u64,
1553+
) -> &'ll Value {
1554+
let ptr_as_int = self.ptrtoint(value, self.type_i64());
1555+
let resigned_int = self.call_intrinsic(
1556+
"llvm.ptrauth.resign",
1557+
&[],
1558+
&[
1559+
ptr_as_int,
1560+
self.const_i32(old_key as i32),
1561+
self.const_i64(old_discriminator as i64),
1562+
self.const_i32(new_key as i32),
1563+
self.const_i64(new_discriminator as i64),
1564+
],
1565+
);
1566+
1567+
self.inttoptr(resigned_int, self.val_ty(value))
1568+
}
15451569
}
15461570

15471571
impl<'ll> StaticBuilderMethods for Builder<'_, 'll, '_> {
@@ -2059,8 +2083,14 @@ impl<'a, 'll, 'tcx> Builder<'a, 'll, 'tcx> {
20592083
// bundles.
20602084
// Once this is resolved, we should analyze each call and skip direct calls. See the
20612085
// discussion in the rust-lang issue: <https://github.com/rust-lang/rust/issues/152532>
2062-
let key: u32 = 0;
2063-
let discriminator: u64 = 0;
2086+
2087+
let key: u32 = self.sess().pointer_authentication_fn_ptr_key().unwrap() as u32;
2088+
let discriminator = if self.sess().pointer_authentication_fn_ptr_type_discrimination() {
2089+
fn_abi?.ptrauth_type_discriminator
2090+
} else {
2091+
0
2092+
};
2093+
20642094
Some(llvm::OperandBundleBox::new(
20652095
"ptrauth",
20662096
&[self.const_u32(key), self.const_u64(discriminator)],

compiler/rustc_codegen_llvm/src/common.rs

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -30,11 +30,9 @@ pub(crate) fn maybe_sign_fn_ptr<'ll, 'tcx>(
3030
cx: &CodegenCx<'ll, '_>,
3131
instance: Instance<'tcx>,
3232
llfn: &'ll llvm::Value,
33-
schema: &PointerAuthSchema,
33+
schema: PointerAuthSchema,
3434
) -> &'ll llvm::Value {
35-
if cx.tcx.sess.pointer_authentication_functions().is_none() {
36-
return llfn;
37-
}
35+
assert!(cx.tcx.sess.pointer_authentication_functions().is_some());
3836

3937
// Only free functions or methods
4038
let def_id = instance.def_id();
@@ -317,7 +315,7 @@ impl<'ll, 'tcx> ConstCodegenMethods for CodegenCx<'ll, 'tcx> {
317315
cv: Scalar,
318316
layout: abi::Scalar,
319317
llty: &'ll Type,
320-
schema: Option<&PointerAuthSchema>,
318+
schema: Option<PointerAuthSchema>,
321319
) -> &'ll Value {
322320
let bitsize = if layout.is_bool() { 1 } else { layout.size(self).bits() };
323321
match cv {

compiler/rustc_codegen_llvm/src/context.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -913,7 +913,7 @@ impl<'ll, 'tcx> MiscCodegenMethods<'tcx> for CodegenCx<'ll, 'tcx> {
913913
fn get_fn_addr(
914914
&self,
915915
instance: Instance<'tcx>,
916-
pointer_auth_schema: Option<&PointerAuthSchema>,
916+
pointer_auth_schema: Option<PointerAuthSchema>,
917917
) -> &'ll Value {
918918
// When pointer authentication metadata is provided, `get_fn_addr` will
919919
// attempt to sign the pointer using LLVM's `ConstPtrAuth` constant

compiler/rustc_codegen_ssa/src/traits/builder.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -667,4 +667,13 @@ pub trait BuilderMethods<'a, 'tcx>:
667667
fn zext(&mut self, val: Self::Value, dest_ty: Self::Type) -> Self::Value;
668668

669669
fn apply_attrs_to_cleanup_callsite(&mut self, llret: Self::Value);
670+
671+
fn ptrauth_resign(
672+
&mut self,
673+
value: Self::Value,
674+
old_key: u32,
675+
old_discriminator: u64,
676+
new_key: u32,
677+
new_discriminator: u64,
678+
) -> Self::Value;
670679
}

compiler/rustc_codegen_ssa/src/traits/consts.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ pub trait ConstCodegenMethods: BackendTypes {
4747
cv: Scalar,
4848
layout: abi::Scalar,
4949
llty: Self::Type,
50-
schema: Option<&PointerAuthSchema>,
50+
schema: Option<PointerAuthSchema>,
5151
) -> Self::Value;
5252

5353
fn const_ptr_byte_offset(&self, val: Self::Value, offset: abi::Size) -> Self::Value;

compiler/rustc_codegen_ssa/src/traits/misc.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ pub trait MiscCodegenMethods<'tcx>: BackendTypes {
2222
fn get_fn_addr(
2323
&self,
2424
instance: Instance<'tcx>,
25-
pointer_auth_schema: Option<&PointerAuthSchema>,
25+
pointer_auth_schema: Option<PointerAuthSchema>,
2626
) -> Self::Value;
2727
fn eh_personality(&self) -> Self::Function;
2828
fn sess(&self) -> &Session;

0 commit comments

Comments
 (0)