Codesign w/ debugging entitlement for backtraces on macOS#7010
Conversation
|
@swift-ci test |
|
It doesn't duplicate binaries though, only writes the linked binary to a different location when backtraces are enabled. We move the binary to the final location after codesigning is completed to satisfy the inputs of the phony product rule. So far this is the only way I found to make it work for shell commands that don't have outputs different from inputs (like the |
|
@swift-ci test |
|
llbuild has an |
this may also be interesting in the context of plugins? cc @neonichu @abertelrud |
This sounds like the right way to make this work. Also, I wonder whether it would be worth providing more general support for code signing and entitlements in SwiftPM, so that e.g. a user could specify in the package manifest that they'd like their program signed, and maybe provide a list of entitlements they'd like it to have? |
| } | ||
|
|
||
| func codeSigningArguments(plistPath: AbsolutePath, binaryPath: AbsolutePath) -> [String] { | ||
| ["codesign", "--force", "--sign", "-", "--entitlements", plistPath.pathString, binaryPath.pathString] |
There was a problem hiding this comment.
It might be a good idea to have a command line option to let you specify the code signing identity (here we're using -).
There was a problem hiding this comment.
IMO that should come as a separate PR to make this facility a bit more general.
There was a problem hiding this comment.
Sounds good. I only mention it because people who are aware of how this works will pretty quickly notice that we're signing things and ask how to sign with a different identity.
There was a problem hiding this comment.
That's fair, but signing with a different identity or with a different entitlement requires a public API design and likely an evolution proposal. Scoping this to one specific case means we don't have to block backtraces with this potential future design work.
There was a problem hiding this comment.
Sure. No objection from me.
I think that would be useful, but in my mind, it's very separable from this. We need to design APIs for configuring this etc. |
519bbe1 to
a5d824e
Compare
Dependency of #7010 Added per the llbuild documentation at https://github.com/apple/swift-llbuild/blob/a3b8d34be319f1b3ba8de53c434386419dec1f4f/docs/buildsystem.rst#L387 and a corresponding test at https://github.com/apple/swift-llbuild/blob/a3b8d34be319f1b3ba8de53c434386419dec1f4f/tests/BuildSystem/Build/mutable-outputs.llbuild#L66. I also took the opportunity to get rid of deprecated TSC dependencies in `ManifestWriter.swift`, replacing it with string interpolation instead.
Dependency of #7010. Added per the llbuild documentation at https://github.com/apple/swift-llbuild/blob/a3b8d34be319f1b3ba8de53c434386419dec1f4f/docs/buildsystem.rst#L387 and a corresponding test at https://github.com/apple/swift-llbuild/blob/a3b8d34be319f1b3ba8de53c434386419dec1f4f/tests/BuildSystem/Build/mutable-outputs.llbuild#L66. Newly introduced attributes are not used anywhere yet in this PR, so technically it is NFC. I also took the opportunity to get rid of deprecated TSC dependencies in `ManifestWriter.swift`, replacing it with string interpolation instead.
If we're calling it The reasoning behind |
|
Note: if we're changing |
|
My objections to the current name are:
If we can make it explicitly macOS-only and have future plans for more functionality, the name seems fine to me. |
|
I don't mind |
|
Yeah, there's a case for |
a5d824e to
f7b42ad
Compare
|
IIUC @tomerd prefers |
|
@swift-ci test |
|
@swift-ci test windows |
|
@swift-ci test |
|
@swift-ci test windows |
|
@swift-ci test |
|
@swift-ci test |
|
@swift-ci test |
|
@swift-ci test windows |
|
@swift-ci test |
|
@swift-ci test |
|
@swift-ci test windows |
| public var enableGetTaskAllowEntitlement: Bool = false | ||
|
|
||
| @Flag(help: .hidden) | ||
| public var disableGetTaskAllowEntitlement: Bool = false |
There was a problem hiding this comment.
you can probably marge this into one optional Bool setting
There was a problem hiding this comment.
It doesn't look @Flag supports optional types, unless I'm something? Maybe @natecook1000 or @rauhul can clarify?
There was a problem hiding this comment.
What is the difference between true/false/nil behaviors?
There was a problem hiding this comment.
IIRC I had to provide a default value, but the default value depended on values of other options. I assume false would mean --disable..., true would mean --enable..., and nil would mean neither were passed on CLI?
There was a problem hiding this comment.
Hmm so you want to infer true/false based on other flags unless explicitly specified... that is reasonable. I don't think we support Optional Flags yet, but I wonder if you could use an EnumerableFlag instead.
There was a problem hiding this comment.
You can actually have a boolean flag as long as there's an inversion, which I think is exactly what you want in this case. The declaration would look like:
@Flag(inversion: .prefixedEnableDisable)
var getTaskAllowEntitlement: Bool?It looks like we might not allow an = nil in there, which may have been what you ran into. That's also an issue we should be able to fix pretty easily.
There was a problem hiding this comment.
My bad, it actually does support an optional default value, at least with .prefixedEnableDisable it works great. I'll submit a follow-up PR.
| } | ||
|
|
||
| // Create a phony node to represent the entire target. | ||
| let targetName = try buildProduct.product.getLLBuildTargetName(config: self.buildConfig) |
There was a problem hiding this comment.
please check if this has performance implications, I vaguely remeber @neonichu ran into something like that with this API, tho no 100% sure
There was a problem hiding this comment.
This phony node is not new, it's only moved from previous L62 where it was declared too late for us. I had to move it up to this line.
### Motivation: Following up on feedback to #7010, it's better to have a single optional boolean option than two non-optional booleans. ### Modifications: Replaced `var enableGetTaskAllowEntitlement = false` and `var disableGetTaskAllowEntitlement = false` with `var getTaskAllowEntitlement: Bool? = nil`, which has an additional `inversion: .prefixedEnableDisable` configuration. ### Result: Code handling these flags is simpler and easier to read.
Motivation:
The new Swift backtracer will only function on macOS if:
SWIFT_BACKTRACEenvironment variable has itsenableoption set toyesortty, andThe program you are running was signed with the
com.apple.security.get-task-allowentitlement.Xcode automatically signs all local builds with that entitlement by default; without it the Swift backtracer won't work.
SwiftPM should sign Debug binaries with the entitlement by default. It should also have an option to sign Release binaries with the entitlement, noting that they should not be distributed in that state but that crashes may only manifest in release builds (where the optimizer is fully enabled).
Modifications:
Added new
--enable-get-task-allow-entitlementand--disable-get-task-allow-entitlementCLI flags. Made it enabled by default for debug builds on macOS. When enabled, applying codesigning withcom.apple.security.get-task-allowinLLBuildManifestBuilder+Product.swift.Result:
Backtraces work on macOS when built with SwiftPM.
Resolves rdar://112065568.