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-osx 41 Skip the invoke of Xcode to test the runtime on OS X. 42 --skip-objc-conformance 43 Skip the Objective C conformance tests (run on OS X). 44 45EOF 46} 47 48header() { 49 echo "" 50 echo "========================================================================" 51 echo " ${@}" 52 echo "========================================================================" 53} 54 55# Thanks to libtool, builds can fail in odd ways and since it eats some output 56# it can be hard to spot, so force error output if make exits with a non zero. 57wrapped_make() { 58 set +e # Don't stop if the command fails. 59 make $* 60 MAKE_EXIT_STATUS=$? 61 if [ ${MAKE_EXIT_STATUS} -ne 0 ]; then 62 echo "Error: 'make $*' exited with status ${MAKE_EXIT_STATUS}" 63 exit ${MAKE_EXIT_STATUS} 64 fi 65 set -e 66} 67 68NUM_MAKE_JOBS=$(/usr/sbin/sysctl -n hw.ncpu) 69if [[ "${NUM_MAKE_JOBS}" -lt 4 ]] ; then 70 NUM_MAKE_JOBS=4 71fi 72 73DO_AUTOGEN=no 74DO_CLEAN=no 75REGEN_DESCRIPTORS=no 76CORE_ONLY=no 77DO_XCODE_IOS_TESTS=yes 78DO_XCODE_OSX_TESTS=yes 79DO_OBJC_CONFORMANCE_TESTS=yes 80while [[ $# != 0 ]]; do 81 case "${1}" in 82 -h | --help ) 83 printUsage 84 exit 0 85 ;; 86 -c | --clean ) 87 DO_CLEAN=yes 88 ;; 89 -a | --autogen ) 90 DO_AUTOGEN=yes 91 ;; 92 -r | --regenerate-descriptors ) 93 REGEN_DESCRIPTORS=yes 94 ;; 95 -j | --jobs ) 96 shift 97 NUM_MAKE_JOBS="${1}" 98 ;; 99 --core-only ) 100 CORE_ONLY=yes 101 ;; 102 --skip-xcode ) 103 DO_XCODE_IOS_TESTS=no 104 DO_XCODE_OSX_TESTS=no 105 ;; 106 --skip-xcode-ios ) 107 DO_XCODE_IOS_TESTS=no 108 ;; 109 --skip-xcode-osx ) 110 DO_XCODE_OSX_TESTS=no 111 ;; 112 --skip-objc-conformance ) 113 DO_OBJC_CONFORMANCE_TESTS=no 114 ;; 115 -*) 116 echo "ERROR: Unknown option: ${1}" 1>&2 117 printUsage 118 exit 1 119 ;; 120 *) 121 echo "ERROR: Unknown argument: ${1}" 1>&2 122 printUsage 123 exit 1 124 ;; 125 esac 126 shift 127done 128 129# Into the proto dir. 130cd "${ProtoRootDir}" 131 132# if no Makefile, force the autogen. 133if [[ ! -f Makefile ]] ; then 134 DO_AUTOGEN=yes 135fi 136 137if [[ "${DO_AUTOGEN}" == "yes" ]] ; then 138 header "Running autogen & configure" 139 ./autogen.sh 140 ./configure \ 141 CPPFLAGS="-mmacosx-version-min=10.9 -Wunused-const-variable -Wunused-function" \ 142 CXXFLAGS="-Wnon-virtual-dtor -Woverloaded-virtual" 143fi 144 145if [[ "${DO_CLEAN}" == "yes" ]] ; then 146 header "Cleaning" 147 wrapped_make clean 148 if [[ "${DO_XCODE_IOS_TESTS}" == "yes" ]] ; then 149 XCODEBUILD_CLEAN_BASE_IOS=( 150 xcodebuild 151 -project objectivec/ProtocolBuffers_iOS.xcodeproj 152 -scheme ProtocolBuffers 153 ) 154 "${XCODEBUILD_CLEAN_BASE_IOS[@]}" -configuration Debug clean 155 "${XCODEBUILD_CLEAN_BASE_IOS[@]}" -configuration Release clean 156 fi 157 if [[ "${DO_XCODE_OSX_TESTS}" == "yes" ]] ; then 158 XCODEBUILD_CLEAN_BASE_OSX=( 159 xcodebuild 160 -project objectivec/ProtocolBuffers_OSX.xcodeproj 161 -scheme ProtocolBuffers 162 ) 163 "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Debug clean 164 "${XCODEBUILD_CLEAN_BASE_OSX[@]}" -configuration Release clean 165 fi 166fi 167 168if [[ "${REGEN_DESCRIPTORS}" == "yes" ]] ; then 169 header "Regenerating the descriptor sources." 170 ./generate_descriptor_proto.sh -j "${NUM_MAKE_JOBS}" 171fi 172 173if [[ "${CORE_ONLY}" == "yes" ]] ; then 174 header "Building core Only" 175 wrapped_make -j "${NUM_MAKE_JOBS}" 176else 177 header "Building" 178 # Can't issue these together, when fully parallel, something sometimes chokes 179 # at random. 180 wrapped_make -j "${NUM_MAKE_JOBS}" all 181 wrapped_make -j "${NUM_MAKE_JOBS}" check 182 # Fire off the conformance tests also. 183 cd conformance 184 wrapped_make -j "${NUM_MAKE_JOBS}" test_cpp 185 cd .. 186fi 187 188# Ensure the WKT sources checked in are current. 189objectivec/generate_well_known_types.sh --check-only -j "${NUM_MAKE_JOBS}" 190 191header "Checking on the ObjC Runtime Code" 192objectivec/DevTools/pddm_tests.py 193if ! objectivec/DevTools/pddm.py --dry-run objectivec/*.[hm] objectivec/Tests/*.[hm] ; then 194 echo "" 195 echo "Update by running:" 196 echo " objectivec/DevTools/pddm.py objectivec/*.[hm] objectivec/Tests/*.[hm]" 197 exit 1 198fi 199 200if [[ "${DO_XCODE_IOS_TESTS}" == "yes" ]] ; then 201 XCODEBUILD_TEST_BASE_IOS=( 202 xcodebuild 203 -project objectivec/ProtocolBuffers_iOS.xcodeproj 204 -scheme ProtocolBuffers 205 ) 206 # Don't need to worry about form factors or retina/non retina; 207 # just pick a mix of OS Versions and 32/64 bit. 208 # NOTE: Different Xcode have different simulated hardware/os support. 209 readonly XCODE_VERSION_LINE="$(xcodebuild -version | grep Xcode\ )" 210 readonly XCODE_VERSION="${XCODE_VERSION_LINE/Xcode /}" # drop the prefix. 211 IOS_SIMULATOR_NAME="Simulator" 212 case "${XCODE_VERSION}" in 213 6.* ) 214 echo "ERROR: Xcode 6.3/6.4 no longer supported for building, please use 7.0 or higher." 1>&2 215 exit 10 216 ;; 217 7.1* ) 218 XCODEBUILD_TEST_BASE_IOS+=( 219 -destination "platform=iOS Simulator,name=iPhone 4s,OS=8.1" # 32bit 220 -destination "platform=iOS Simulator,name=iPhone 6,OS=9.0" # 64bit 221 -destination "platform=iOS Simulator,name=iPad 2,OS=8.1" # 32bit 222 -destination "platform=iOS Simulator,name=iPad Air,OS=9.0" # 64bit 223 ) 224 ;; 225 7.3* ) 226 XCODEBUILD_TEST_BASE_IOS+=( 227 -destination "platform=iOS Simulator,name=iPhone 4s,OS=8.1" # 32bit 228 -destination "platform=iOS Simulator,name=iPhone 6,OS=9.3" # 64bit 229 -destination "platform=iOS Simulator,name=iPad 2,OS=8.1" # 32bit 230 -destination "platform=iOS Simulator,name=iPad Air,OS=9.3" # 64bit 231 ) 232 ;; 233 7.* ) 234 XCODEBUILD_TEST_BASE_IOS+=( 235 -destination "platform=iOS Simulator,name=iPhone 4s,OS=8.1" # 32bit 236 -destination "platform=iOS Simulator,name=iPhone 6,OS=9.2" # 64bit 237 -destination "platform=iOS Simulator,name=iPad 2,OS=8.1" # 32bit 238 -destination "platform=iOS Simulator,name=iPad Air,OS=9.2" # 64bit 239 ) 240 ;; 241 * ) 242 echo "Time to update the simulator targets for Xcode ${XCODE_VERSION}" 243 exit 2 244 ;; 245 esac 246 header "Doing Xcode iOS build/tests - Debug" 247 "${XCODEBUILD_TEST_BASE_IOS[@]}" -configuration Debug test 248 header "Doing Xcode iOS build/tests - Release" 249 "${XCODEBUILD_TEST_BASE_IOS[@]}" -configuration Release test 250 # Don't leave the simulator in the developer's face. 251 killall "${IOS_SIMULATOR_NAME}" 252fi 253if [[ "${DO_XCODE_OSX_TESTS}" == "yes" ]] ; then 254 XCODEBUILD_TEST_BASE_OSX=( 255 xcodebuild 256 -project objectivec/ProtocolBuffers_OSX.xcodeproj 257 -scheme ProtocolBuffers 258 # Since the ObjC 2.0 Runtime is required, 32bit OS X isn't supported. 259 -destination "platform=OS X,arch=x86_64" # 64bit 260 ) 261 header "Doing Xcode OS X build/tests - Debug" 262 "${XCODEBUILD_TEST_BASE_OSX[@]}" -configuration Debug test 263 header "Doing Xcode OS X build/tests - Release" 264 "${XCODEBUILD_TEST_BASE_OSX[@]}" -configuration Release test 265fi 266 267if [[ "${DO_OBJC_CONFORMANCE_TESTS}" == "yes" ]] ; then 268 cd conformance 269 wrapped_make -j "${NUM_MAKE_JOBS}" test_objc 270 cd .. 271fi 272