build_utm.sh 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. #!/bin/sh
  2. set -e
  3. command -v realpath >/dev/null 2>&1 || realpath() {
  4. [[ $1 = /* ]] && echo "$1" || echo "$PWD/${1#./}"
  5. }
  6. BASEDIR="$(dirname "$(realpath $0)")"
  7. usage () {
  8. echo "Usage: $(basename $0) [-t teamid] [-p platform] [-a architecture] [-t targetversion] [-o output]"
  9. echo ""
  10. echo " -t teamid Team Identifier for app groups. Optional for iOS. Required for macOS."
  11. echo " -p platform Target platform. Default ios. [ios|ios_simulator|ios-tci|ios_simulator-tci|macos|visionos|visionos_simulator]"
  12. echo " -a architecture Target architecture. Default arm64. [armv7|armv7s|arm64|i386|x86_64]"
  13. echo " -o output Output archive path. Default is current directory."
  14. echo ""
  15. exit 1
  16. }
  17. PRODUCT_BUNDLE_PREFIX="com.utmapp"
  18. TEAM_IDENTIFIER=
  19. ARCH=arm64
  20. PLATFORM=ios
  21. OUTPUT=$PWD
  22. SDK=
  23. SCHEME=
  24. while [ "x$1" != "x" ]; do
  25. case $1 in
  26. -t )
  27. TEAM_IDENTIFIER=$2
  28. shift
  29. ;;
  30. -a )
  31. ARCH=$2
  32. shift
  33. ;;
  34. -p )
  35. PLATFORM=$2
  36. shift
  37. ;;
  38. -o )
  39. OUTPUT=$2
  40. shift
  41. ;;
  42. * )
  43. usage
  44. ;;
  45. esac
  46. shift
  47. done
  48. case $PLATFORM in
  49. *-tci )
  50. SCHEME="iOS-TCI"
  51. ;;
  52. ios* | visionos* )
  53. SCHEME="iOS"
  54. ;;
  55. macos )
  56. SCHEME="macOS"
  57. ;;
  58. * )
  59. usage
  60. ;;
  61. esac
  62. case $PLATFORM in
  63. visionos_simulator* )
  64. SDK=xrsimulator
  65. ;;
  66. visionos* )
  67. SDK=xros
  68. ;;
  69. ios_simulator* )
  70. SDK=iphonesimulator
  71. ;;
  72. ios* )
  73. SDK=iphoneos
  74. ;;
  75. macos )
  76. SDK=macosx
  77. ;;
  78. * )
  79. usage
  80. ;;
  81. esac
  82. ARCH_ARGS=$(echo $ARCH | xargs printf -- "-arch %s ")
  83. if [ ! -z "$TEAM_IDENTIFIER" ]; then
  84. TEAM_IDENTIFIER_PREFIX="TeamIdentifierPrefix=${TEAM_IDENTIFIER}."
  85. fi
  86. xcodebuild archive -archivePath "$OUTPUT" -scheme "$SCHEME" -sdk "$SDK" $ARCH_ARGS -configuration Release CODE_SIGNING_ALLOWED=NO $TEAM_IDENTIFIER_PREFIX
  87. BUILT_PATH=$(find $OUTPUT.xcarchive -name '*.app' -type d | head -1)
  88. # Only retain the target architecture to address < iOS 15 crash & save disk space
  89. case $PLATFORM in
  90. ios | ios-tci )
  91. find "$BUILT_PATH" -type f -path '*/Frameworks/*.dylib' | while read FILE; do
  92. if [[ $(lipo -info "$FILE") =~ "Architectures in the fat file" ]]; then
  93. lipo -thin $ARCH "$FILE" -output "$FILE"
  94. fi
  95. done
  96. find "$BUILT_PATH" -type d -path '*/Frameworks/*.framework' | while read FRAMEWORK; do
  97. FILE="${FRAMEWORK}"/$(basename "${FRAMEWORK%.*}")
  98. if [[ $(lipo -info "$FILE") =~ "Architectures in the fat file" ]]; then
  99. lipo -thin $ARCH "$FILE" -output "$FILE"
  100. fi
  101. done
  102. ;;
  103. esac
  104. find "$BUILT_PATH" -type d -path '*/Frameworks/*.framework' -exec codesign --force --sign - --timestamp=none \{\} \;
  105. if [ "$PLATFORM" == "macos" ]; then
  106. # always build with vm entitlements, package_mac.sh can strip it later
  107. # this way we can import into Xcode and re-sign from there
  108. UTM_ENTITLEMENTS="/tmp/utm.$$.entitlements"
  109. LAUNCHER_ENTITLEMENTS="/tmp/launcher.$$.entitlements"
  110. HELPER_ENTITLEMENTS="/tmp/helper.$$.entitlements"
  111. CLI_ENTITLEMENTS="/tmp/cli.$$.entitlements"
  112. cp "$BASEDIR/../Platform/macOS/macOS.entitlements" "$UTM_ENTITLEMENTS"
  113. cp "$BASEDIR/../QEMULauncher/QEMULauncher.entitlements" "$LAUNCHER_ENTITLEMENTS"
  114. cp "$BASEDIR/../QEMUHelper/QEMUHelper.entitlements" "$HELPER_ENTITLEMENTS"
  115. cp "$BASEDIR/../utmctl/utmctl.entitlements" "$CLI_ENTITLEMENTS"
  116. if [ ! -z "$TEAM_IDENTIFIER" ]; then
  117. TEAM_ID_PREFIX="${TEAM_IDENTIFIER}."
  118. fi
  119. /usr/libexec/PlistBuddy -c "Set :com.apple.security.application-groups:0 ${TEAM_ID_PREFIX}${PRODUCT_BUNDLE_PREFIX}.UTM" "$UTM_ENTITLEMENTS"
  120. /usr/libexec/PlistBuddy -c "Set :com.apple.security.application-groups:0 ${TEAM_ID_PREFIX}${PRODUCT_BUNDLE_PREFIX}.UTM" "$HELPER_ENTITLEMENTS"
  121. /usr/libexec/PlistBuddy -c "Set :com.apple.security.application-groups:0 ${TEAM_ID_PREFIX}${PRODUCT_BUNDLE_PREFIX}.UTM" "$CLI_ENTITLEMENTS"
  122. codesign --force --sign - --entitlements "$LAUNCHER_ENTITLEMENTS" --timestamp=none --options runtime "$BUILT_PATH/Contents/XPCServices/QEMUHelper.xpc/Contents/MacOS/QEMULauncher.app/Contents/MacOS/QEMULauncher"
  123. codesign --force --sign - --entitlements "$HELPER_ENTITLEMENTS" --timestamp=none --options runtime "$BUILT_PATH/Contents/XPCServices/QEMUHelper.xpc/Contents/MacOS/QEMUHelper"
  124. codesign --force --sign - --entitlements "$CLI_ENTITLEMENTS" --timestamp=none --options runtime "$BUILT_PATH/Contents/MacOS/utmctl"
  125. codesign --force --sign - --entitlements "$UTM_ENTITLEMENTS" --timestamp=none --options runtime "$BUILT_PATH/Contents/MacOS/UTM"
  126. rm "$UTM_ENTITLEMENTS"
  127. rm "$LAUNCHER_ENTITLEMENTS"
  128. rm "$HELPER_ENTITLEMENTS"
  129. rm "$CLI_ENTITLEMENTS"
  130. else
  131. # always build with iOS entitlements, package.sh can strip it later
  132. codesign --force --sign - --entitlements "$BASEDIR/../Platform/iOS/iOS.entitlements" --timestamp=none "$BUILT_PATH"
  133. fi