Skip to content

Commit 4a1a56b

Browse files
committed
Add deactivation symbol operand to ConstantPtrAuth.
Deactivation symbol operands are supported in the code generator by building on the previously added support for IRELATIVE relocations. TODO: - Fix broken test. - Add bitcode and IR writer support. - Add tests. Pull Request: llvm#133537
1 parent cad9057 commit 4a1a56b

File tree

16 files changed

+126
-41
lines changed

16 files changed

+126
-41
lines changed

clang/lib/CodeGen/CGPointerAuth.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -308,9 +308,9 @@ CodeGenModule::getConstantSignedPointer(llvm::Constant *Pointer, unsigned Key,
308308
IntegerDiscriminator = llvm::ConstantInt::get(Int64Ty, 0);
309309
}
310310

311-
return llvm::ConstantPtrAuth::get(Pointer,
312-
llvm::ConstantInt::get(Int32Ty, Key),
313-
IntegerDiscriminator, AddressDiscriminator);
311+
return llvm::ConstantPtrAuth::get(
312+
Pointer, llvm::ConstantInt::get(Int32Ty, Key), IntegerDiscriminator,
313+
AddressDiscriminator, llvm::Constant::getNullValue(UnqualPtrTy));
314314
}
315315

316316
/// Does a given PointerAuthScheme require us to sign a value

llvm/include/llvm/Bitcode/LLVMBitCodes.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -431,6 +431,7 @@ enum ConstantsCodes {
431431
CST_CODE_CE_GEP_WITH_INRANGE = 31, // [opty, flags, range, n x operands]
432432
CST_CODE_CE_GEP = 32, // [opty, flags, n x operands]
433433
CST_CODE_PTRAUTH = 33, // [ptr, key, disc, addrdisc]
434+
CST_CODE_PTRAUTH2 = 34, // [ptr, key, disc, addrdisc, DeactivationSymbol]
434435
};
435436

436437
/// CastOpcodes - These are values used in the bitcode files to encode which

llvm/include/llvm/IR/Constants.h

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1022,10 +1022,10 @@ class ConstantPtrAuth final : public Constant {
10221022
friend struct ConstantPtrAuthKeyType;
10231023
friend class Constant;
10241024

1025-
constexpr static IntrusiveOperandsAllocMarker AllocMarker{4};
1025+
constexpr static IntrusiveOperandsAllocMarker AllocMarker{5};
10261026

10271027
ConstantPtrAuth(Constant *Ptr, ConstantInt *Key, ConstantInt *Disc,
1028-
Constant *AddrDisc);
1028+
Constant *AddrDisc, Constant *DeactivationSymbol);
10291029

10301030
void *operator new(size_t s) { return User::operator new(s, AllocMarker); }
10311031

@@ -1035,7 +1035,8 @@ class ConstantPtrAuth final : public Constant {
10351035
public:
10361036
/// Return a pointer signed with the specified parameters.
10371037
static ConstantPtrAuth *get(Constant *Ptr, ConstantInt *Key,
1038-
ConstantInt *Disc, Constant *AddrDisc);
1038+
ConstantInt *Disc, Constant *AddrDisc,
1039+
Constant *DeactivationSymbol);
10391040

10401041
/// Produce a new ptrauth expression signing the given value using
10411042
/// the same schema as is stored in one.
@@ -1067,6 +1068,10 @@ class ConstantPtrAuth final : public Constant {
10671068
return !getAddrDiscriminator()->isNullValue();
10681069
}
10691070

1071+
Constant *getDeactivationSymbol() const {
1072+
return cast<Constant>(Op<4>().get());
1073+
}
1074+
10701075
/// A constant value for the address discriminator which has special
10711076
/// significance to ctors/dtors lowering. Regular address discrimination can't
10721077
/// be applied for them since uses of llvm.global_{c|d}tors are disallowed
@@ -1094,7 +1099,7 @@ class ConstantPtrAuth final : public Constant {
10941099

10951100
template <>
10961101
struct OperandTraits<ConstantPtrAuth>
1097-
: public FixedNumOperandTraits<ConstantPtrAuth, 4> {};
1102+
: public FixedNumOperandTraits<ConstantPtrAuth, 5> {};
10981103

10991104
DEFINE_TRANSPARENT_OPERAND_ACCESSORS(ConstantPtrAuth, Constant)
11001105

llvm/include/llvm/SandboxIR/Constant.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1096,7 +1096,8 @@ class ConstantPtrAuth final : public Constant {
10961096
public:
10971097
/// Return a pointer signed with the specified parameters.
10981098
static ConstantPtrAuth *get(Constant *Ptr, ConstantInt *Key,
1099-
ConstantInt *Disc, Constant *AddrDisc);
1099+
ConstantInt *Disc, Constant *AddrDisc,
1100+
Constant *DeactivationSymbol);
11001101
/// The pointer that is signed in this ptrauth signed pointer.
11011102
Constant *getPointer() const;
11021103

@@ -1111,6 +1112,8 @@ class ConstantPtrAuth final : public Constant {
11111112
/// the only global-initializer user of the ptrauth signed pointer.
11121113
Constant *getAddrDiscriminator() const;
11131114

1115+
Constant *getDeactivationSymbol() const;
1116+
11141117
/// Whether there is any non-null address discriminator.
11151118
bool hasAddressDiscriminator() const {
11161119
return cast<llvm::ConstantPtrAuth>(Val)->hasAddressDiscriminator();

llvm/lib/AsmParser/LLParser.cpp

Lines changed: 21 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -4226,11 +4226,12 @@ bool LLParser::parseValID(ValID &ID, PerFunctionState *PFS, Type *ExpectedTy) {
42264226
}
42274227
case lltok::kw_ptrauth: {
42284228
// ValID ::= 'ptrauth' '(' ptr @foo ',' i32 <key>
4229-
// (',' i64 <disc> (',' ptr addrdisc)? )? ')'
4229+
// (',' i64 <disc> (',' ptr addrdisc (',' ptr ds)? )? )? ')'
42304230
Lex.Lex();
42314231

42324232
Constant *Ptr, *Key;
4233-
Constant *Disc = nullptr, *AddrDisc = nullptr;
4233+
Constant *Disc = nullptr, *AddrDisc = nullptr,
4234+
*DeactivationSymbol = nullptr;
42344235

42354236
if (parseToken(lltok::lparen,
42364237
"expected '(' in constant ptrauth expression") ||
@@ -4239,11 +4240,14 @@ bool LLParser::parseValID(ValID &ID, PerFunctionState *PFS, Type *ExpectedTy) {
42394240
"expected comma in constant ptrauth expression") ||
42404241
parseGlobalTypeAndValue(Key))
42414242
return true;
4242-
// If present, parse the optional disc/addrdisc.
4243-
if (EatIfPresent(lltok::comma))
4244-
if (parseGlobalTypeAndValue(Disc) ||
4245-
(EatIfPresent(lltok::comma) && parseGlobalTypeAndValue(AddrDisc)))
4246-
return true;
4243+
// If present, parse the optional disc/addrdisc/ds.
4244+
if (EatIfPresent(lltok::comma) && parseGlobalTypeAndValue(Disc))
4245+
return true;
4246+
if (EatIfPresent(lltok::comma) && parseGlobalTypeAndValue(AddrDisc))
4247+
return true;
4248+
if (EatIfPresent(lltok::comma) &&
4249+
parseGlobalTypeAndValue(DeactivationSymbol))
4250+
return true;
42474251
if (parseToken(lltok::rparen,
42484252
"expected ')' in constant ptrauth expression"))
42494253
return true;
@@ -4274,7 +4278,16 @@ bool LLParser::parseValID(ValID &ID, PerFunctionState *PFS, Type *ExpectedTy) {
42744278
AddrDisc = ConstantPointerNull::get(PointerType::get(Context, 0));
42754279
}
42764280

4277-
ID.ConstantVal = ConstantPtrAuth::get(Ptr, KeyC, DiscC, AddrDisc);
4281+
if (DeactivationSymbol) {
4282+
if (!DeactivationSymbol->getType()->isPointerTy())
4283+
return error(
4284+
ID.Loc, "constant ptrauth deactivation symbol must be a pointer");
4285+
} else {
4286+
DeactivationSymbol = ConstantPointerNull::get(PointerType::get(Context, 0));
4287+
}
4288+
4289+
ID.ConstantVal =
4290+
ConstantPtrAuth::get(Ptr, KeyC, DiscC, AddrDisc, DeactivationSymbol);
42784291
ID.Kind = ValID::t_Constant;
42794292
return false;
42804293
}

llvm/lib/Bitcode/Reader/BitcodeReader.cpp

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1611,7 +1611,13 @@ Expected<Value *> BitcodeReader::materializeValue(unsigned StartValID,
16111611
if (!Disc)
16121612
return error("ptrauth disc operand must be ConstantInt");
16131613

1614-
C = ConstantPtrAuth::get(ConstOps[0], Key, Disc, ConstOps[3]);
1614+
auto *DeactivationSymbol =
1615+
ConstOps.size() > 4 ? ConstOps[4]
1616+
: ConstantPointerNull::get(cast<PointerType>(
1617+
ConstOps[3]->getType()));
1618+
1619+
C = ConstantPtrAuth::get(ConstOps[0], Key, Disc, ConstOps[3],
1620+
DeactivationSymbol);
16151621
break;
16161622
}
16171623
case BitcodeConstant::NoCFIOpcode: {
@@ -3811,6 +3817,16 @@ Error BitcodeReader::parseConstants() {
38113817
(unsigned)Record[2], (unsigned)Record[3]});
38123818
break;
38133819
}
3820+
case bitc::CST_CODE_PTRAUTH2: {
3821+
if (Record.size() < 4)
3822+
return error("Invalid ptrauth record");
3823+
// Ptr, Key, Disc, AddrDisc, DeactivationSymbol
3824+
V = BitcodeConstant::create(
3825+
Alloc, CurTy, BitcodeConstant::ConstantPtrAuthOpcode,
3826+
{(unsigned)Record[0], (unsigned)Record[1], (unsigned)Record[2],
3827+
(unsigned)Record[3], (unsigned)Record[4]});
3828+
break;
3829+
}
38143830
}
38153831

38163832
assert(V->getType() == getTypeByID(CurTyID) && "Incorrect result type ID");

llvm/lib/IR/AsmWriter.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1630,12 +1630,14 @@ static void WriteConstantInternal(raw_ostream &Out, const Constant *CV,
16301630
if (const ConstantPtrAuth *CPA = dyn_cast<ConstantPtrAuth>(CV)) {
16311631
Out << "ptrauth (";
16321632

1633-
// ptrauth (ptr CST, i32 KEY[, i64 DISC[, ptr ADDRDISC]?]?)
1633+
// ptrauth (ptr CST, i32 KEY[, i64 DISC[, ptr ADDRDISC[, ptr DS]?]?]?)
16341634
unsigned NumOpsToWrite = 2;
16351635
if (!CPA->getOperand(2)->isNullValue())
16361636
NumOpsToWrite = 3;
16371637
if (!CPA->getOperand(3)->isNullValue())
16381638
NumOpsToWrite = 4;
1639+
if (!CPA->getOperand(4)->isNullValue())
1640+
NumOpsToWrite = 5;
16391641

16401642
ListSeparator LS;
16411643
for (unsigned i = 0, e = NumOpsToWrite; i != e; ++i) {

llvm/lib/IR/Constants.cpp

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2072,19 +2072,22 @@ Value *NoCFIValue::handleOperandChangeImpl(Value *From, Value *To) {
20722072
//
20732073

20742074
ConstantPtrAuth *ConstantPtrAuth::get(Constant *Ptr, ConstantInt *Key,
2075-
ConstantInt *Disc, Constant *AddrDisc) {
2076-
Constant *ArgVec[] = {Ptr, Key, Disc, AddrDisc};
2075+
ConstantInt *Disc, Constant *AddrDisc,
2076+
Constant *DeactivationSymbol) {
2077+
Constant *ArgVec[] = {Ptr, Key, Disc, AddrDisc, DeactivationSymbol};
20772078
ConstantPtrAuthKeyType MapKey(ArgVec);
20782079
LLVMContextImpl *pImpl = Ptr->getContext().pImpl;
20792080
return pImpl->ConstantPtrAuths.getOrCreate(Ptr->getType(), MapKey);
20802081
}
20812082

20822083
ConstantPtrAuth *ConstantPtrAuth::getWithSameSchema(Constant *Pointer) const {
2083-
return get(Pointer, getKey(), getDiscriminator(), getAddrDiscriminator());
2084+
return get(Pointer, getKey(), getDiscriminator(), getAddrDiscriminator(),
2085+
getDeactivationSymbol());
20842086
}
20852087

20862088
ConstantPtrAuth::ConstantPtrAuth(Constant *Ptr, ConstantInt *Key,
2087-
ConstantInt *Disc, Constant *AddrDisc)
2089+
ConstantInt *Disc, Constant *AddrDisc,
2090+
Constant *DeactivationSymbol)
20882091
: Constant(Ptr->getType(), Value::ConstantPtrAuthVal, AllocMarker) {
20892092
assert(Ptr->getType()->isPointerTy());
20902093
assert(Key->getBitWidth() == 32);
@@ -2094,6 +2097,7 @@ ConstantPtrAuth::ConstantPtrAuth(Constant *Ptr, ConstantInt *Key,
20942097
setOperand(1, Key);
20952098
setOperand(2, Disc);
20962099
setOperand(3, AddrDisc);
2100+
setOperand(4, DeactivationSymbol);
20972101
}
20982102

20992103
/// Remove the constant from the constant table.

llvm/lib/IR/ConstantsContext.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -545,7 +545,8 @@ struct ConstantPtrAuthKeyType {
545545

546546
ConstantPtrAuth *create(TypeClass *Ty) const {
547547
return new ConstantPtrAuth(Operands[0], cast<ConstantInt>(Operands[1]),
548-
cast<ConstantInt>(Operands[2]), Operands[3]);
548+
cast<ConstantInt>(Operands[2]), Operands[3],
549+
Operands[4]);
549550
}
550551
};
551552

llvm/lib/IR/Core.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1687,7 +1687,9 @@ LLVMValueRef LLVMConstantPtrAuth(LLVMValueRef Ptr, LLVMValueRef Key,
16871687
LLVMValueRef Disc, LLVMValueRef AddrDisc) {
16881688
return wrap(ConstantPtrAuth::get(
16891689
unwrap<Constant>(Ptr), unwrap<ConstantInt>(Key),
1690-
unwrap<ConstantInt>(Disc), unwrap<Constant>(AddrDisc)));
1690+
unwrap<ConstantInt>(Disc), unwrap<Constant>(AddrDisc),
1691+
ConstantPointerNull::get(
1692+
cast<PointerType>(unwrap<Constant>(AddrDisc)->getType()))));
16911693
}
16921694

16931695
/*-- Opcode mapping */

0 commit comments

Comments
 (0)