1*9712c20fSFrederick Mayle#!/bin/sh 2*9712c20fSFrederick Mayle# Copyright 2012 Google LLC 3*9712c20fSFrederick Mayle# 4*9712c20fSFrederick Mayle# Redistribution and use in source and binary forms, with or without 5*9712c20fSFrederick Mayle# modification, are permitted provided that the following conditions are 6*9712c20fSFrederick Mayle# met: 7*9712c20fSFrederick Mayle# 8*9712c20fSFrederick Mayle# * Redistributions of source code must retain the above copyright 9*9712c20fSFrederick Mayle# notice, this list of conditions and the following disclaimer. 10*9712c20fSFrederick Mayle# * Redistributions in binary form must reproduce the above 11*9712c20fSFrederick Mayle# copyright notice, this list of conditions and the following disclaimer 12*9712c20fSFrederick Mayle# in the documentation and/or other materials provided with the 13*9712c20fSFrederick Mayle# distribution. 14*9712c20fSFrederick Mayle# * Neither the name of Google LLC nor the names of its 15*9712c20fSFrederick Mayle# contributors may be used to endorse or promote products derived from 16*9712c20fSFrederick Mayle# this software without specific prior written permission. 17*9712c20fSFrederick Mayle# 18*9712c20fSFrederick Mayle# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 19*9712c20fSFrederick Mayle# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 20*9712c20fSFrederick Mayle# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 21*9712c20fSFrederick Mayle# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 22*9712c20fSFrederick Mayle# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 23*9712c20fSFrederick Mayle# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 24*9712c20fSFrederick Mayle# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25*9712c20fSFrederick Mayle# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26*9712c20fSFrederick Mayle# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27*9712c20fSFrederick Mayle# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 28*9712c20fSFrederick Mayle# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29*9712c20fSFrederick Mayle 30*9712c20fSFrederick Mayle# Sanitize the environment 31*9712c20fSFrederick Mayleexport LANG=C 32*9712c20fSFrederick Mayleexport LC_ALL=C 33*9712c20fSFrederick Mayle 34*9712c20fSFrederick Mayleif [ "$BASH_VERSION" ]; then 35*9712c20fSFrederick Mayle set -o posix 36*9712c20fSFrederick Maylefi 37*9712c20fSFrederick Mayle 38*9712c20fSFrederick MaylePROGDIR=$(dirname "$0") 39*9712c20fSFrederick MaylePROGDIR=$(cd "$PROGDIR" && pwd) 40*9712c20fSFrederick MaylePROGNAME=$(basename "$0") 41*9712c20fSFrederick Mayle 42*9712c20fSFrederick Mayle. $PROGDIR/common-functions.sh 43*9712c20fSFrederick Mayle 44*9712c20fSFrederick MayleDEFAULT_ABI="armeabi" 45*9712c20fSFrederick MayleVALID_ABIS="armeabi armeabi-v7a x86 mips" 46*9712c20fSFrederick Mayle 47*9712c20fSFrederick MayleABI= 48*9712c20fSFrederick MayleADB= 49*9712c20fSFrederick MayleALL_TESTS= 50*9712c20fSFrederick MayleENABLE_M32= 51*9712c20fSFrederick MayleHELP= 52*9712c20fSFrederick MayleHELP_ALL= 53*9712c20fSFrederick MayleNDK_DIR= 54*9712c20fSFrederick MayleNO_CLEANUP= 55*9712c20fSFrederick MayleNO_DEVICE= 56*9712c20fSFrederick MayleNUM_JOBS=$(get_core_count) 57*9712c20fSFrederick MayleTMPDIR= 58*9712c20fSFrederick Mayle 59*9712c20fSFrederick Maylefor opt do 60*9712c20fSFrederick Mayle # The following extracts the value if the option is like --name=<value>. 61*9712c20fSFrederick Mayle optarg=$(expr -- $opt : '^--[^=]*=\(.*\)$') 62*9712c20fSFrederick Mayle case $opt in 63*9712c20fSFrederick Mayle --abi=*) ABI=$optarg;; 64*9712c20fSFrederick Mayle --adb=*) ADB=$optarg;; 65*9712c20fSFrederick Mayle --all-tests) ALL_TESTS=true;; 66*9712c20fSFrederick Mayle --enable-m32) ENABLE_M32=true;; 67*9712c20fSFrederick Mayle --help|-h|-?) HELP=TRUE;; 68*9712c20fSFrederick Mayle --help-all) HELP_ALL=true;; 69*9712c20fSFrederick Mayle --jobs=*) NUM_JOBS=$optarg;; 70*9712c20fSFrederick Mayle --ndk-dir=*) NDK_DIR=$optarg;; 71*9712c20fSFrederick Mayle --tmp-dir=*) TMPDIR=$optarg;; 72*9712c20fSFrederick Mayle --no-cleanup) NO_CLEANUP=true;; 73*9712c20fSFrederick Mayle --no-device) NO_DEVICE=true;; 74*9712c20fSFrederick Mayle --quiet) decrease_verbosity;; 75*9712c20fSFrederick Mayle --verbose) increase_verbosity;; 76*9712c20fSFrederick Mayle -*) panic "Invalid option '$opt', see --help for details.";; 77*9712c20fSFrederick Mayle *) panic "This script doesn't take any parameters. See --help for details." 78*9712c20fSFrederick Mayle ;; 79*9712c20fSFrederick Mayle esac 80*9712c20fSFrederick Mayledone 81*9712c20fSFrederick Mayle 82*9712c20fSFrederick Mayleif [ "$HELP" -o "$HELP_ALL" ]; then 83*9712c20fSFrederick Mayle echo "\ 84*9712c20fSFrederick Mayle Usage: $PROGNAME [options] 85*9712c20fSFrederick Mayle 86*9712c20fSFrederick Mayle This script is used to check that your Google Breakpad source tree can 87*9712c20fSFrederick Mayle be properly built for Android, and that the client library and host tools 88*9712c20fSFrederick Mayle work properly together. 89*9712c20fSFrederick Mayle" 90*9712c20fSFrederick Mayle if [ "$HELP_ALL" ]; then 91*9712c20fSFrederick Mayle echo "\ 92*9712c20fSFrederick Mayle In more details, this script will: 93*9712c20fSFrederick Mayle 94*9712c20fSFrederick Mayle - Rebuild the host version of Google Breakpad in a temporary 95*9712c20fSFrederick Mayle directory (with the Auto-tools based build system). 96*9712c20fSFrederick Mayle 97*9712c20fSFrederick Mayle - Rebuild the Android client library with the Google Breakpad build 98*9712c20fSFrederick Mayle system (using autotools/configure). This requires that you define 99*9712c20fSFrederick Mayle ANDROID_NDK_ROOT in your environment to point to a valid Android NDK 100*9712c20fSFrederick Mayle installation directory, or use the --ndk-dir=<path> option. 101*9712c20fSFrederick Mayle 102*9712c20fSFrederick Mayle - Rebuild the Android client library and a test crashing program with the 103*9712c20fSFrederick Mayle Android NDK build system (ndk-build). 104*9712c20fSFrederick Mayle 105*9712c20fSFrederick Mayle - Require an Android device connected to your machine, and the 'adb' 106*9712c20fSFrederick Mayle tool in your path. They are used to: 107*9712c20fSFrederick Mayle 108*9712c20fSFrederick Mayle - Install and run a test crashing program. 109*9712c20fSFrederick Mayle - Extract the corresponding minidump from the device. 110*9712c20fSFrederick Mayle - Dump the symbols from the test program on the host with 'dump_syms' 111*9712c20fSFrederick Mayle - Generate a stack trace with 'minidump_stackwalk' 112*9712c20fSFrederick Mayle - Check the stack trace content for valid source file locations. 113*9712c20fSFrederick Mayle 114*9712c20fSFrederick Mayle You can however skip this requirement and only test the builds by using 115*9712c20fSFrederick Mayle the --no-device flag. 116*9712c20fSFrederick Mayle 117*9712c20fSFrederick Mayle By default, all generated files will be created in a temporary directory 118*9712c20fSFrederick Mayle that is removed when the script completion. If you want to inspect the 119*9712c20fSFrederick Mayle files, use the --no-cleanup option. 120*9712c20fSFrederick Mayle 121*9712c20fSFrederick Mayle Finally, use --verbose to increase the verbosity level, this will help 122*9712c20fSFrederick Mayle you see which exact commands are being issues and their result. Use the 123*9712c20fSFrederick Mayle flag twice for even more output. Use --quiet to decrease verbosity 124*9712c20fSFrederick Mayle instead and run the script silently. 125*9712c20fSFrederick Mayle 126*9712c20fSFrederick Mayle If you have a device connected, the script will probe it to determine 127*9712c20fSFrederick Mayle its primary CPU ABI, and build the test program for it. You can however 128*9712c20fSFrederick Mayle use the --abi=<name> option to override this (this can be useful to check 129*9712c20fSFrederick Mayle the secondary ABI, e.g. using --abi=armeabi to check that such a program 130*9712c20fSFrederick Mayle works correctly on an ARMv7-A device). 131*9712c20fSFrederick Mayle 132*9712c20fSFrederick Mayle If you don't have a device connected, the test program will be built (but 133*9712c20fSFrederick Mayle not run) with the default '$DEFAULT_ABI' ABI. Again, you can use 134*9712c20fSFrederick Mayle --abi=<name> to override this. Valid ABI names are: 135*9712c20fSFrederick Mayle 136*9712c20fSFrederick Mayle $VALID_ABIS 137*9712c20fSFrederick Mayle 138*9712c20fSFrederick Mayle The script will only run the client library unit test on the device 139*9712c20fSFrederick Mayle by default. You can use --all-tests to also build and run the unit 140*9712c20fSFrederick Mayle tests for the Breakpad tools and processor, but be warned that this 141*9712c20fSFrederick Mayle adds several minutes of testing time. --all-tests will also run the 142*9712c20fSFrederick Mayle host unit tests suite. 143*9712c20fSFrederick Mayle" 144*9712c20fSFrederick Mayle 145*9712c20fSFrederick Mayle fi # HELP_ALL 146*9712c20fSFrederick Mayle 147*9712c20fSFrederick Mayle echo "\ 148*9712c20fSFrederick Mayle Valid options: 149*9712c20fSFrederick Mayle 150*9712c20fSFrederick Mayle --help|-h|-? Display this message. 151*9712c20fSFrederick Mayle --help-all Display extended help. 152*9712c20fSFrederick Mayle --enable-m32 Build 32-bit version of host tools. 153*9712c20fSFrederick Mayle --abi=<name> Specify target CPU ABI [auto-detected]. 154*9712c20fSFrederick Mayle --jobs=<count> Run <count> build tasks in parallel [$NUM_JOBS]. 155*9712c20fSFrederick Mayle --ndk-dir=<path> Specify NDK installation directory. 156*9712c20fSFrederick Mayle --tmp-dir=<path> Specify temporary directory (will be wiped-out). 157*9712c20fSFrederick Mayle --adb=<path> Specify adb program path. 158*9712c20fSFrederick Mayle --no-cleanup Don't remove temporary directory after completion. 159*9712c20fSFrederick Mayle --no-device Do not try to detect devices, nor run crash test. 160*9712c20fSFrederick Mayle --all-tests Run all unit tests (i.e. tools and processor ones too). 161*9712c20fSFrederick Mayle --verbose Increase verbosity. 162*9712c20fSFrederick Mayle --quiet Decrease verbosity." 163*9712c20fSFrederick Mayle 164*9712c20fSFrederick Mayle exit 0 165*9712c20fSFrederick Maylefi 166*9712c20fSFrederick Mayle 167*9712c20fSFrederick MayleTESTAPP_DIR=$PROGDIR/sample_app 168*9712c20fSFrederick Mayle 169*9712c20fSFrederick Mayle# Select NDK install directory. 170*9712c20fSFrederick Mayleif [ -z "$NDK_DIR" ]; then 171*9712c20fSFrederick Mayle if [ -z "$ANDROID_NDK_ROOT" ]; then 172*9712c20fSFrederick Mayle panic "Please define ANDROID_NDK_ROOT in your environment, or use \ 173*9712c20fSFrederick Mayle--ndk-dir=<path>." 174*9712c20fSFrederick Mayle fi 175*9712c20fSFrederick Mayle NDK_DIR="$ANDROID_NDK_ROOT" 176*9712c20fSFrederick Mayle log "Found NDK directory: $NDK_DIR" 177*9712c20fSFrederick Mayleelse 178*9712c20fSFrederick Mayle log "Using NDK directory: $NDK_DIR" 179*9712c20fSFrederick Maylefi 180*9712c20fSFrederick Mayle# Small sanity check. 181*9712c20fSFrederick MayleNDK_BUILD="$NDK_DIR/ndk-build" 182*9712c20fSFrederick Mayleif [ ! -f "$NDK_BUILD" ]; then 183*9712c20fSFrederick Mayle panic "Your NDK directory is not valid (missing ndk-build): $NDK_DIR" 184*9712c20fSFrederick Maylefi 185*9712c20fSFrederick Mayle 186*9712c20fSFrederick Mayle# Ensure the temporary directory is deleted on exit, except if the --no-cleanup 187*9712c20fSFrederick Mayle# option is used. 188*9712c20fSFrederick Mayle 189*9712c20fSFrederick Mayleclean_tmpdir () { 190*9712c20fSFrederick Mayle if [ "$TMPDIR" ]; then 191*9712c20fSFrederick Mayle if [ -z "$NO_CLEANUP" ]; then 192*9712c20fSFrederick Mayle log "Cleaning up: $TMPDIR" 193*9712c20fSFrederick Mayle rm -rf "$TMPDIR" 194*9712c20fSFrederick Mayle else 195*9712c20fSFrederick Mayle dump "Temporary directory contents preserved: $TMPDIR" 196*9712c20fSFrederick Mayle fi 197*9712c20fSFrederick Mayle fi 198*9712c20fSFrederick Mayle exit "$@" 199*9712c20fSFrederick Mayle} 200*9712c20fSFrederick Mayle 201*9712c20fSFrederick Mayleatexit clean_tmpdir 202*9712c20fSFrederick Mayle 203*9712c20fSFrederick Mayle# If --tmp-dir=<path> is not used, create a temporary directory. 204*9712c20fSFrederick Mayle# Otherwise, start by cleaning up the user-provided path. 205*9712c20fSFrederick Mayleif [ -z "$TMPDIR" ]; then 206*9712c20fSFrederick Mayle TMPDIR=$(mktemp -d /tmp/$PROGNAME.XXXXXXXX) 207*9712c20fSFrederick Mayle fail_panic "Can't create temporary directory!" 208*9712c20fSFrederick Mayle log "Using temporary directory: $TMPDIR" 209*9712c20fSFrederick Mayleelse 210*9712c20fSFrederick Mayle if [ ! -d "$TMPDIR" ]; then 211*9712c20fSFrederick Mayle mkdir -p "$TMPDIR" 212*9712c20fSFrederick Mayle fail_panic "Can't create temporary directory: $TMPDIR" 213*9712c20fSFrederick Mayle else 214*9712c20fSFrederick Mayle log "Cleaning up temporary directory: $TMPDIR" 215*9712c20fSFrederick Mayle rm -rf "$TMPDIR"/* 216*9712c20fSFrederick Mayle fail_panic "Cannot cleanup temporary directory!" 217*9712c20fSFrederick Mayle fi 218*9712c20fSFrederick Maylefi 219*9712c20fSFrederick Mayle 220*9712c20fSFrederick Mayleif [ -z "$NO_DEVICE" ]; then 221*9712c20fSFrederick Mayle if ! adb_check_device $ADB; then 222*9712c20fSFrederick Mayle echo "$(adb_get_error)" 223*9712c20fSFrederick Mayle echo "Use --no-device to build the code without running any tests." 224*9712c20fSFrederick Mayle exit 1 225*9712c20fSFrederick Mayle fi 226*9712c20fSFrederick Maylefi 227*9712c20fSFrederick Mayle 228*9712c20fSFrederick MayleBUILD_LOG="$TMPDIR/build.log" 229*9712c20fSFrederick MayleRUN_LOG="$TMPDIR/run.log" 230*9712c20fSFrederick MayleCRASH_LOG="$TMPDIR/crash.log" 231*9712c20fSFrederick Mayle 232*9712c20fSFrederick Mayleset_run_log "$RUN_LOG" 233*9712c20fSFrederick Mayle 234*9712c20fSFrederick MayleTMPHOST="$TMPDIR/host-local" 235*9712c20fSFrederick Mayle 236*9712c20fSFrederick Maylecd "$TMPDIR" 237*9712c20fSFrederick Mayle 238*9712c20fSFrederick Mayle# Build host version of the tools 239*9712c20fSFrederick Mayledump "Building host binaries." 240*9712c20fSFrederick MayleCONFIGURE_FLAGS= 241*9712c20fSFrederick Mayleif [ "$ENABLE_M32" ]; then 242*9712c20fSFrederick Mayle CONFIGURE_FLAGS="$CONFIGURE_FLAGS --enable-m32" 243*9712c20fSFrederick Maylefi 244*9712c20fSFrederick Mayle( 245*9712c20fSFrederick Mayle run mkdir "$TMPDIR/build-host" && 246*9712c20fSFrederick Mayle run cd "$TMPDIR/build-host" && 247*9712c20fSFrederick Mayle run2 "$PROGDIR/../configure" --prefix="$TMPHOST" $CONFIGURE_FLAGS && 248*9712c20fSFrederick Mayle run2 make -j$NUM_JOBS install 249*9712c20fSFrederick Mayle) 250*9712c20fSFrederick Maylefail_panic "Can't build host binaries!" 251*9712c20fSFrederick Mayle 252*9712c20fSFrederick Mayleif [ "$ALL_TESTS" ]; then 253*9712c20fSFrederick Mayle dump "Running host unit tests." 254*9712c20fSFrederick Mayle ( 255*9712c20fSFrederick Mayle run cd "$TMPDIR/build-host" && 256*9712c20fSFrederick Mayle run2 make -j$NUM_JOBS check 257*9712c20fSFrederick Mayle ) 258*9712c20fSFrederick Mayle fail_panic "Host unit tests failed!!" 259*9712c20fSFrederick Maylefi 260*9712c20fSFrederick Mayle 261*9712c20fSFrederick MayleTMPBIN=$TMPHOST/bin 262*9712c20fSFrederick Mayle 263*9712c20fSFrederick Mayle# Generate a stand-alone NDK toolchain 264*9712c20fSFrederick Mayle 265*9712c20fSFrederick Mayle# Extract CPU ABI and architecture from device, if any. 266*9712c20fSFrederick Mayleif adb_check_device; then 267*9712c20fSFrederick Mayle DEVICE_ABI=$(adb_shell getprop ro.product.cpu.abi) 268*9712c20fSFrederick Mayle DEVICE_ABI2=$(adb_shell getprop ro.product.cpu.abi2) 269*9712c20fSFrederick Mayle if [ -z "$DEVICE_ABI" ]; then 270*9712c20fSFrederick Mayle panic "Can't extract ABI from connected device!" 271*9712c20fSFrederick Mayle fi 272*9712c20fSFrederick Mayle if [ "$DEVICE_ABI2" ]; then 273*9712c20fSFrederick Mayle dump "Found device ABIs: $DEVICE_ABI $DEVICE_ABI2" 274*9712c20fSFrederick Mayle else 275*9712c20fSFrederick Mayle dump "Found device ABI: $DEVICE_ABI" 276*9712c20fSFrederick Mayle DEVICE_ABI2=$DEVICE_ABI 277*9712c20fSFrederick Mayle fi 278*9712c20fSFrederick Mayle 279*9712c20fSFrederick Mayle # If --abi=<name> is used, check that the device supports it. 280*9712c20fSFrederick Mayle if [ "$ABI" -a "$DEVICE_ABI" != "$ABI" -a "$DEVICE_ABI2" != "$ABI" ]; then 281*9712c20fSFrederick Mayle dump "ERROR: Device ABI(s) do not match --abi command-line value ($ABI)!" 282*9712c20fSFrederick Mayle panic "Please use --no-device to skip device tests." 283*9712c20fSFrederick Mayle fi 284*9712c20fSFrederick Mayle 285*9712c20fSFrederick Mayle if [ -z "$ABI" ]; then 286*9712c20fSFrederick Mayle ABI=$DEVICE_ABI 287*9712c20fSFrederick Mayle dump "Using CPU ABI: $ABI (device)" 288*9712c20fSFrederick Mayle else 289*9712c20fSFrederick Mayle dump "Using CPU ABI: $ABI (command-line)" 290*9712c20fSFrederick Mayle fi 291*9712c20fSFrederick Mayleelse 292*9712c20fSFrederick Mayle if [ -z "$ABI" ]; then 293*9712c20fSFrederick Mayle # No device connected, choose default ABI 294*9712c20fSFrederick Mayle ABI=$DEFAULT_ABI 295*9712c20fSFrederick Mayle dump "Using CPU ABI: $ABI (default)" 296*9712c20fSFrederick Mayle else 297*9712c20fSFrederick Mayle dump "Using CPU ABI: $ABI (command-line)" 298*9712c20fSFrederick Mayle fi 299*9712c20fSFrederick Maylefi 300*9712c20fSFrederick Mayle 301*9712c20fSFrederick Mayle# Check the ABI value 302*9712c20fSFrederick MayleVALID= 303*9712c20fSFrederick Maylefor VALID_ABI in $VALID_ABIS; do 304*9712c20fSFrederick Mayle if [ "$ABI" = "$VALID_ABI" ]; then 305*9712c20fSFrederick Mayle VALID=true 306*9712c20fSFrederick Mayle break 307*9712c20fSFrederick Mayle fi 308*9712c20fSFrederick Mayledone 309*9712c20fSFrederick Mayle 310*9712c20fSFrederick Mayleif [ -z "$VALID" ]; then 311*9712c20fSFrederick Mayle panic "Unknown CPU ABI '$ABI'. Valid values are: $VALID_ABIS" 312*9712c20fSFrederick Maylefi 313*9712c20fSFrederick Mayle 314*9712c20fSFrederick Mayle# Extract architecture name from ABI 315*9712c20fSFrederick Maylecase $ABI in 316*9712c20fSFrederick Mayle armeabi*) ARCH=arm;; 317*9712c20fSFrederick Mayle *) ARCH=$ABI;; 318*9712c20fSFrederick Mayleesac 319*9712c20fSFrederick Mayle 320*9712c20fSFrederick Mayle# Extract GNU configuration name 321*9712c20fSFrederick Maylecase $ARCH in 322*9712c20fSFrederick Mayle arm) 323*9712c20fSFrederick Mayle GNU_CONFIG=arm-linux-androideabi 324*9712c20fSFrederick Mayle ;; 325*9712c20fSFrederick Mayle x86) 326*9712c20fSFrederick Mayle GNU_CONFIG=i686-linux-android 327*9712c20fSFrederick Mayle ;; 328*9712c20fSFrederick Mayle mips) 329*9712c20fSFrederick Mayle GNU_CONFIG=mipsel-linux-android 330*9712c20fSFrederick Mayle ;; 331*9712c20fSFrederick Mayle *) 332*9712c20fSFrederick Mayle GNU_CONFIG="$ARCH-linux-android" 333*9712c20fSFrederick Mayle ;; 334*9712c20fSFrederick Mayleesac 335*9712c20fSFrederick Mayle 336*9712c20fSFrederick Mayle# Generate standalone NDK toolchain installation 337*9712c20fSFrederick MayleNDK_STANDALONE="$TMPDIR/ndk-$ARCH-toolchain" 338*9712c20fSFrederick Mayleecho "Generating NDK standalone toolchain installation" 339*9712c20fSFrederick Maylemkdir -p "$NDK_STANDALONE" 340*9712c20fSFrederick Mayle# NOTE: The --platform=android-9 is required to provide <regex.h> for GTest. 341*9712c20fSFrederick Maylerun "$NDK_DIR/build/tools/make-standalone-toolchain.sh" \ 342*9712c20fSFrederick Mayle --arch="$ARCH" \ 343*9712c20fSFrederick Mayle --platform=android-9 \ 344*9712c20fSFrederick Mayle --install-dir="$NDK_STANDALONE" 345*9712c20fSFrederick Maylefail_panic "Can't generate standalone NDK toolchain installation!" 346*9712c20fSFrederick Mayle 347*9712c20fSFrederick Mayle# Rebuild the client library, processor and tools with the auto-tools based 348*9712c20fSFrederick Mayle# build system. Even though it's not going to be used, this checks that this 349*9712c20fSFrederick Mayle# still works correctly. 350*9712c20fSFrederick Mayleecho "Building full Android binaries with configure/make" 351*9712c20fSFrederick MayleTMPTARGET="$TMPDIR/target-local" 352*9712c20fSFrederick Mayle( 353*9712c20fSFrederick Mayle PATH="$NDK_STANDALONE/bin:$PATH" 354*9712c20fSFrederick Mayle run mkdir "$TMPTARGET" && 355*9712c20fSFrederick Mayle run mkdir "$TMPDIR"/build-target && 356*9712c20fSFrederick Mayle run cd "$TMPDIR"/build-target && 357*9712c20fSFrederick Mayle run2 "$PROGDIR"/../configure --prefix="$TMPTARGET" \ 358*9712c20fSFrederick Mayle --host="$GNU_CONFIG" && 359*9712c20fSFrederick Mayle run2 make -j$NUM_JOBS install 360*9712c20fSFrederick Mayle) 361*9712c20fSFrederick Maylefail_panic "Could not rebuild Android binaries!" 362*9712c20fSFrederick Mayle 363*9712c20fSFrederick Mayle# Build and/or run unit test suite. 364*9712c20fSFrederick Mayle# If --no-device is used, only rebuild it, otherwise, run in on the 365*9712c20fSFrederick Mayle# connected device. 366*9712c20fSFrederick Mayleif [ "$NO_DEVICE" ]; then 367*9712c20fSFrederick Mayle ACTION="Building" 368*9712c20fSFrederick Mayle # This is a trick to force the Makefile to ignore running the scripts. 369*9712c20fSFrederick Mayle TESTS_ENVIRONMENT="TESTS_ENVIRONMENT=true" 370*9712c20fSFrederick Mayleelse 371*9712c20fSFrederick Mayle ACTION="Running" 372*9712c20fSFrederick Mayle TESTS_ENVIRONMENT= 373*9712c20fSFrederick Maylefi 374*9712c20fSFrederick Mayle 375*9712c20fSFrederick Mayle( 376*9712c20fSFrederick Mayle PATH="$NDK_STANDALONE/bin:$PATH" 377*9712c20fSFrederick Mayle run cd "$TMPDIR"/build-target && 378*9712c20fSFrederick Mayle # Reconfigure to only run the client unit test suite. 379*9712c20fSFrederick Mayle # This one should _never_ fail. 380*9712c20fSFrederick Mayle dump "$ACTION Android client library unit tests." 381*9712c20fSFrederick Mayle run2 "$PROGDIR"/../configure --prefix="$TMPTARGET" \ 382*9712c20fSFrederick Mayle --host="$GNU_CONFIG" \ 383*9712c20fSFrederick Mayle --disable-tools \ 384*9712c20fSFrederick Mayle --disable-processor && 385*9712c20fSFrederick Mayle run make -j$NUM_JOBS check $TESTS_ENVIRONMENT || exit $? 386*9712c20fSFrederick Mayle 387*9712c20fSFrederick Mayle if [ "$ALL_TESTS" ]; then 388*9712c20fSFrederick Mayle dump "$ACTION Tools and processor unit tests." 389*9712c20fSFrederick Mayle # Reconfigure to run the processor and tools tests. 390*9712c20fSFrederick Mayle # Most of these fail for now, so do not worry about it. 391*9712c20fSFrederick Mayle run2 "$PROGDIR"/../configure --prefix="$TMPTARGET" \ 392*9712c20fSFrederick Mayle --host="$GNU_CONFIG" && 393*9712c20fSFrederick Mayle run make -j$NUM_JOBS check $TESTS_ENVIRONMENT 394*9712c20fSFrederick Mayle if [ $? != 0 ]; then 395*9712c20fSFrederick Mayle dump "Tools and processor unit tests failed as expected. \ 396*9712c20fSFrederick MayleUse --verbose for results." 397*9712c20fSFrederick Mayle fi 398*9712c20fSFrederick Mayle fi 399*9712c20fSFrederick Mayle) 400*9712c20fSFrederick Maylefail_panic "Client library unit test suite failed!" 401*9712c20fSFrederick Mayle 402*9712c20fSFrederick Mayle# Copy sources to temporary directory 403*9712c20fSFrederick MaylePROJECT_DIR=$TMPDIR/project 404*9712c20fSFrederick Mayledump "Copying test program sources to: $PROJECT_DIR" 405*9712c20fSFrederick Maylerun cp -r "$TESTAPP_DIR" "$PROJECT_DIR" && 406*9712c20fSFrederick Maylerun rm -rf "$PROJECT_DIR/obj" && 407*9712c20fSFrederick Maylerun rm -rf "$PROJECT_DIR/libs" 408*9712c20fSFrederick Maylefail_panic "Could not copy test program sources to: $PROJECT_DIR" 409*9712c20fSFrederick Mayle 410*9712c20fSFrederick Mayle# Build the test program with ndk-build. 411*9712c20fSFrederick Mayledump "Building test program with ndk-build" 412*9712c20fSFrederick Mayleexport NDK_MODULE_PATH="$PROGDIR" 413*9712c20fSFrederick MayleNDK_BUILD_FLAGS="-j$NUM_JOBS" 414*9712c20fSFrederick Mayleif verbosity_is_higher_than 1; then 415*9712c20fSFrederick Mayle NDK_BUILD_FLAGS="$NDK_BUILD_FLAGS NDK_LOG=1 V=1" 416*9712c20fSFrederick Maylefi 417*9712c20fSFrederick Maylerun "$NDK_DIR/ndk-build" -C "$PROJECT_DIR" $NDK_BUILD_FLAGS APP_ABI=$ABI 418*9712c20fSFrederick Maylefail_panic "Can't build test program!" 419*9712c20fSFrederick Mayle 420*9712c20fSFrederick Mayle# Unless --no-device was used, stop right here if ADB isn't in the path, 421*9712c20fSFrederick Mayle# or there is no connected device. 422*9712c20fSFrederick Mayleif [ "$NO_DEVICE" ]; then 423*9712c20fSFrederick Mayle dump "Done. Please connect a device to run all tests!" 424*9712c20fSFrederick Mayle clean_exit 0 425*9712c20fSFrederick Maylefi 426*9712c20fSFrederick Mayle 427*9712c20fSFrederick Mayle# Push the program to the device. 428*9712c20fSFrederick MayleTESTAPP=test_google_breakpad 429*9712c20fSFrederick MayleTESTAPP_FILE="$PROJECT_DIR/libs/$ABI/test_google_breakpad" 430*9712c20fSFrederick Mayleif [ ! -f "$TESTAPP_FILE" ]; then 431*9712c20fSFrederick Mayle panic "Device requires '$ABI' binaries. None found!" 432*9712c20fSFrederick Maylefi 433*9712c20fSFrederick Mayle 434*9712c20fSFrederick Mayle# Run the program there 435*9712c20fSFrederick Mayledump "Installing test program on device" 436*9712c20fSFrederick MayleDEVICE_TMP=/data/local/tmp 437*9712c20fSFrederick Mayleadb_push "$TESTAPP_FILE" "$DEVICE_TMP/" 438*9712c20fSFrederick Maylefail_panic "Cannot push test program to device!" 439*9712c20fSFrederick Mayle 440*9712c20fSFrederick Mayledump "Running test program on device" 441*9712c20fSFrederick Mayleadb_shell cd "$DEVICE_TMP" "&&" ./$TESTAPP > "$CRASH_LOG" 2>/dev/null 442*9712c20fSFrederick Mayleif [ $? = 0 ]; then 443*9712c20fSFrederick Mayle panic "Test program did *not* crash as expected!" 444*9712c20fSFrederick Maylefi 445*9712c20fSFrederick Mayleif verbosity_is_higher_than 0; then 446*9712c20fSFrederick Mayle echo -n "Crash log: " 447*9712c20fSFrederick Mayle cat "$CRASH_LOG" 448*9712c20fSFrederick Maylefi 449*9712c20fSFrederick Mayle 450*9712c20fSFrederick Mayle# Extract minidump from device 451*9712c20fSFrederick MayleMINIDUMP_NAME=$(awk '$1 == "Dump" && $2 == "path:" { print $3; }' "$CRASH_LOG") 452*9712c20fSFrederick MayleMINIDUMP_NAME=$(basename "$MINIDUMP_NAME") 453*9712c20fSFrederick Mayleif [ -z "$MINIDUMP_NAME" ]; then 454*9712c20fSFrederick Mayle panic "Test program didn't write minidump properly!" 455*9712c20fSFrederick Maylefi 456*9712c20fSFrederick Mayle 457*9712c20fSFrederick Mayledump "Extracting minidump: $MINIDUMP_NAME" 458*9712c20fSFrederick Mayleadb_pull "$DEVICE_TMP/$MINIDUMP_NAME" . 459*9712c20fSFrederick Maylefail_panic "Can't extract minidump!" 460*9712c20fSFrederick Mayle 461*9712c20fSFrederick Mayledump "Parsing test program symbols" 462*9712c20fSFrederick Mayleif verbosity_is_higher_than 1; then 463*9712c20fSFrederick Mayle log "COMMAND: $TMPBIN/dump_syms \ 464*9712c20fSFrederick Mayle $PROJECT_DIR/obj/local/$ABI/$TESTAPP >$TESTAPP.sym" 465*9712c20fSFrederick Maylefi 466*9712c20fSFrederick Mayle"$TMPBIN/dump_syms" "$PROJECT_DIR/obj/local/$ABI/$TESTAPP" > $TESTAPP.sym 467*9712c20fSFrederick Maylefail_panic "dump_syms doesn't work!" 468*9712c20fSFrederick Mayle 469*9712c20fSFrederick MayleVERSION=$(awk '$1 == "MODULE" { print $4; }' $TESTAPP.sym) 470*9712c20fSFrederick Mayledump "Found module version: $VERSION" 471*9712c20fSFrederick Mayleif [ -z "$VERSION" ]; then 472*9712c20fSFrederick Mayle echo "ERROR: Can't find proper module version from symbol dump!" 473*9712c20fSFrederick Mayle head -n5 $TESTAPP.sym 474*9712c20fSFrederick Mayle clean_exit 1 475*9712c20fSFrederick Maylefi 476*9712c20fSFrederick Mayle 477*9712c20fSFrederick Maylerun mkdir -p "$TMPDIR/symbols/$TESTAPP/$VERSION" 478*9712c20fSFrederick Maylerun mv $TESTAPP.sym "$TMPDIR/symbols/$TESTAPP/$VERSION/" 479*9712c20fSFrederick Mayle 480*9712c20fSFrederick Mayledump "Generating stack trace" 481*9712c20fSFrederick Mayle# Don't use 'run' to be able to send stdout and stderr to two different files. 482*9712c20fSFrederick Maylelog "COMMAND: $TMPBIN/minidump_stackwalk $MINIDUMP_NAME symbols" 483*9712c20fSFrederick Mayle"$TMPBIN/minidump_stackwalk" $MINIDUMP_NAME \ 484*9712c20fSFrederick Mayle "$TMPDIR/symbols" \ 485*9712c20fSFrederick Mayle > "$BUILD_LOG" 2>>"$RUN_LOG" 486*9712c20fSFrederick Maylefail_panic "minidump_stackwalk doesn't work!" 487*9712c20fSFrederick Mayle 488*9712c20fSFrederick Mayledump "Checking stack trace content" 489*9712c20fSFrederick Mayle 490*9712c20fSFrederick Mayleif verbosity_is_higher_than 1; then 491*9712c20fSFrederick Mayle cat "$BUILD_LOG" 492*9712c20fSFrederick Maylefi 493*9712c20fSFrederick Mayle 494*9712c20fSFrederick Mayle# The generated stack trace should look like the following: 495*9712c20fSFrederick Mayle# 496*9712c20fSFrederick Mayle# Thread 0 (crashed) 497*9712c20fSFrederick Mayle# 0 test_google_breakpad!crash [test_breakpad.cpp : 17 + 0x4] 498*9712c20fSFrederick Mayle# r4 = 0x00015530 r5 = 0xbea2cbe4 r6 = 0xffffff38 r7 = 0xbea2cb5c 499*9712c20fSFrederick Mayle# r8 = 0x00000000 r9 = 0x00000000 r10 = 0x00000000 fp = 0x00000000 500*9712c20fSFrederick Mayle# sp = 0xbea2cb50 lr = 0x00009025 pc = 0x00008f84 501*9712c20fSFrederick Mayle# Found by: given as instruction pointer in context 502*9712c20fSFrederick Mayle# 1 test_google_breakpad!main [test_breakpad.cpp : 25 + 0x3] 503*9712c20fSFrederick Mayle# r4 = 0x00015530 r5 = 0xbea2cbe4 r6 = 0xffffff38 r7 = 0xbea2cb5c 504*9712c20fSFrederick Mayle# r8 = 0x00000000 r9 = 0x00000000 r10 = 0x00000000 fp = 0x00000000 505*9712c20fSFrederick Mayle# sp = 0xbea2cb50 pc = 0x00009025 506*9712c20fSFrederick Mayle# Found by: call frame info 507*9712c20fSFrederick Mayle# 2 libc.so + 0x164e5 508*9712c20fSFrederick Mayle# r4 = 0x00008f64 r5 = 0xbea2cc34 r6 = 0x00000001 r7 = 0xbea2cc3c 509*9712c20fSFrederick Mayle# r8 = 0x00000000 r9 = 0x00000000 r10 = 0x00000000 fp = 0x00000000 510*9712c20fSFrederick Mayle# sp = 0xbea2cc18 pc = 0x400c34e7 511*9712c20fSFrederick Mayle# Found by: call frame info 512*9712c20fSFrederick Mayle# ... 513*9712c20fSFrederick Mayle# 514*9712c20fSFrederick Mayle# The most important part for us is ensuring that the source location could 515*9712c20fSFrederick Mayle# be extracted, so look at the 'test_breakpad.cpp' references here. 516*9712c20fSFrederick Mayle# 517*9712c20fSFrederick Mayle# First, extract all the lines with test_google_breakpad! in them, and 518*9712c20fSFrederick Mayle# dump the corresponding crash location. 519*9712c20fSFrederick Mayle# 520*9712c20fSFrederick Mayle# Note that if the source location can't be extracted, the second field 521*9712c20fSFrederick Mayle# will only be 'test_google_breakpad' without the exclamation mark. 522*9712c20fSFrederick Mayle# 523*9712c20fSFrederick MayleLOCATIONS=$(awk '$2 ~ "^test_google_breakpad!.*" { print $3; }' "$BUILD_LOG") 524*9712c20fSFrederick Mayle 525*9712c20fSFrederick Mayleif [ -z "$LOCATIONS" ]; then 526*9712c20fSFrederick Mayle if verbosity_is_lower_than 1; then 527*9712c20fSFrederick Mayle cat "$BUILD_LOG" 528*9712c20fSFrederick Mayle fi 529*9712c20fSFrederick Mayle panic "No source location found in stack trace!" 530*9712c20fSFrederick Maylefi 531*9712c20fSFrederick Mayle 532*9712c20fSFrederick Mayle# Now check that they all match "[<source file>" 533*9712c20fSFrederick MayleBAD_LOCATIONS= 534*9712c20fSFrederick Maylefor LOCATION in $LOCATIONS; do 535*9712c20fSFrederick Mayle case $LOCATION in 536*9712c20fSFrederick Mayle # Escape the opening bracket, or some shells like Dash will not 537*9712c20fSFrederick Mayle # match them properly. 538*9712c20fSFrederick Mayle \[*.cpp|\[*.cc|\[*.h) # These are valid source locations in our executable 539*9712c20fSFrederick Mayle ;; 540*9712c20fSFrederick Mayle *) # Everything else is not! 541*9712c20fSFrederick Mayle BAD_LOCATIONS="$BAD_LOCATIONS $LOCATION" 542*9712c20fSFrederick Mayle ;; 543*9712c20fSFrederick Mayle esac 544*9712c20fSFrederick Mayledone 545*9712c20fSFrederick Mayle 546*9712c20fSFrederick Mayleif [ "$BAD_LOCATIONS" ]; then 547*9712c20fSFrederick Mayle dump "ERROR: Generated stack trace doesn't contain valid source locations:" 548*9712c20fSFrederick Mayle cat "$BUILD_LOG" 549*9712c20fSFrederick Mayle echo "Bad locations are: $BAD_LOCATIONS" 550*9712c20fSFrederick Mayle exit 1 551*9712c20fSFrederick Maylefi 552*9712c20fSFrederick Mayle 553*9712c20fSFrederick Mayleecho "All clear! Congratulations." 554*9712c20fSFrederick Mayle 555