#!/bin/bash # Build the macOS installer for the tokend and command line tools. # # This is only tested and supported on macOS 10.10 or later, using Xcode 6.0.1. # Building should also work on older macOS versions with slight changes; YMMV. # You need to install the following packages from homebrew or macports or fink: # autoconf automake libtool pkg-config help2man gengetopt export MACOSX_DEPLOYMENT_TARGET="10.10" set -ex test -x ./configure || ./bootstrap BUILDPATH=${PWD} xcode_ver=$(xcodebuild -version | sed -En 's/Xcode[[:space:]](.*)/\1/p') base_ver="12.2" if [ $(echo -e $base_ver"\n"$xcode_ver | sort -V | head -1) == "$base_ver" ]; then export BUILD_ARM="true" fi export SED=/usr/bin/sed PREFIX=/Library/OpenSC export PKG_CONFIG_PATH=$PKG_CONFIG_PATH:/usr/lib/pkgconfig if ! pkg-config libcrypto --atleast-version=1.0.1; then # OpenSSL is not installed if ! test -e $BUILDPATH/openssl_bin/$PREFIX/lib/pkgconfig; then # Build OpenSSL manually, because Apple's binaries are deprecated if ! test -e openssl; then git clone --depth=1 https://github.com/openssl/openssl.git -b OpenSSL_1_1_1-stable fi cd openssl MACHINE=x86_64 ./config no-shared --prefix=$PREFIX make clean make -j 4 make DESTDIR=$BUILDPATH/openssl_bin install_sw if test -n "${BUILD_ARM}"; then make clean MACHINE=arm64 KERNEL_BITS=64 ./config no-shared --prefix=$PREFIX make -j 4 make DESTDIR=$BUILDPATH/openssl_arm64 install_sw lipo -create $BUILDPATH/openssl_arm64/$PREFIX/lib/libcrypto.a $BUILDPATH/openssl_bin/$PREFIX/lib/libcrypto.a -output libcrypto.a lipo -create $BUILDPATH/openssl_arm64/$PREFIX/lib/libssl.a $BUILDPATH/openssl_bin/$PREFIX/lib/libssl.a -output libssl.a mv libcrypto.a $BUILDPATH/openssl_bin/$PREFIX/lib/libcrypto.a mv libssl.a $BUILDPATH/openssl_bin/$PREFIX/lib/libssl.a fi cd .. fi export OPENSSL_CFLAGS="`env PKG_CONFIG_PATH=$BUILDPATH/openssl_bin/$PREFIX/lib/pkgconfig PKG_CONFIG_SYSROOT_DIR=$BUILDPATH/openssl_bin pkg-config --static --cflags libcrypto`" export OPENSSL_LIBS="` env PKG_CONFIG_PATH=$BUILDPATH/openssl_bin/$PREFIX/lib/pkgconfig PKG_CONFIG_SYSROOT_DIR=$BUILDPATH/openssl_bin pkg-config --static --libs libcrypto`" fi # Locate the latest OSX SDK SDK_PATH=$(xcrun --sdk macosx --show-sdk-path) export CFLAGS="$CFLAGS -isysroot $SDK_PATH" if test -n "${BUILD_ARM}"; then export CFLAGS="$CFLAGS -arch x86_64 -arch arm64" export LDFLAGS="$LDFLAGS -arch x86_64 -arch arm64" fi export OBJCFLAGS=$CFLAGS if ! test -e $BUILDPATH/openpace_bin/$PREFIX/lib/pkgconfig; then if ! test -e openpace; then git clone --depth=1 https://github.com/frankmorgner/openpace.git -b 1.1.1 fi cd openpace autoreconf -vis ./configure --disable-shared --prefix=$PREFIX CRYPTO_CFLAGS="$OPENSSL_CFLAGS" CRYPTO_LIBS="$OPENSSL_LIBS" HELP2MAN=/usr/bin/true touch src/cvc-create.1 src/cvc-print.1 make DESTDIR=$BUILDPATH/openpace_bin install cd .. fi export OPENPACE_CFLAGS="`env PKG_CONFIG_PATH=$BUILDPATH/openssl_bin/$PREFIX/lib/pkgconfig:$BUILDPATH/openpace_bin/$PREFIX/lib/pkgconfig PKG_CONFIG_SYSROOT_DIR=$BUILDPATH/openpace_bin pkg-config --static --cflags libeac` $OPENSSL_CFLAGS" export OPENPACE_LIBS="` env PKG_CONFIG_PATH=$BUILDPATH/openssl_bin/$PREFIX/lib/pkgconfig:$BUILDPATH/openpace_bin/$PREFIX/lib/pkgconfig PKG_CONFIG_SYSROOT_DIR=$BUILDPATH/openpace_bin pkg-config --static --libs libeac` $OPENSSL_LIBS" if ! test -e ${BUILDPATH}/target/$PREFIX/lib/pkgconfig; then ./configure --prefix=$PREFIX \ --sysconfdir=$PREFIX/etc \ --enable-cvcdir=$PREFIX/etc/cvc \ --enable-x509dir=$PREFIX/etc/x509 \ --enable-openssl-secure-malloc=65536 \ --disable-dependency-tracking \ --enable-shared \ --enable-static \ --enable-strict \ --disable-assert \ --enable-sm # TODO: remove this (must be sensible default in master) # always make clean make clean # compile make -j 4 # copy files rm -rf ${BUILDPATH}/target make install DESTDIR=${BUILDPATH}/target # remove garbage rm -f ${BUILDPATH}/target/$PREFIX/lib/*.la rm -f ${BUILDPATH}/target/$PREFIX/lib/*.a # generate .bundle (required by Adobe Acrobat) ./MacOSX/libtool-bundle ${BUILDPATH}/target/$PREFIX/lib/opensc-pkcs11.so ${BUILDPATH}/target/$PREFIX/lib fi if ! test -e NotificationProxy; then git clone http://github.com/frankmorgner/NotificationProxy.git fi if test -n "${CODE_SIGN_IDENTITY}" -a -n "${DEVELOPMENT_TEAM}"; then xcodebuild -target NotificationProxy -configuration Release -project NotificationProxy/NotificationProxy.xcodeproj install DSTROOT=$BUILDPATH/target/Library/OpenSC/ \ CODE_SIGN_IDENTITY="${CODE_SIGN_IDENTITY}" DEVELOPMENT_TEAM="${DEVELOPMENT_TEAM}" OTHER_CODE_SIGN_FLAGS="--timestamp --options=runtime" CODE_SIGN_INJECT_BASE_ENTITLEMENTS=NO CODE_SIGN_STYLE=Manual else xcodebuild -target NotificationProxy -configuration Release -project NotificationProxy/NotificationProxy.xcodeproj install DSTROOT=$BUILDPATH/target/Library/OpenSC/ fi mkdir -p "$BUILDPATH/target/Applications/Utilities" osacompile -o "$BUILDPATH/target/Applications/Utilities/OpenSC Notify.app" "MacOSX/OpenSC_Notify.applescript" if test -n "${CODE_SIGN_IDENTITY}"; then codesign --force --sign "${CODE_SIGN_IDENTITY}" --entitlements MacOSX/OpenSC_applescripts.entitlements --deep --timestamp --options runtime "$BUILDPATH/target/Applications/Utilities/OpenSC Notify.app" fi # Build OpenSC.tokend when XCode version < 10 if (( $(xcodebuild -version | sed -En 's/Xcode[[:space:]]+([0-9]+)(\.[0-9]*)*/\1/p') < 10 )); then # Check out OpenSC.tokend, if not already fetched. if ! test -e OpenSC.tokend; then git clone http://github.com/OpenSC/OpenSC.tokend.git fi # Create the symlink to OpenSC sources test -L OpenSC.tokend/build/opensc-src || ln -sf ${BUILDPATH}/src OpenSC.tokend/build/opensc-src # Build and copy OpenSC.tokend if test -n "${CODE_SIGN_IDENTITY}" -a -n "${DEVELOPMENT_TEAM}"; then xcodebuild -target OpenSC -configuration Deployment -project OpenSC.tokend/Tokend.xcodeproj install DSTROOT=${BUILDPATH}/target_tokend \ CODE_SIGN_IDENTITY="${CODE_SIGN_IDENTITY}" DEVELOPMENT_TEAM="${DEVELOPMENT_TEAM}" OTHER_CODE_SIGN_FLAGS="--timestamp --options=runtime" CODE_SIGN_INJECT_BASE_ENTITLEMENTS=NO CODE_SIGN_STYLE=Manual else xcodebuild -target OpenSC -configuration Deployment -project OpenSC.tokend/Tokend.xcodeproj install DSTROOT=${BUILDPATH}/target_tokend fi TOKEND="-tokend" else # https://github.com/OpenSC/OpenSC.tokend/issues/33 mkdir -p ${BUILDPATH}/target_tokend TOKEND="" fi #if ! test -e $BUILDPATH/target/Library/Security/tokend/OpenSC.tokend/Contents/Resources/Applications/terminal-notifier.app; then #if ! test -e terminal-notifier-1.7.1.zip; then #curl -L https://github.com/julienXX/terminal-notifier/releases/download/1.7.1/terminal-notifier-1.7.1.zip > terminal-notifier-1.7.1.zip #fi #if ! test -e terminal-notifier-1.7.1; then #unzip terminal-notifier-1.7.1.zip #fi #mkdir -p $BUILDPATH/target/Library/Security/tokend/OpenSC.tokend/Contents/Resources/Applications #cp -r terminal-notifier-1.7.1/terminal-notifier.app $BUILDPATH/target/Library/Security/tokend/OpenSC.tokend/Contents/Resources/Applications #fi imagedir=$(mktemp -d) # Prepare target root mkdir -p ${BUILDPATH}/target/usr/local/bin cp MacOSX/opensc-uninstall ${BUILDPATH}/target/usr/local/bin # Prepare startup root mkdir -p ${BUILDPATH}/target_startup/Library/LaunchAgents cp src/tools/org.opensc-project.mac.pkcs11-register.plist ${BUILDPATH}/target_startup/Library/LaunchAgents cp src/tools/org.opensc-project.mac.opensc-notify.plist ${BUILDPATH}/target_startup/Library/LaunchAgents # Build OpenSCToken if possible if test -e OpenSCToken -a -n "${CODE_SIGN_IDENTITY}" -a -n "${DEVELOPMENT_TEAM}"; then cd OpenSCToken # make sure OpenSCToken builds with the same dependencies as before if ! test -e OpenSC; then git clone --depth=1 file://$PWD/../../OpenSC else cd OpenSC && git pull && cd .. fi mkdir -p build if ! test -e build/openssl; then # build/openssl/lib/libcrypto.a is hardcoded in OpenSCToken ln -sf $BUILDPATH/openssl_bin/$PREFIX build/openssl # in OpenSCToken's variant of OpenSC we still use OpenSSL flags from above fi if ! test -e build/openpace; then # build/openpace/lib/libeac.a is hardcoded in OpenSCToken ln -sf $BUILDPATH/openpace_bin/$PREFIX build/openpace # in OpenSCToken's variant of OpenSC we still use OpenPACE flags from above fi BP=${BUILDPATH} . ./bootstrap BUILDPATH=${BP} xcodebuild -target OpenSCTokenApp -configuration Debug -project OpenSCTokenApp.xcodeproj install DSTROOT=${BUILDPATH}/target_token \ CODE_SIGN_IDENTITY="${CODE_SIGN_IDENTITY}" DEVELOPMENT_TEAM="${DEVELOPMENT_TEAM}" OTHER_CODE_SIGN_FLAGS="--timestamp --options=runtime" CODE_SIGN_INJECT_BASE_ENTITLEMENTS=NO CODE_SIGN_STYLE=Manual cd .. COMPONENT_TOKEN="--component-plist MacOSX/target_token.plist" else # if no OpenSCToken is checked out, then we create a dummy package mkdir -p ${BUILDPATH}/target_token fi if test -n "${CODE_SIGN_IDENTITY}"; then for d in ${BUILDPATH}/target/Library/OpenSC/bin ${BUILDPATH}/target/Library/OpenSC/lib do # find executable files and run codesign on them find ${d} -type f -perm +111 -print -exec \ codesign --force --sign "${CODE_SIGN_IDENTITY}" --entitlements MacOSX/OpenSC_binaries.entitlements --deep --timestamp --options runtime {} \; done fi # Build package pkgbuild --root ${BUILDPATH}/target --component-plist MacOSX/target.plist --scripts MacOSX/scripts --identifier org.opensc-project.mac --version @PACKAGE_VERSION@ --install-location / OpenSC.pkg pkgbuild --root ${BUILDPATH}/target_tokend --component-plist MacOSX/target_tokend.plist --identifier org.opensc-project.tokend --version @PACKAGE_VERSION@ --install-location / OpenSC-tokend.pkg pkgbuild --root ${BUILDPATH}/target_token $COMPONENT_TOKEN --identifier org.opensc-project.mac.opensctoken --version @PACKAGE_VERSION@ --install-location / OpenSCToken.pkg pkgbuild --root ${BUILDPATH}/target_startup --component-plist MacOSX/target_startup.plist --identifier org.opensc-project.startup --version @PACKAGE_VERSION@ --install-location / OpenSC-startup.pkg # Build product productbuild --distribution MacOSX/Distribution.xml --package-path . --resources MacOSX/resources "${imagedir}/OpenSC @PACKAGE_VERSION@.pkg" # Sign installer if test -n "${INSTALLER_SIGN_IDENTITY}"; then productsign --sign "${INSTALLER_SIGN_IDENTITY}" "${imagedir}/OpenSC @PACKAGE_VERSION@.pkg" "${BUILDPATH}/OpenSC @PACKAGE_VERSION@.pkg" mv "${BUILDPATH}/OpenSC @PACKAGE_VERSION@.pkg" "${imagedir}/OpenSC @PACKAGE_VERSION@.pkg" fi # Build "Uninstaller" osacompile -o "${imagedir}/OpenSC Uninstaller.app" "MacOSX/OpenSC_Uninstaller.applescript" if test -n "${CODE_SIGN_IDENTITY}"; then codesign --force --sign "${CODE_SIGN_IDENTITY}" --entitlements MacOSX/OpenSC_applescripts.entitlements --deep --timestamp --options runtime "${imagedir}/OpenSC Uninstaller.app" fi # Create .dmg rm -f OpenSC-@PACKAGE_VERSION@$TOKEND.dmg i=0 while ! hdiutil create -srcfolder "${imagedir}" -volname "@PACKAGE_NAME@" -fs JHFS+ OpenSC-@PACKAGE_VERSION@$TOKEND.dmg do i=$[$i+1] if [ $i -gt 2 ] then exit 1 fi done rm -rf ${imagedir} #if [ "$TRAVIS_EVENT_TYPE" != "pull_request" ]; then xcrun altool --notarize-app --file $(pwd)/vorteil_darwin-x86.dmg --username $OSX_NOTARIZE_USERNAME --primary-bundle-id com.vorteil.cli -p $OSX_NOTARIZE_PW -- >> /dev/null; fi; #if [ "$TRAVIS_EVENT_TYPE" != "pull_request" ]; then for ((i=1;i<=30;i+=1)); do xcrun stapler staple $(pwd)/vorteil_darwin-x86.dmg >> /dev/null; if [ $? = 65 ]; then echo "Waiting for notarization to complete..." && sleep 10; fi; done; fi;