Monday, January 31, 2011

Mac App Store rejections due to HXRuntime

Recently, we have had reports of applications being rejected from the Mac App Store with the following message:

The application links against </usr/local/lib/HXRuntime Carbon Mach-O.dylib>, which is missing.

We believe that this is a false-positive in Apple's automated rejection tools. While 2011r1 will not have this 'problem', you can work around it via the following command line invocation:
[joe@Mac-Pro.local ~] install_name_tool -id '@executable_path/rbframework.dylib' '/My Application.app/Contents/MacOS/rbframework.dylib'



The rest of the post is a technical explanation of what is going on and can be skipped if you are not interested. Also, it describes the current implementation details and is in no way an API contract or something to rely on.

The bulk of the REALbasic framework is implemented in C++ and lives in the 'rbframework.dylib' file next to your executable. When you build an application, the REALbasic linker hardcodes the relative path to that dylib. This can be seen by running 'otool -L' on your binary:

[joe@Mac-Pro.local ~] otool -L '/My Application.app/Contents/MacOS/My Application'
My Application:
@executable_path/rbframework.dylib (compatibility version 0.0.0, current version 0.0.0)
/System/Library/Frameworks/Carbon.framework/Carbon (compatibility version 0.0.0, current version 0.0.0)
/usr/lib/libSystem.dylib (compatibility version 0.0.0, current version 0.0.0)

Dylibs also have an 'install name', which is used solely by 'ld' (the linker that comes with Xcode). When you link a binary using Xcode, ld takes the install name of the library it's going to link in and then embeds it in your resulting binary. Since REALbasic does not use ld, we have simply left the install name for rbframework.dylib at its default. This can be seen by running 'otool -l' and searching for the install name's load command:

[joe@Mac-Pro.local ~] otool -l '/My Application.app/Contents/MacOS/rbframework.dylib'
...
Load command 5
cmd LC_ID_DYLIB
cmdsize 72
name /usr/local/lib/HXRuntime Carbon Mach-O.dylib (offset 24)
time stamp 1 Wed Dec 31 19:00:01 1969
current version 1.0.0
compatibility version 1.0.0

Our guess is that Apple has an automated tool that is looking at the install name of rbframework.dylib and rejecting it because it does not exist. However, since the install name is unused by anything but ld64, it is a false positive and not something Apple should be looking at.

While a future version of REALbasic will contain an install name that does not trigger this false positive, a temporary solution is to manually change the install name via install_name_tool, as mentioned above.

7 comments:

Anthony said...

Great explanation, Joe. Thanks!

TJ said...

Any thoughts on why this would only now be affecting submitted apps? I've 2 accepted apps (and I know of others as well) built with 2010r5.

Joe Ranieri said...

@TJ: My best guess is that they have recently added more checks (like this one) to their automated tool.

Sol said...
This comment has been removed by the author.
Dean said...

When you post these kind of code snippets can you also post the best way to do this in an IDE script like a post build script? I know there are RS variables and maybe a slightly different syntax for an IDE script an I'd love this to just be part of the build process. I could try to write it myself but I don't know how I would check the binary afterward to know if my code correctly accomplished the task.

Tom said...

Hello,

Can I apply this fix to the app if the app name contains one or more spaces like 'Finalize Cut Pro'? MAS reviewers are reporting that a fix has not been applied to such apps. Thank you.

Alyssa said...

Just an update on this: This was fixed on 28 Jan 2011, for Real Studio 2011r1