Search

Signings of the Times

Mark Dalrymple

6 min read

Sep 5, 2012

iOS

Signings of the Times

You know that sinking feeling in your stomach. That horrible emotion that you know that something has gone wrong, seriously wrong, and you’re going to be facing a mountain of pain. That terror that’s even worse than your significant other sitting you down saying “we need to talk”. It’s this:

Signing could not install app

That’s right. Something has gone wrong with signing, provisioning, or certificates, or something.

Now you, as the individual in charge of putting out a beta (or enterprise) release, have to fix it. Over the past numerous months I’ve had to set up some ad-hoc beta builds for OTA (over the air) delivery, as well as distributing builds with App47, an enterprise application management system and TestFlight, and I knew I was in for some suffering when I got that alert on my first installation test.

What usually happens is hours of flailing around, Trying Stuff, begging Uncle Google for advice, and then magically It Starts Working, in which case you step away from the keyboard, commit the current state of your Xcode project, and find a bottle of single malt to crawl into. This time before hitting the Glen Breton, I’m writing down what I discovered.

Finding Some Evidence

The console log on your device might have some useful information on it. Before trying your install, make sure your device is actually being shown on the console in the Xcode organizer. Sometimes I select the console, or look at the Organizer window funny, and the console view goes blank, refusing to show any new content. If your console goes blank, wave a dead chicken over it by clicking off the console and back on it a couple of times. When you get a screenful of text, try installing your program. You hopefully will see something like this.

installd <Error>: entitlement 'get-task-allow' has value not permitted by a provisioning profile
installd <Error>: entitlement 'application-identifier' has value not permitted by a provisioning profile
installd <Error>: 00381000 verify_signer_identity: Could not copy validate signature: -402620394
installd <Error>: 00381000 preflight_application_install: Could not verify executable at /var/tmp/install_staging.RoDpEv/foo_extracted/Payload/Catalog.app
itunesstored <Notice>: MobileInstallationInstall: failed with -1
installd <Error>: 00381000 install_application: Could not preflight application install
installd <Error>: 00381000 handle_install: API failed
installd <Error>: 00381000 send_message: failed to send mach message of 71 bytes: 10000003
installd <Error>: 00381000 send_error: Could not send error response to client

The first two lines are the interesting part. Something is wrong with the provisioning profile. How can you see what’s up? Time to duck down to the command line and peer inside your application.

The codesign tool will look at an app and tell you about things relating to signing. It has an extensive man page, but the two variants I use most often show the signing information, and the entitlements baked in to the app.

codesign looks inside of application bundles, not IPA files, so you need to unpack the IPA. Luckily it’s just a zip archive:

% <strong>unzip Catalog.ipa</strong>
Archive:  Catalog.ipa
   creating: Payload/
   creating: Payload/Catalog.app/
 extracting: Payload/Catalog.app/1x1.png
   creating: Payload/Catalog.app/_CodeSignature/
  inflating: Payload/Catalog.app/_CodeSignature/CodeResources
  inflating: Payload/Catalog.app/Catalog
  ...

You’ll have a directory called Payload that contains the app. The program causing me problems today is called Catalog.app.

First, take a look at the code signing:

% <strong>codesign -dvvv Payload/Catalog.app</strong>
Executable=/Users/markd/junk/Payload/Catalog.app/Catalog
Identifier=com.bignerdranch.Catalog
Format=bundle with Mach-O thin (armv7)
CodeDirectory v=20100 size=2513 flags=0x0(none) hashes=117+5 location=embedded
Hash type=sha1 size=20
CDHash=f748ae9eb017fd3b88dce5d55519788239928edc
Signature size=4309
Authority=iPhone Distribution: Big Nerd Ranch, Inc
Authority=Apple Worldwide Developer Relations Certification Authority
Authority=Apple Root CA
Signed Time=Aug 30, 2012 7:25:55 PM
Info.plist entries=28
Sealed Resources rules=3 files=31
Internal requirements count=1 size=296

The interesting part to me is that yes, it is signed using the Big Nerd Ranch profile I was given for making this release.

So what about the entitlements?

% codesign -d --entitlements - ./Payload/Catalog.app
Executable=/Users/markd/junk/Payload/Catalog.app/Catalog
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
        <key>application-identifier</key>
        <string>9B7AX7DA2G.com.bignerdranch.Catalog</string>
        <key>get-task-allow</key>
        <true/>
</dict>
</plist>

See that get-task-allow = true? That sounds like one of our problems:

installd <Error>: entitlement 'get-task-allow' has value not permitted by a provisioning profile

It should be set to false. This is an entitlement that tells the launcher that this program can be attached to by other programs, specifically things like debuggers. For things being distributed to real people with a release profile, this needs to be turned off.

How did it get turned on in the first place? One way is to have it explicitly set in an Entitlements.plist file that’s included in your build. The other way happens automatically: Xcode will set it to true if you sign it with a development profile, and to false if you sign it with a distribution profile.

So that was problem #1 (building with a debug profile and signing the IPA with a release profile), and also an indication of what problem #2 was. I must be using the wrong profile (the one for development) when building the app.

Align the Stars with the Phase of the Moon

So, what about that profile? What can go wrong with it? You need to make sure that you sign the application at build time with a profile that’s miscible with what you’ll eventually sign the IPA with. This is the application ID from codesign:

        <key>application-identifier</key>
        <string>9B7AX7DA2G.com.bignerdranch.Catalog</string>

There was this complaint when trying to install stuff:

entitlement 'application-identifier' has value not permitted by a provisioning profile

So there’s something about this identifier that’s not quite right. The leading chunk of goop is the team ID (also called the bundle seed ID), which kind of looked familiar because it’s my personal ID marklar. I looked in the organizer and noticed the profile I’m using to sign the IPAs has a different leading part:

Signing with BNR Profile
So, the bundle ID really should be

E6B2EB2666.com.bignerdranch.Catalog

The only way Xcode will bake the proper ID in there for us is if we sign it with a profile that matches. So after some editing of the signing build settings, I made sure it used the proper profile:

Signing with the proper profile

Fixed that stuff, and did a build, signed an IPA, and double-checked my work:

% codesign -d --entitlements - ./Payload/Catalog.app
...
<dict>
        <key>application-identifier</key>
        <string>E6B2EB2666.com.bignerdranch.Catalog</string>
        <key>get-task-allow</key>
        <false/>
...

Much better. The application identifier team ID portion matches what’s in the distribution profile, and get-task-allow is false.

The Takeway

I’d like to say that it only took me five minutes to fix. If I face this again, it might only take five minutes, but it was easily a couple of hours spread out over a couple of days, first wrestling with the third party tool and getting installation failures, then building my own OTA distribution with something like BetaBuilder for easier testing (removing a variable from the system). Once I noticed the info in the log, I hacked the get-task-allow with an entitlement file (which I subsequently removed) to get something working, and then finally fixed all the signing wibbly bits, life was good.

Mark Dalrymple

Author Big Nerd Ranch

MarkD is a long-time Unix and Mac developer, having worked at AOL, Google, and several start-ups over the years.  He’s the author of Advanced Mac OS X Programming: The Big Nerd Ranch Guide, over 100 blog posts for Big Nerd Ranch, and an occasional speaker at conferences. Believing in the power of community, he’s a co-founder of CocoaHeads, an international Mac and iPhone meetup, and runs the Pittsburgh PA chapter. In his spare time, he plays orchestral and swing band music.

Speak with a Nerd

Schedule a call today! Our team of Nerds are ready to help

Let's Talk

Related Posts

We are ready to discuss your needs.

Not applicable? Click here to schedule a call.

Stay in Touch WITH Big Nerd Ranch News