//
// Clean up a SecCodeSigner
//
-SecCodeSigner::~SecCodeSigner() throw()
+SecCodeSigner::~SecCodeSigner() _NOEXCEPT
try {
delete mLimitedAsync;
} catch (...) {
//
bool SecCodeSigner::valid() const
{
- if (mOpFlags & kSecCSRemoveSignature)
+ if (mOpFlags & (kSecCSRemoveSignature | kSecCSEditSignature)) {
return true;
+ }
return mSigner;
}
//
void SecCodeSigner::sign(SecStaticCode *code, SecCSFlags flags)
{
- code->setValidationFlags(flags);
- if (code->isSigned() && (flags & kSecCSSignPreserveSignature))
+ //Never preserve a linker signature.
+ if (code->isSigned() &&
+ (flags & kSecCSSignPreserveSignature) &&
+ !code->flag(kSecCodeSignatureLinkerSigned)) {
return;
+ }
+ code->setValidationFlags(flags);
Signer operation(*this, code);
if ((flags | mOpFlags) & kSecCSRemoveSignature) {
secinfo("signer", "%p will remove signature from %p", this, code);
operation.remove(flags);
+ } else if ((flags | mOpFlags) & kSecCSEditSignature) {
+ secinfo("signer", "%p will edit signature of %p", this, code);
+ operation.edit(flags);
} else {
if (!valid())
MacOSError::throwMe(errSecCSInvalidObjectRef);
SecCodeSigner::Parser::Parser(SecCodeSigner &state, CFDictionaryRef parameters)
: CFDictionary(parameters, errSecCSBadDictionaryFormat)
{
+ CFNumberRef editCpuType = get<CFNumberRef>(kSecCodeSignerEditCpuType);
+ CFNumberRef editCpuSubtype = get<CFNumberRef>(kSecCodeSignerEditCpuSubtype);
+ if (editCpuType != NULL && editCpuSubtype != NULL) {
+ state.mEditArch = Architecture(cfNumber<uint32_t>(editCpuType),
+ cfNumber<uint32_t>(editCpuSubtype));
+ }
+
+ state.mEditCMS = get<CFDataRef>(kSecCodeSignerEditCMS);
+
+ state.mDryRun = getBool(kSecCodeSignerDryRun);
+
+ state.mSDKRoot = get<CFURLRef>(kSecCodeSignerSDKRoot);
+
+ state.mPreserveAFSC = getBool(kSecCodeSignerPreserveAFSC);
+
+ if (state.mOpFlags & kSecCSEditSignature) {
+ return;
+ /* Everything below this point is irrelevant for
+ * Signature Editing, which does not create any
+ * parts of the signature, only replaces them.
+ */
+ }
+
// the signer may be an identity or null
state.mSigner = SecIdentityRef(get<CFTypeRef>(kSecCodeSignerIdentity));
if (state.mSigner)
MacOSError::throwMe(errSecCSInvalidObjectRef);
}
- state.mDryRun = getBool(kSecCodeSignerDryRun);
-
state.mResourceRules = get<CFDictionaryRef>(kSecCodeSignerResourceRules);
state.mApplicationData = get<CFDataRef>(kSecCodeSignerApplicationData);
state.mEntitlementData = get<CFDataRef>(kSecCodeSignerEntitlements);
- state.mSDKRoot = get<CFURLRef>(kSecCodeSignerSDKRoot);
-
if (CFBooleanRef timestampRequest = get<CFBooleanRef>(kSecCodeSignerRequireTimestamp)) {
state.mWantTimeStamp = timestampRequest == kCFBooleanTrue;
} else { // pick default
}
state.mRuntimeVersionOverride = parseRuntimeVersion(runtime);
}
+
+ // Don't add the adhoc flag, even if no signer identity was specified.
+ // Useful for editing in the CMS at a later point.
+ state.mOmitAdhocFlag = getBool(kSecCodeSignerOmitAdhocFlag);
}