[MacPorts] #53567: Signed libraries in app-bundle don't work in MacOS 10.10 after libgcc update
MacPorts
noreply at macports.org
Tue Feb 14 10:06:50 UTC 2017
#53567: Signed libraries in app-bundle don't work in MacOS 10.10 after libgcc
update
-----------------------------------------+--------------------
Reporter: michalfapso | Owner:
Type: defect | Status: new
Priority: Normal | Milestone:
Component: ports | Version: 2.4.0
Keywords: codesign, signature, bundle | Port: libgcc
-----------------------------------------+--------------------
== What should happen: ==
Signature of an app-bundle properly running on MacOS 10.12 should be
accepted also on MacOS 10.10
== What happens ==
The app-bundle doesn't run on MacOS 10.10. It complains about an invalid
signature for libstdc++.6.dylib and libgomp.1.dylib, which were included
in the app-bundle/Frameworks subdir. It shows the error only when running
the app. Verifying the signature on both MacOS 10.10 and 10.12 using
codesign or spctl doesn't show any problem.
Here is the crash report:
{{{
Process: main [2704]
Path:
/Users/USER/Downloads/codesign_test.app/Contents/MacOS/main
Identifier: esc.codesign_test
Version: ???
Code Type: X86-64 (Native)
Parent Process: ??? [1]
Responsible: main [2704]
User ID: 501
Date/Time: 2017-02-14 01:16:29.681 -0800
OS Version: Mac OS X 10.10 (14A389)
Report Version: 11
Anonymous UUID: 289A82EA-E13C-9F37-E706-539160D5EEAD
Sleep/Wake UUID: E4E56CBD-BEDD-4B03-AA8F-C22BFEA5AFE7
Time Awake Since Boot: 290000 seconds
Crashed Thread: 0
Exception Type: EXC_BREAKPOINT (SIGTRAP)
Exception Codes: 0x0000000000000002, 0x0000000000000000
Application Specific Information:
dyld: launch, loading dependent libraries
Dyld Error Message:
Library not loaded: @executable_path/../Frameworks/libgomp.1.dylib
Referenced from:
/Users/USER/Downloads/codesign_test.app/Contents/MacOS/main
Reason: no suitable image found. Did find:
/Users/esc/Downloads/codesign_test.app/Contents/MacOS/../Frameworks/libgomp.1.dylib:
code signature invalid for
'/Users/esc/Downloads/codesign_test.app/Contents/MacOS/../Frameworks/libgomp.1.dylib'
/Users/esc/Downloads/codesign_test.app/Contents/MacOS/../Frameworks/libgomp.1.dylib:
code signature invalid for
'/Users/esc/Downloads/codesign_test.app/Contents/MacOS/../Frameworks/libgomp.1.dylib'
Binary Images:
0x7fff5fdf8000 - 0x7fff5fe2e837 dyld (353.2.1)
<4696A982-1500-34EC-9777-1EF7A03E2659> /usr/lib/dyld
Model: MacBookPro11,3, BootROM VirtualBox, 4 processors, 4 GHz, 3 GB, SMC
2.3f35
Graphics: Display, PCI, 3 MB
Memory Module: Bank 0/DIMM 0, 2.93 GB, DRAM, 1600 MHz, innotek GmbH, -
Network Service: Ethernet, Ethernet, en0
Serial ATA Device: VBOX HARDDISK, 42.95 GB
Serial ATA Device: VBOX CD-ROM
USB Device: USB Tablet
USB Device: USB Keyboard
Thunderbolt Bus:
}}}
It is similar with libstdc++.6.dylib, but it doesn't complain about an
invalid signature, because it finds a valid library in
/usr/lib/libstdc++.6.dylib and uses that one instead of the one provided
in the bundle. However, the version from macports has several new symbols
which are not included in the version on MacOS 10.10 which causes "symbol
not found" at runtime.
== Quick fix ==
Taking libgomp.1.dylib and libstdc++.6.dylib from our older bundle created
before macports update and putting them into the new app-bundle instead of
the ones in the current macports, works correctly on both MacOS 10.12 and
10.10.
== How to reproduce ==
The problem with MacOS 10.10 was first reported by two of our users. We
installed the 10.10 in a VirtualBox (https://techsviewer.com/install-mac-
os-x-10-10-yosemite-retail-on-virtualbox-with-windows-7-or-windows-8/)
main.cpp:
{{{#!cpp
#include <iostream>
int main()
{
std::cout << "main() works!" << std::endl;
return 0;
}
}}}
Info.plist:
{{{#!xml
<?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>NSPrincipalClass</key>
<string>NSApplication</string>
<key>CFBundleIconFile</key>
<string></string>
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleGetInfoString</key>
<string>Created by Qt/QMake</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleExecutable</key>
<string>main</string>
<key>CFBundleIdentifier</key>
<string>esc.codesign_test</string>
<key>NOTE</key>
<string>This file was generated by Qt/QMake.</string>
</dict>
</plist>
}}}
PkgInfo:
{{{
APPL????
}}}
create_bundle.sh:
{{{#!sh
#!/bin/bash
BUNDLEID=esc.codesign_test
APPCERT="Developer ID Application: Escape Motions, s.r.o"
EXE=main
rm $EXE
g++ -lgomp -mmacosx-version-min=10.8 -o $EXE main.cpp
APP=codesign_test.app
BUNDLE_PATH="$APP"
TARGET_DIR="$APP/Contents/Frameworks"
function copy_lib
{
DYLIB=$1
DYLIB_TARGET_NAME=$2
DYLIB_OTOOL_PATH=$3
DYLIB_EXE=$4
if [ -z "$DYLIB_TARGET_NAME" ]; then
DYLIB_TARGET_NAME="`basename "$DYLIB"`"
fi
if [ -z "$DYLIB_OTOOL_PATH" ]; then
DYLIB_OTOOL_PATH="$DYLIB"
fi
if [ -z "$DYLIB_EXE" ]; then
DYLIB_EXE="$APP/Contents/MacOS/$EXE"
fi
if [[ ! -z "$(echo $DESTDIR | grep final_release_)" || ! -e
"$TARGET_DIR/$DYLIB_TARGET_NAME" ]]; then
cp "$DYLIB" "$TARGET_DIR/$DYLIB_TARGET_NAME"
chmod +w "$TARGET_DIR/$DYLIB_TARGET_NAME"
install_name_tool -id
@executable_path/../Frameworks/$DYLIB_TARGET_NAME
"$TARGET_DIR/$DYLIB_TARGET_NAME"
fi
#install_name_tool -change `otool -L "$EXE" | grep
"$DYLIB_OTOOL_PATH" | awk '{print $1}'`
@executable_path/../Frameworks/"`basename "$DYLIB"`" "$EXE"
install_name_tool -change "$DYLIB_OTOOL_PATH"
@executable_path/../Frameworks/"$DYLIB_TARGET_NAME" "$DYLIB_EXE"
}
rm -r $APP
mkdir -p $APP/Contents/MacOS
cp main $APP/Contents/MacOS/
cp Info.plist $APP/Contents
cp PkgInfo $APP/Contents
sign_timestamp="" # --timestamp=none
sign_force=""
mkdir -p $APP/Contents/Frameworks
copy_lib "/opt/local/lib/libgcc/libstdc++.6.dylib" "" "" ""
# Copying the lib from an older bundle:
#copy_lib
"/Applications/Rebelle.app/Contents/Frameworks/libstdc++.6.dylib"
"libstdc++.6.dylib" "/opt/local/lib/libgcc/libstdc++.6.dylib" ""
# Copying the lib from current macports:
copy_lib "/opt/local/lib/libgcc/libgcc_s.1.dylib" "" "" ""
copy_lib "/opt/local/lib/libgcc/libgcc_s.1.dylib" "" ""
"$TARGET_DIR/libstdc++.6.dylib"
copy_lib "/opt/local/lib/libgcc/libgomp.1.dylib" "" "" ""
# Copying the lib from an older bundle:
#copy_lib "/Applications/Rebelle.app/Contents/Frameworks/libgomp.1.dylib"
"" "/opt/local/lib/libgcc/libgomp.1.dylib" ""
# Copying the lib from current macports:
copy_lib "/opt/local/lib/libgcc/libgcc_s.1.dylib" "" ""
"$TARGET_DIR/libgomp.1.dylib"
IFS=$'\n'
for file_to_sign in `find "$BUNDLE_PATH/Contents" -name '*.dylib'`; do
echo "signing $file_to_sign"
# Note: in case of error about a headerpad, an older version of
the problematic library has to be activated in macports: sudo port
activate libgcc @5.2.0_0
codesign --verbose $sign_timestamp $sign_force -s "$APPCERT" -i
$BUNDLEID "$file_to_sign"
done
codesign $sign_timestamp -f -s "$APPCERT" -v --verbose "$BUNDLE_PATH"
echo "checking..."
echo
spctl -vvvvv --assess "$BUNDLE_PATH"
echo
codesign --verify --strict=symlinks --verbose=4 "$BUNDLE_PATH"
echo
codesign --display --strict=symlinks --verbose=4 "$BUNDLE_PATH"
echo
spctl -a -t exec -vvvv "$BUNDLE_PATH"
echo
echo "checking...done"
appname="${APP%.app}"
#rm "$appname.zip"
zip -r "$appname.zip" "$APP"
}}}
Let me know if you need any more info.
Michal
--
Ticket URL: <https://trac.macports.org/ticket/53567>
MacPorts <https://www.macports.org/>
Ports system for macOS
More information about the macports-tickets
mailing list