xref: /aosp_15_r20/external/protobuf/objectivec/DevTools/full_mac_build.sh (revision 1b3f573f81763fcece89efc2b6a5209149e44ab8)
1#!/bin/bash
2#
3# Helper to do build so you don't have to remember all the steps/args.
4
5
6set -eu
7
8# Some base locations.
9readonly ScriptDir=$(dirname "$(echo $0 | sed -e "s,^\([^/]\),$(pwd)/\1,")")
10readonly ProtoRootDir="${ScriptDir}/../.."
11
12printUsage() {
13  NAME=$(basename "${0}")
14  cat << EOF
15usage: ${NAME} [OPTIONS]
16
17This script does the common build steps needed.
18
19OPTIONS:
20
21 General:
22
23   -h, --help
24         Show this message
25   -c, --clean
26         Issue a clean before the normal build.
27   -a, --autogen
28         Start by rerunning autogen & configure.
29   -r, --regenerate-descriptors
30         Run generate_descriptor_proto.sh to regenerate all the checked in
31         proto sources.
32   -j #, --jobs #
33         Force the number of parallel jobs (useful for debugging build issues).
34   --core-only
35         Skip some of the core protobuf build/checks to shorten the build time.
36   --skip-xcode
37         Skip the invoke of Xcode to test the runtime on both iOS and OS X.
38   --skip-xcode-ios
39         Skip the invoke of Xcode to test the runtime on iOS.
40   --skip-xcode-debug
41         Skip the Xcode Debug configuration.
42   --skip-xcode-release
43         Skip the Xcode Release configuration.
44   --skip-xcode-osx | --skip-xcode-macos
45         Skip the invoke of Xcode to test the runtime on OS X.
46   --skip-xcode-tvos
47         Skip the invoke of Xcode to test the runtime on tvOS.
48   --skip-objc-conformance
49         Skip the Objective C conformance tests (run on OS X).
50   --xcode-quiet
51         Pass -quiet to xcodebuild.
52
53EOF
54}
55
56header() {
57  echo ""
58  echo "========================================================================"
59  echo "    ${@}"
60  echo "========================================================================"
61}
62
63# Thanks to libtool, builds can fail in odd ways and since it eats some output
64# it can be hard to spot, so force error output if make exits with a non zero.
65wrapped_make() {
66  set +e  # Don't stop if the command fails.
67  make $*
68  MAKE_EXIT_STATUS=$?
69  if [ ${MAKE_EXIT_STATUS} -ne 0 ]; then
70    echo "Error: 'make $*' exited with status ${MAKE_EXIT_STATUS}"
71    exit ${MAKE_EXIT_STATUS}
72  fi
73  set -e
74}
75
76NUM_MAKE_JOBS=$(/usr/sbin/sysctl -n hw.ncpu)
77if [[ "${NUM_MAKE_JOBS}" -lt 2 ]] ; then
78  NUM_MAKE_JOBS=2
79fi
80
81DO_AUTOGEN=no
82DO_CLEAN=no
83REGEN_DESCRIPTORS=no
84CORE_ONLY=no
85DO_XCODE_IOS_TESTS=yes
86DO_XCODE_OSX_TESTS=yes
87DO_XCODE_TVOS_TESTS=yes
88DO_XCODE_DEBUG=yes
89DO_XCODE_RELEASE=yes
90DO_OBJC_CONFORMANCE_TESTS=yes
91XCODE_QUIET=no
92while [[ $# != 0 ]]; do
93  case "${1}" in
94    -h | --help )
95      printUsage
96      exit 0
97      ;;
98    -c | --clean )
99      DO_CLEAN=yes
100      ;;
101    -a | --autogen )
102      DO_AUTOGEN=yes
103      ;;
104    -r | --regenerate-descriptors )
105      REGEN_DESCRIPTORS=yes
106      ;;
107    -j | --jobs )
108      shift
109      NUM_MAKE_JOBS="${1}"
110      ;;
111    --core-only )
112      CORE_ONLY=yes
113      ;;
114    --skip-xcode )
115      DO_XCODE_IOS_TESTS=no
116      DO_XCODE_OSX_TESTS=no
117      DO_XCODE_TVOS_TESTS=no
118      ;;
119    --skip-xcode-ios )
120      DO_XCODE_IOS_TESTS=no
121      ;;
122    --skip-xcode-osx | --skip-xcode-macos)
123      DO_XCODE_OSX_TESTS=no
124      ;;
125    --skip-xcode-tvos )
126      DO_XCODE_TVOS_TESTS=no
127      ;;
128    --skip-xcode-debug )
129      DO_XCODE_DEBUG=no
130      ;;
131    --skip-xcode-release )
132      DO_XCODE_RELEASE=no
133      ;;
134    --skip-objc-conformance )
135      DO_OBJC_CONFORMANCE_TESTS=no
136      ;;
137    --xcode-quiet )
138      XCODE_QUIET=yes
139      ;;
140    -*)
141      echo "ERROR: Unknown option: ${1}" 1>&2
142      printUsage
143      exit 1
144      ;;
145    *)
146      echo "ERROR: Unknown argument: ${1}" 1>&2
147      printUsage
148      exit 1
149      ;;
150  esac
151  shift
152done
153
154# Into the proto dir.
155cd "${ProtoRootDir}"
156
157# if no Makefile, force the autogen.
158if [[ ! -f Makefile ]] ; then
159  DO_AUTOGEN=yes
160fi
161
162if [[ "${DO_AUTOGEN}" == "yes" ]] ; then
163  header "Running autogen & configure"
164  ./autogen.sh
165  ./configure \
166    CPPFLAGS="-mmacosx-version-min=10.9 -Wunused-const-variable -Wunused-function"
167fi
168
169if [[ "${DO_CLEAN}" == "yes" ]] ; then
170  header "Cleaning"
171  wrapped_make clean
172  if [[ "${DO_XCODE_IOS_TESTS}" == "yes" ]] ; then
173    XCODEBUILD_CLEAN_BASE_IOS=(
174      xcodebuild
175        -project objectivec/ProtocolBuffers_iOS.xcodeproj
176        -scheme ProtocolBuffers
177    )
178    if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
179      "${XCODEBUILD_CLEAN_BASE_IOS[@]}" -configuration Debug clean
180    fi
181    if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
182      "${XCODEBUILD_CLEAN_BASE_IOS[@]}" -configuration Release clean
183    fi
184  fi
185  if [[ "${DO_XCODE_OSX_TESTS}" == "yes" ]] ; then
186    XCODEBUILD_CLEAN_BASE_OSX=(
187      xcodebuild
188        -project objectivec/ProtocolBuffers_OSX.xcodeproj
189        -scheme ProtocolBuffers
190    )
191    if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
192      "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Debug clean
193    fi
194    if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
195      "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Release clean
196    fi
197  fi
198  if [[ "${DO_XCODE_TVOS_TESTS}" == "yes" ]] ; then
199    XCODEBUILD_CLEAN_BASE_OSX=(
200      xcodebuild
201        -project objectivec/ProtocolBuffers_tvOS.xcodeproj
202        -scheme ProtocolBuffers
203    )
204    if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
205      "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Debug clean
206    fi
207    if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
208      "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Release clean
209    fi
210  fi
211fi
212
213if [[ "${REGEN_DESCRIPTORS}" == "yes" ]] ; then
214  header "Regenerating the descriptor sources."
215  ./generate_descriptor_proto.sh -j "${NUM_MAKE_JOBS}"
216fi
217
218if [[ "${CORE_ONLY}" == "yes" ]] ; then
219  header "Building core Only"
220  wrapped_make -j "${NUM_MAKE_JOBS}"
221else
222  header "Building"
223  # Can't issue these together, when fully parallel, something sometimes chokes
224  # at random.
225  wrapped_make -j "${NUM_MAKE_JOBS}" all
226  wrapped_make -j "${NUM_MAKE_JOBS}" check
227  # Fire off the conformance tests also.
228  cd conformance
229  wrapped_make -j "${NUM_MAKE_JOBS}" test_cpp
230  cd ..
231fi
232
233# Ensure the WKT sources checked in are current.
234objectivec/generate_well_known_types.sh --check-only -j "${NUM_MAKE_JOBS}"
235
236header "Checking on the ObjC Runtime Code"
237# Some of the kokoro machines don't have python3 yet, so fall back to python if need be.
238if hash python3 >/dev/null 2>&1 ; then
239  LOCAL_PYTHON=python3
240else
241  LOCAL_PYTHON=python
242fi
243"${LOCAL_PYTHON}" objectivec/DevTools/pddm_tests.py
244if ! "${LOCAL_PYTHON}" objectivec/DevTools/pddm.py --dry-run objectivec/*.[hm] objectivec/Tests/*.[hm] ; then
245  echo ""
246  echo "Update by running:"
247  echo "   objectivec/DevTools/pddm.py objectivec/*.[hm] objectivec/Tests/*.[hm]"
248  exit 1
249fi
250
251readonly XCODE_VERSION_LINE="$(xcodebuild -version | grep Xcode\  )"
252readonly XCODE_VERSION="${XCODE_VERSION_LINE/Xcode /}"  # drop the prefix.
253
254if [[ "${DO_XCODE_IOS_TESTS}" == "yes" ]] ; then
255  XCODEBUILD_TEST_BASE_IOS=(
256    xcodebuild
257      -project objectivec/ProtocolBuffers_iOS.xcodeproj
258      -scheme ProtocolBuffers
259  )
260  if [[ "${XCODE_QUIET}" == "yes" ]] ; then
261    XCODEBUILD_TEST_BASE_IOS+=( -quiet )
262  fi
263  # Don't need to worry about form factors or retina/non retina;
264  # just pick a mix of OS Versions and 32/64 bit.
265  # NOTE: Different Xcode have different simulated hardware/os support.
266  case "${XCODE_VERSION}" in
267    [6-8].* )
268      echo "ERROR: The unittests include Swift code that is now Swift 4.0." 1>&2
269      echo "ERROR: Xcode 9.0 or higher is required to build the test suite, but the library works with Xcode 7.x." 1>&2
270      exit 11
271      ;;
272    9.[0-2]* )
273      XCODEBUILD_TEST_BASE_IOS+=(
274          -destination "platform=iOS Simulator,name=iPhone 4s,OS=8.1" # 32bit
275          -destination "platform=iOS Simulator,name=iPhone 7,OS=latest" # 64bit
276          # 9.0-9.2 all seem to often fail running destinations in parallel
277          -disable-concurrent-testing
278      )
279      ;;
280    9.[3-4]* )
281      XCODEBUILD_TEST_BASE_IOS+=(
282          # Xcode 9.3 chokes targeting iOS 8.x - http://www.openradar.me/39335367
283          -destination "platform=iOS Simulator,name=iPhone 4s,OS=9.0" # 32bit
284          -destination "platform=iOS Simulator,name=iPhone 7,OS=latest" # 64bit
285          # 9.3 also seems to often fail running destinations in parallel
286          -disable-concurrent-testing
287      )
288      ;;
289    10.*)
290      XCODEBUILD_TEST_BASE_IOS+=(
291          -destination "platform=iOS Simulator,name=iPhone 4s,OS=8.1" # 32bit
292          -destination "platform=iOS Simulator,name=iPhone 7,OS=latest" # 64bit
293          # 10.x also seems to often fail running destinations in parallel (with
294          # 32bit one include at least)
295          -disable-concurrent-destination-testing
296      )
297      ;;
298    11.* | 12.* | 13.* | 14.*)
299      # Dropped 32bit as Apple doesn't seem support the simulators either.
300      XCODEBUILD_TEST_BASE_IOS+=(
301          -destination "platform=iOS Simulator,name=iPhone 8,OS=latest" # 64bit
302      )
303      ;;
304    * )
305      echo ""
306      echo "ATTENTION: Time to update the simulator targets for Xcode ${XCODE_VERSION}"
307      echo ""
308      echo "ERROR: Build aborted!"
309      exit 2
310      ;;
311  esac
312  if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
313    header "Doing Xcode iOS build/tests - Debug"
314    "${XCODEBUILD_TEST_BASE_IOS[@]}" -configuration Debug test
315  fi
316  if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
317    header "Doing Xcode iOS build/tests - Release"
318    "${XCODEBUILD_TEST_BASE_IOS[@]}" -configuration Release test
319  fi
320  # Don't leave the simulator in the developer's face.
321  killall Simulator 2> /dev/null || true
322fi
323if [[ "${DO_XCODE_OSX_TESTS}" == "yes" ]] ; then
324  XCODEBUILD_TEST_BASE_OSX=(
325    xcodebuild
326      -project objectivec/ProtocolBuffers_OSX.xcodeproj
327      -scheme ProtocolBuffers
328      # Since the ObjC 2.0 Runtime is required, 32bit OS X isn't supported.
329      -destination "platform=OS X,arch=x86_64" # 64bit
330  )
331  if [[ "${XCODE_QUIET}" == "yes" ]] ; then
332    XCODEBUILD_TEST_BASE_OSX+=( -quiet )
333  fi
334  case "${XCODE_VERSION}" in
335    [6-8].* )
336      echo "ERROR: The unittests include Swift code that is now Swift 4.0." 1>&2
337      echo "ERROR: Xcode 9.0 or higher is required to build the test suite, but the library works with Xcode 7.x." 1>&2
338      exit 11
339      ;;
340  esac
341  if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
342    header "Doing Xcode OS X build/tests - Debug"
343    "${XCODEBUILD_TEST_BASE_OSX[@]}" -configuration Debug test
344  fi
345  if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
346    header "Doing Xcode OS X build/tests - Release"
347    "${XCODEBUILD_TEST_BASE_OSX[@]}" -configuration Release test
348  fi
349fi
350if [[ "${DO_XCODE_TVOS_TESTS}" == "yes" ]] ; then
351  XCODEBUILD_TEST_BASE_TVOS=(
352    xcodebuild
353      -project objectivec/ProtocolBuffers_tvOS.xcodeproj
354      -scheme ProtocolBuffers
355  )
356  case "${XCODE_VERSION}" in
357    [6-9].* )
358      echo "ERROR: Xcode 10.0 or higher is required to build the test suite." 1>&2
359      exit 11
360      ;;
361    10.* | 11.* | 12.*)
362      XCODEBUILD_TEST_BASE_TVOS+=(
363        -destination "platform=tvOS Simulator,name=Apple TV 4K,OS=latest"
364      )
365      ;;
366    13.* | 14.*)
367      XCODEBUILD_TEST_BASE_TVOS+=(
368        -destination "platform=tvOS Simulator,name=Apple TV 4K (2nd generation),OS=latest"
369      )
370      ;;
371    * )
372      echo ""
373      echo "ATTENTION: Time to update the simulator targets for Xcode ${XCODE_VERSION}"
374      echo ""
375      echo "ERROR: Build aborted!"
376      exit 2
377      ;;
378  esac
379  if [[ "${XCODE_QUIET}" == "yes" ]] ; then
380    XCODEBUILD_TEST_BASE_TVOS+=( -quiet )
381  fi
382  if [[ "${DO_XCODE_DEBUG}" == "yes" ]] ; then
383    header "Doing Xcode tvOS build/tests - Debug"
384    "${XCODEBUILD_TEST_BASE_TVOS[@]}" -configuration Debug test
385  fi
386  if [[ "${DO_XCODE_RELEASE}" == "yes" ]] ; then
387    header "Doing Xcode tvOS build/tests - Release"
388    "${XCODEBUILD_TEST_BASE_TVOS[@]}" -configuration Release test
389  fi
390fi
391
392if [[ "${DO_OBJC_CONFORMANCE_TESTS}" == "yes" ]] ; then
393  header "Running ObjC Conformance Tests"
394  cd conformance
395  wrapped_make -j "${NUM_MAKE_JOBS}" test_objc
396  cd ..
397fi
398
399echo ""
400echo "$(basename "${0}"): Success!"
401