1function hmm() { 2cat <<EOF 3 4Run "m help" for help with the build system itself. 5 6Invoke ". build/envsetup.sh" from your shell to add the following functions to your environment: 7- lunch: lunch <product_name>-<build_variant> 8 Selects <product_name> as the product to build, and <build_variant> as the variant to 9 build, and stores those selections in the environment to be read by subsequent 10 invocations of 'm' etc. 11- tapas: tapas [<App1> <App2> ...] [arm|x86|mips|arm64|x86_64|mips64] [eng|userdebug|user] 12- croot: Changes directory to the top of the tree, or a subdirectory thereof. 13- m: Makes from the top of the tree. 14- mm: Builds and installs all of the modules in the current directory, and their 15 dependencies. 16- mmm: Builds and installs all of the modules in the supplied directories, and their 17 dependencies. 18 To limit the modules being built use the syntax: mmm dir/:target1,target2. 19- mma: Same as 'mm' 20- mmma: Same as 'mmm' 21- provision: Flash device with all required partitions. Options will be passed on to fastboot. 22- cgrep: Greps on all local C/C++ files. 23- ggrep: Greps on all local Gradle files. 24- gogrep: Greps on all local Go files. 25- jgrep: Greps on all local Java files. 26- resgrep: Greps on all local res/*.xml files. 27- mangrep: Greps on all local AndroidManifest.xml files. 28- mgrep: Greps on all local Makefiles and *.bp files. 29- owngrep: Greps on all local OWNERS files. 30- sepgrep: Greps on all local sepolicy files. 31- sgrep: Greps on all local source files. 32- godir: Go to the directory containing a file. 33- allmod: List all modules. 34- gomod: Go to the directory containing a module. 35- pathmod: Get the directory containing a module. 36- refreshmod: Refresh list of modules for allmod/gomod. 37 38Environment options: 39- SANITIZE_HOST: Set to 'address' to use ASAN for all host modules. 40- ANDROID_QUIET_BUILD: set to 'true' to display only the essential messages. 41 42Look at the source to view more functions. The complete list is: 43EOF 44 local T=$(gettop) 45 local A="" 46 local i 47 for i in `cat $T/build/envsetup.sh | sed -n "/^[[:blank:]]*function /s/function \([a-z_]*\).*/\1/p" | sort | uniq`; do 48 A="$A $i" 49 done 50 echo $A 51} 52 53# Get all the build variables needed by this script in a single call to the build system. 54function build_build_var_cache() 55{ 56 local T=$(gettop) 57 # Grep out the variable names from the script. 58 cached_vars=(`cat $T/build/envsetup.sh | tr '()' ' ' | awk '{for(i=1;i<=NF;i++) if($i~/get_build_var/) print $(i+1)}' | sort -u | tr '\n' ' '`) 59 cached_abs_vars=(`cat $T/build/envsetup.sh | tr '()' ' ' | awk '{for(i=1;i<=NF;i++) if($i~/get_abs_build_var/) print $(i+1)}' | sort -u | tr '\n' ' '`) 60 # Call the build system to dump the "<val>=<value>" pairs as a shell script. 61 build_dicts_script=`\builtin cd $T; build/soong/soong_ui.bash --dumpvars-mode \ 62 --vars="${cached_vars[*]}" \ 63 --abs-vars="${cached_abs_vars[*]}" \ 64 --var-prefix=var_cache_ \ 65 --abs-var-prefix=abs_var_cache_` 66 local ret=$? 67 if [ $ret -ne 0 ] 68 then 69 unset build_dicts_script 70 return $ret 71 fi 72 # Execute the script to store the "<val>=<value>" pairs as shell variables. 73 eval "$build_dicts_script" 74 ret=$? 75 unset build_dicts_script 76 if [ $ret -ne 0 ] 77 then 78 return $ret 79 fi 80 BUILD_VAR_CACHE_READY="true" 81} 82 83# Delete the build var cache, so that we can still call into the build system 84# to get build variables not listed in this script. 85function destroy_build_var_cache() 86{ 87 unset BUILD_VAR_CACHE_READY 88 local v 89 for v in $cached_vars; do 90 unset var_cache_$v 91 done 92 unset cached_vars 93 for v in $cached_abs_vars; do 94 unset abs_var_cache_$v 95 done 96 unset cached_abs_vars 97} 98 99# Get the value of a build variable as an absolute path. 100function get_abs_build_var() 101{ 102 if [ "$BUILD_VAR_CACHE_READY" = "true" ] 103 then 104 eval "echo \"\${abs_var_cache_$1}\"" 105 return 106 fi 107 108 local T=$(gettop) 109 if [ ! "$T" ]; then 110 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 111 return 112 fi 113 (\cd $T; build/soong/soong_ui.bash --dumpvar-mode --abs $1) 114} 115 116# Get the exact value of a build variable. 117function get_build_var() 118{ 119 if [ "$BUILD_VAR_CACHE_READY" = "true" ] 120 then 121 eval "echo \"\${var_cache_$1}\"" 122 return 123 fi 124 125 local T=$(gettop) 126 if [ ! "$T" ]; then 127 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 128 return 129 fi 130 (\cd $T; build/soong/soong_ui.bash --dumpvar-mode $1) 131} 132 133# check to see if the supplied product is one we can build 134function check_product() 135{ 136 local T=$(gettop) 137 if [ ! "$T" ]; then 138 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 139 return 140 fi 141 TARGET_PRODUCT=$1 \ 142 TARGET_BUILD_VARIANT= \ 143 TARGET_BUILD_TYPE= \ 144 TARGET_BUILD_APPS= \ 145 get_build_var TARGET_DEVICE > /dev/null 146 # hide successful answers, but allow the errors to show 147} 148 149VARIANT_CHOICES=(user userdebug eng) 150 151# check to see if the supplied variant is valid 152function check_variant() 153{ 154 local v 155 for v in ${VARIANT_CHOICES[@]} 156 do 157 if [ "$v" = "$1" ] 158 then 159 return 0 160 fi 161 done 162 return 1 163} 164 165function setpaths() 166{ 167 local T=$(gettop) 168 if [ ! "$T" ]; then 169 echo "Couldn't locate the top of the tree. Try setting TOP." 170 return 171 fi 172 173 ################################################################## 174 # # 175 # Read me before you modify this code # 176 # # 177 # This function sets ANDROID_BUILD_PATHS to what it is adding # 178 # to PATH, and the next time it is run, it removes that from # 179 # PATH. This is required so lunch can be run more than once # 180 # and still have working paths. # 181 # # 182 ################################################################## 183 184 # Note: on windows/cygwin, ANDROID_BUILD_PATHS will contain spaces 185 # due to "C:\Program Files" being in the path. 186 187 # out with the old 188 if [ -n "$ANDROID_BUILD_PATHS" ] ; then 189 export PATH=${PATH/$ANDROID_BUILD_PATHS/} 190 fi 191 if [ -n "$ANDROID_PRE_BUILD_PATHS" ] ; then 192 export PATH=${PATH/$ANDROID_PRE_BUILD_PATHS/} 193 # strip leading ':', if any 194 export PATH=${PATH/:%/} 195 fi 196 197 # and in with the new 198 local prebuiltdir=$(getprebuilt) 199 local gccprebuiltdir=$(get_abs_build_var ANDROID_GCC_PREBUILTS) 200 201 # defined in core/config.mk 202 local targetgccversion=$(get_build_var TARGET_GCC_VERSION) 203 local targetgccversion2=$(get_build_var 2ND_TARGET_GCC_VERSION) 204 export TARGET_GCC_VERSION=$targetgccversion 205 206 # The gcc toolchain does not exists for windows/cygwin. In this case, do not reference it. 207 export ANDROID_TOOLCHAIN= 208 export ANDROID_TOOLCHAIN_2ND_ARCH= 209 local ARCH=$(get_build_var TARGET_ARCH) 210 local toolchaindir toolchaindir2= 211 case $ARCH in 212 x86) toolchaindir=x86/x86_64-linux-android-$targetgccversion/bin 213 ;; 214 x86_64) toolchaindir=x86/x86_64-linux-android-$targetgccversion/bin 215 ;; 216 arm) toolchaindir=arm/arm-linux-androideabi-$targetgccversion/bin 217 ;; 218 arm64) toolchaindir=aarch64/aarch64-linux-android-$targetgccversion/bin; 219 toolchaindir2=arm/arm-linux-androideabi-$targetgccversion2/bin 220 ;; 221 mips|mips64) toolchaindir=mips/mips64el-linux-android-$targetgccversion/bin 222 ;; 223 *) 224 echo "Can't find toolchain for unknown architecture: $ARCH" 225 toolchaindir=xxxxxxxxx 226 ;; 227 esac 228 if [ -d "$gccprebuiltdir/$toolchaindir" ]; then 229 export ANDROID_TOOLCHAIN=$gccprebuiltdir/$toolchaindir 230 fi 231 232 if [ "$toolchaindir2" -a -d "$gccprebuiltdir/$toolchaindir2" ]; then 233 export ANDROID_TOOLCHAIN_2ND_ARCH=$gccprebuiltdir/$toolchaindir2 234 fi 235 236 export ANDROID_DEV_SCRIPTS=$T/development/scripts:$T/prebuilts/devtools/tools:$T/external/selinux/prebuilts/bin 237 238 # add kernel specific binaries 239 case $(uname -s) in 240 Linux) 241 export ANDROID_DEV_SCRIPTS=$ANDROID_DEV_SCRIPTS:$T/prebuilts/misc/linux-x86/dtc:$T/prebuilts/misc/linux-x86/libufdt 242 ;; 243 *) 244 ;; 245 esac 246 247 ANDROID_BUILD_PATHS=$(get_build_var ANDROID_BUILD_PATHS):$ANDROID_TOOLCHAIN 248 if [ -n "$ANDROID_TOOLCHAIN_2ND_ARCH" ]; then 249 ANDROID_BUILD_PATHS=$ANDROID_BUILD_PATHS:$ANDROID_TOOLCHAIN_2ND_ARCH 250 fi 251 ANDROID_BUILD_PATHS=$ANDROID_BUILD_PATHS:$ANDROID_DEV_SCRIPTS 252 253 # Append llvm binutils prebuilts path to ANDROID_BUILD_PATHS. 254 local ANDROID_LLVM_BINUTILS=$(get_abs_build_var ANDROID_CLANG_PREBUILTS)/llvm-binutils-stable 255 ANDROID_BUILD_PATHS=$ANDROID_BUILD_PATHS:$ANDROID_LLVM_BINUTILS 256 257 # Set up ASAN_SYMBOLIZER_PATH for SANITIZE_HOST=address builds. 258 export ASAN_SYMBOLIZER_PATH=$ANDROID_LLVM_BINUTILS/llvm-symbolizer 259 260 # If prebuilts/android-emulator/<system>/ exists, prepend it to our PATH 261 # to ensure that the corresponding 'emulator' binaries are used. 262 case $(uname -s) in 263 Darwin) 264 ANDROID_EMULATOR_PREBUILTS=$T/prebuilts/android-emulator/darwin-x86_64 265 ;; 266 Linux) 267 ANDROID_EMULATOR_PREBUILTS=$T/prebuilts/android-emulator/linux-x86_64 268 ;; 269 *) 270 ANDROID_EMULATOR_PREBUILTS= 271 ;; 272 esac 273 if [ -n "$ANDROID_EMULATOR_PREBUILTS" -a -d "$ANDROID_EMULATOR_PREBUILTS" ]; then 274 ANDROID_BUILD_PATHS=$ANDROID_BUILD_PATHS:$ANDROID_EMULATOR_PREBUILTS 275 export ANDROID_EMULATOR_PREBUILTS 276 fi 277 278 # Append asuite prebuilts path to ANDROID_BUILD_PATHS. 279 local os_arch=$(get_build_var HOST_PREBUILT_TAG) 280 local ACLOUD_PATH="$T/prebuilts/asuite/acloud/$os_arch" 281 local AIDEGEN_PATH="$T/prebuilts/asuite/aidegen/$os_arch" 282 local ATEST_PATH="$T/prebuilts/asuite/atest/$os_arch" 283 export ANDROID_BUILD_PATHS=$ANDROID_BUILD_PATHS:$ACLOUD_PATH:$AIDEGEN_PATH:$ATEST_PATH: 284 285 export PATH=$ANDROID_BUILD_PATHS$PATH 286 287 # out with the duplicate old 288 if [ -n $ANDROID_PYTHONPATH ]; then 289 export PYTHONPATH=${PYTHONPATH//$ANDROID_PYTHONPATH/} 290 fi 291 # and in with the new 292 export ANDROID_PYTHONPATH=$T/development/python-packages: 293 if [ -n $VENDOR_PYTHONPATH ]; then 294 ANDROID_PYTHONPATH=$ANDROID_PYTHONPATH$VENDOR_PYTHONPATH 295 fi 296 export PYTHONPATH=$ANDROID_PYTHONPATH$PYTHONPATH 297 298 export ANDROID_JAVA_HOME=$(get_abs_build_var ANDROID_JAVA_HOME) 299 export JAVA_HOME=$ANDROID_JAVA_HOME 300 export ANDROID_JAVA_TOOLCHAIN=$(get_abs_build_var ANDROID_JAVA_TOOLCHAIN) 301 export ANDROID_PRE_BUILD_PATHS=$ANDROID_JAVA_TOOLCHAIN: 302 export PATH=$ANDROID_PRE_BUILD_PATHS$PATH 303 304 unset ANDROID_PRODUCT_OUT 305 export ANDROID_PRODUCT_OUT=$(get_abs_build_var PRODUCT_OUT) 306 export OUT=$ANDROID_PRODUCT_OUT 307 308 unset ANDROID_HOST_OUT 309 export ANDROID_HOST_OUT=$(get_abs_build_var HOST_OUT) 310 311 unset ANDROID_HOST_OUT_TESTCASES 312 export ANDROID_HOST_OUT_TESTCASES=$(get_abs_build_var HOST_OUT_TESTCASES) 313 314 unset ANDROID_TARGET_OUT_TESTCASES 315 export ANDROID_TARGET_OUT_TESTCASES=$(get_abs_build_var TARGET_OUT_TESTCASES) 316 317 # needed for building linux on MacOS 318 # TODO: fix the path 319 #export HOST_EXTRACFLAGS="-I "$T/system/kernel_headers/host_include 320} 321 322function printconfig() 323{ 324 local T=$(gettop) 325 if [ ! "$T" ]; then 326 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 327 return 328 fi 329 get_build_var report_config 330} 331 332function set_stuff_for_environment() 333{ 334 setpaths 335 set_sequence_number 336 337 export ANDROID_BUILD_TOP=$(gettop) 338 # With this environment variable new GCC can apply colors to warnings/errors 339 export GCC_COLORS='error=01;31:warning=01;35:note=01;36:caret=01;32:locus=01:quote=01' 340} 341 342function set_sequence_number() 343{ 344 export BUILD_ENV_SEQUENCE_NUMBER=13 345} 346 347# Takes a command name, and check if it's in ENVSETUP_NO_COMPLETION or not. 348function should_add_completion() { 349 local cmd="$(basename $1| sed 's/_completion//' |sed 's/\.\(.*\)*sh$//')" 350 case :"$ENVSETUP_NO_COMPLETION": in 351 *:"$cmd":*) 352 return 1 353 ;; 354 esac 355 return 0 356} 357 358function addcompletions() 359{ 360 local T dir f 361 362 # Keep us from trying to run in something that's neither bash nor zsh. 363 if [ -z "$BASH_VERSION" -a -z "$ZSH_VERSION" ]; then 364 return 365 fi 366 367 # Keep us from trying to run in bash that's too old. 368 if [ -n "$BASH_VERSION" -a ${BASH_VERSINFO[0]} -lt 3 ]; then 369 return 370 fi 371 372 local completion_files=( 373 system/core/adb/adb.bash 374 system/core/fastboot/fastboot.bash 375 tools/asuite/asuite.sh 376 ) 377 # Completion can be disabled selectively to allow users to use non-standard completion. 378 # e.g. 379 # ENVSETUP_NO_COMPLETION=adb # -> disable adb completion 380 # ENVSETUP_NO_COMPLETION=adb:bit # -> disable adb and bit completion 381 for f in ${completion_files[*]}; do 382 if [ -f "$f" ] && should_add_completion "$f"; then 383 . $f 384 fi 385 done 386 387 if should_add_completion bit ; then 388 complete -C "bit --tab" bit 389 fi 390 if [ -z "$ZSH_VERSION" ]; then 391 # Doesn't work in zsh. 392 complete -o nospace -F _croot croot 393 fi 394 complete -F _lunch lunch 395 396 complete -F _complete_android_module_names gomod 397 complete -F _complete_android_module_names m 398} 399 400function choosetype() 401{ 402 echo "Build type choices are:" 403 echo " 1. release" 404 echo " 2. debug" 405 echo 406 407 local DEFAULT_NUM DEFAULT_VALUE 408 DEFAULT_NUM=1 409 DEFAULT_VALUE=release 410 411 export TARGET_BUILD_TYPE= 412 local ANSWER 413 while [ -z $TARGET_BUILD_TYPE ] 414 do 415 echo -n "Which would you like? ["$DEFAULT_NUM"] " 416 if [ -z "$1" ] ; then 417 read ANSWER 418 else 419 echo $1 420 ANSWER=$1 421 fi 422 case $ANSWER in 423 "") 424 export TARGET_BUILD_TYPE=$DEFAULT_VALUE 425 ;; 426 1) 427 export TARGET_BUILD_TYPE=release 428 ;; 429 release) 430 export TARGET_BUILD_TYPE=release 431 ;; 432 2) 433 export TARGET_BUILD_TYPE=debug 434 ;; 435 debug) 436 export TARGET_BUILD_TYPE=debug 437 ;; 438 *) 439 echo 440 echo "I didn't understand your response. Please try again." 441 echo 442 ;; 443 esac 444 if [ -n "$1" ] ; then 445 break 446 fi 447 done 448 449 build_build_var_cache 450 set_stuff_for_environment 451 destroy_build_var_cache 452} 453 454# 455# This function isn't really right: It chooses a TARGET_PRODUCT 456# based on the list of boards. Usually, that gets you something 457# that kinda works with a generic product, but really, you should 458# pick a product by name. 459# 460function chooseproduct() 461{ 462 local default_value 463 if [ "x$TARGET_PRODUCT" != x ] ; then 464 default_value=$TARGET_PRODUCT 465 else 466 default_value=aosp_arm 467 fi 468 469 export TARGET_BUILD_APPS= 470 export TARGET_PRODUCT= 471 local ANSWER 472 while [ -z "$TARGET_PRODUCT" ] 473 do 474 echo -n "Which product would you like? [$default_value] " 475 if [ -z "$1" ] ; then 476 read ANSWER 477 else 478 echo $1 479 ANSWER=$1 480 fi 481 482 if [ -z "$ANSWER" ] ; then 483 export TARGET_PRODUCT=$default_value 484 else 485 if check_product $ANSWER 486 then 487 export TARGET_PRODUCT=$ANSWER 488 else 489 echo "** Not a valid product: $ANSWER" 490 fi 491 fi 492 if [ -n "$1" ] ; then 493 break 494 fi 495 done 496 497 build_build_var_cache 498 set_stuff_for_environment 499 destroy_build_var_cache 500} 501 502function choosevariant() 503{ 504 echo "Variant choices are:" 505 local index=1 506 local v 507 for v in ${VARIANT_CHOICES[@]} 508 do 509 # The product name is the name of the directory containing 510 # the makefile we found, above. 511 echo " $index. $v" 512 index=$(($index+1)) 513 done 514 515 local default_value=eng 516 local ANSWER 517 518 export TARGET_BUILD_VARIANT= 519 while [ -z "$TARGET_BUILD_VARIANT" ] 520 do 521 echo -n "Which would you like? [$default_value] " 522 if [ -z "$1" ] ; then 523 read ANSWER 524 else 525 echo $1 526 ANSWER=$1 527 fi 528 529 if [ -z "$ANSWER" ] ; then 530 export TARGET_BUILD_VARIANT=$default_value 531 elif (echo -n $ANSWER | grep -q -e "^[0-9][0-9]*$") ; then 532 if [ "$ANSWER" -le "${#VARIANT_CHOICES[@]}" ] ; then 533 export TARGET_BUILD_VARIANT=${VARIANT_CHOICES[@]:$(($ANSWER-1)):1} 534 fi 535 else 536 if check_variant $ANSWER 537 then 538 export TARGET_BUILD_VARIANT=$ANSWER 539 else 540 echo "** Not a valid variant: $ANSWER" 541 fi 542 fi 543 if [ -n "$1" ] ; then 544 break 545 fi 546 done 547} 548 549function choosecombo() 550{ 551 choosetype $1 552 553 echo 554 echo 555 chooseproduct $2 556 557 echo 558 echo 559 choosevariant $3 560 561 echo 562 build_build_var_cache 563 set_stuff_for_environment 564 printconfig 565 destroy_build_var_cache 566} 567 568function add_lunch_combo() 569{ 570 if [ -n "$ZSH_VERSION" ]; then 571 echo -n "${funcfiletrace[1]}: " 572 else 573 echo -n "${BASH_SOURCE[1]}:${BASH_LINENO[0]}: " 574 fi 575 echo "add_lunch_combo is obsolete. Use COMMON_LUNCH_CHOICES in your AndroidProducts.mk instead." 576} 577 578function print_lunch_menu() 579{ 580 local uname=$(uname) 581 local choices=$(TARGET_BUILD_APPS= get_build_var COMMON_LUNCH_CHOICES) 582 echo 583 echo "You're building on" $uname 584 echo 585 echo "Lunch menu... pick a combo:" 586 587 local i=1 588 local choice 589 for choice in $(echo $choices) 590 do 591 echo " $i. $choice" 592 i=$(($i+1)) 593 done 594 595 echo 596} 597 598function lunch() 599{ 600 local answer 601 602 if [ "$1" ] ; then 603 answer=$1 604 else 605 print_lunch_menu 606 echo -n "Which would you like? [aosp_arm-eng] " 607 read answer 608 fi 609 610 local selection= 611 612 if [ -z "$answer" ] 613 then 614 selection=aosp_arm-eng 615 elif (echo -n $answer | grep -q -e "^[0-9][0-9]*$") 616 then 617 local choices=($(TARGET_BUILD_APPS= get_build_var COMMON_LUNCH_CHOICES)) 618 if [ $answer -le ${#choices[@]} ] 619 then 620 # array in zsh starts from 1 instead of 0. 621 if [ -n "$ZSH_VERSION" ] 622 then 623 selection=${choices[$(($answer))]} 624 else 625 selection=${choices[$(($answer-1))]} 626 fi 627 fi 628 else 629 selection=$answer 630 fi 631 632 export TARGET_BUILD_APPS= 633 634 local product variant_and_version variant version 635 636 product=${selection%%-*} # Trim everything after first dash 637 variant_and_version=${selection#*-} # Trim everything up to first dash 638 if [ "$variant_and_version" != "$selection" ]; then 639 variant=${variant_and_version%%-*} 640 if [ "$variant" != "$variant_and_version" ]; then 641 version=${variant_and_version#*-} 642 fi 643 fi 644 645 if [ -z "$product" ] 646 then 647 echo 648 echo "Invalid lunch combo: $selection" 649 return 1 650 fi 651 652 TARGET_PRODUCT=$product \ 653 TARGET_BUILD_VARIANT=$variant \ 654 TARGET_PLATFORM_VERSION=$version \ 655 build_build_var_cache 656 if [ $? -ne 0 ] 657 then 658 return 1 659 fi 660 661 export TARGET_PRODUCT=$(get_build_var TARGET_PRODUCT) 662 export TARGET_BUILD_VARIANT=$(get_build_var TARGET_BUILD_VARIANT) 663 if [ -n "$version" ]; then 664 export TARGET_PLATFORM_VERSION=$(get_build_var TARGET_PLATFORM_VERSION) 665 else 666 unset TARGET_PLATFORM_VERSION 667 fi 668 export TARGET_BUILD_TYPE=release 669 670 echo 671 672 set_stuff_for_environment 673 printconfig 674 destroy_build_var_cache 675} 676 677unset COMMON_LUNCH_CHOICES_CACHE 678# Tab completion for lunch. 679function _lunch() 680{ 681 local cur prev opts 682 COMPREPLY=() 683 cur="${COMP_WORDS[COMP_CWORD]}" 684 prev="${COMP_WORDS[COMP_CWORD-1]}" 685 686 if [ -z "$COMMON_LUNCH_CHOICES_CACHE" ]; then 687 COMMON_LUNCH_CHOICES_CACHE=$(TARGET_BUILD_APPS= get_build_var COMMON_LUNCH_CHOICES) 688 fi 689 690 COMPREPLY=( $(compgen -W "${COMMON_LUNCH_CHOICES_CACHE}" -- ${cur}) ) 691 return 0 692} 693 694# Configures the build to build unbundled apps. 695# Run tapas with one or more app names (from LOCAL_PACKAGE_NAME) 696function tapas() 697{ 698 local showHelp="$(echo $* | xargs -n 1 echo | \grep -E '^(help)$' | xargs)" 699 local arch="$(echo $* | xargs -n 1 echo | \grep -E '^(arm|x86|mips|arm64|x86_64|mips64)$' | xargs)" 700 local variant="$(echo $* | xargs -n 1 echo | \grep -E '^(user|userdebug|eng)$' | xargs)" 701 local density="$(echo $* | xargs -n 1 echo | \grep -E '^(ldpi|mdpi|tvdpi|hdpi|xhdpi|xxhdpi|xxxhdpi|alldpi)$' | xargs)" 702 local apps="$(echo $* | xargs -n 1 echo | \grep -E -v '^(user|userdebug|eng|arm|x86|mips|arm64|x86_64|mips64|ldpi|mdpi|tvdpi|hdpi|xhdpi|xxhdpi|xxxhdpi|alldpi)$' | xargs)" 703 704 if [ "$showHelp" != "" ]; then 705 $(gettop)/build/make/tapasHelp.sh 706 return 707 fi 708 709 if [ $(echo $arch | wc -w) -gt 1 ]; then 710 echo "tapas: Error: Multiple build archs supplied: $arch" 711 return 712 fi 713 if [ $(echo $variant | wc -w) -gt 1 ]; then 714 echo "tapas: Error: Multiple build variants supplied: $variant" 715 return 716 fi 717 if [ $(echo $density | wc -w) -gt 1 ]; then 718 echo "tapas: Error: Multiple densities supplied: $density" 719 return 720 fi 721 722 local product=aosp_arm 723 case $arch in 724 x86) product=aosp_x86;; 725 mips) product=aosp_mips;; 726 arm64) product=aosp_arm64;; 727 x86_64) product=aosp_x86_64;; 728 mips64) product=aosp_mips64;; 729 esac 730 if [ -z "$variant" ]; then 731 variant=eng 732 fi 733 if [ -z "$apps" ]; then 734 apps=all 735 fi 736 if [ -z "$density" ]; then 737 density=alldpi 738 fi 739 740 export TARGET_PRODUCT=$product 741 export TARGET_BUILD_VARIANT=$variant 742 export TARGET_BUILD_DENSITY=$density 743 export TARGET_BUILD_TYPE=release 744 export TARGET_BUILD_APPS=$apps 745 746 build_build_var_cache 747 set_stuff_for_environment 748 printconfig 749 destroy_build_var_cache 750} 751 752function gettop 753{ 754 local TOPFILE=build/make/core/envsetup.mk 755 if [ -n "$TOP" -a -f "$TOP/$TOPFILE" ] ; then 756 # The following circumlocution ensures we remove symlinks from TOP. 757 (cd $TOP; PWD= /bin/pwd) 758 else 759 if [ -f $TOPFILE ] ; then 760 # The following circumlocution (repeated below as well) ensures 761 # that we record the true directory name and not one that is 762 # faked up with symlink names. 763 PWD= /bin/pwd 764 else 765 local HERE=$PWD 766 local T= 767 while [ \( ! \( -f $TOPFILE \) \) -a \( $PWD != "/" \) ]; do 768 \cd .. 769 T=`PWD= /bin/pwd -P` 770 done 771 \cd $HERE 772 if [ -f "$T/$TOPFILE" ]; then 773 echo $T 774 fi 775 fi 776 fi 777} 778 779function croot() 780{ 781 local T=$(gettop) 782 if [ "$T" ]; then 783 if [ "$1" ]; then 784 \cd $(gettop)/$1 785 else 786 \cd $(gettop) 787 fi 788 else 789 echo "Couldn't locate the top of the tree. Try setting TOP." 790 fi 791} 792 793function _croot() 794{ 795 local T=$(gettop) 796 if [ "$T" ]; then 797 local cur="${COMP_WORDS[COMP_CWORD]}" 798 k=0 799 for c in $(compgen -d ${T}/${cur}); do 800 COMPREPLY[k++]=${c#${T}/}/ 801 done 802 fi 803} 804 805function cproj() 806{ 807 local TOPFILE=build/make/core/envsetup.mk 808 local HERE=$PWD 809 local T= 810 while [ \( ! \( -f $TOPFILE \) \) -a \( $PWD != "/" \) ]; do 811 T=$PWD 812 if [ -f "$T/Android.mk" ]; then 813 \cd $T 814 return 815 fi 816 \cd .. 817 done 818 \cd $HERE 819 echo "can't find Android.mk" 820} 821 822# simplified version of ps; output in the form 823# <pid> <procname> 824function qpid() { 825 local prepend='' 826 local append='' 827 if [ "$1" = "--exact" ]; then 828 prepend=' ' 829 append='$' 830 shift 831 elif [ "$1" = "--help" -o "$1" = "-h" ]; then 832 echo "usage: qpid [[--exact] <process name|pid>" 833 return 255 834 fi 835 836 local EXE="$1" 837 if [ "$EXE" ] ; then 838 qpid | \grep "$prepend$EXE$append" 839 else 840 adb shell ps \ 841 | tr -d '\r' \ 842 | sed -e 1d -e 's/^[^ ]* *\([0-9]*\).* \([^ ]*\)$/\1 \2/' 843 fi 844} 845 846# coredump_setup - enable core dumps globally for any process 847# that has the core-file-size limit set correctly 848# 849# NOTE: You must call also coredump_enable for a specific process 850# if its core-file-size limit is not set already. 851# NOTE: Core dumps are written to ramdisk; they will not survive a reboot! 852 853function coredump_setup() 854{ 855 echo "Getting root..."; 856 adb root; 857 adb wait-for-device; 858 859 echo "Remounting root partition read-write..."; 860 adb shell mount -w -o remount -t rootfs rootfs; 861 sleep 1; 862 adb wait-for-device; 863 adb shell mkdir -p /cores; 864 adb shell mount -t tmpfs tmpfs /cores; 865 adb shell chmod 0777 /cores; 866 867 echo "Granting SELinux permission to dump in /cores..."; 868 adb shell restorecon -R /cores; 869 870 echo "Set core pattern."; 871 adb shell 'echo /cores/core.%p > /proc/sys/kernel/core_pattern'; 872 873 echo "Done." 874} 875 876# coredump_enable - enable core dumps for the specified process 877# $1 = PID of process (e.g., $(pid mediaserver)) 878# 879# NOTE: coredump_setup must have been called as well for a core 880# dump to actually be generated. 881 882function coredump_enable() 883{ 884 local PID=$1; 885 if [ -z "$PID" ]; then 886 printf "Expecting a PID!\n"; 887 return; 888 fi; 889 echo "Setting core limit for $PID to infinite..."; 890 adb shell /system/bin/ulimit -p $PID -c unlimited 891} 892 893# core - send SIGV and pull the core for process 894# $1 = PID of process (e.g., $(pid mediaserver)) 895# 896# NOTE: coredump_setup must be called once per boot for core dumps to be 897# enabled globally. 898 899function core() 900{ 901 local PID=$1; 902 903 if [ -z "$PID" ]; then 904 printf "Expecting a PID!\n"; 905 return; 906 fi; 907 908 local CORENAME=core.$PID; 909 local COREPATH=/cores/$CORENAME; 910 local SIG=SEGV; 911 912 coredump_enable $1; 913 914 local done=0; 915 while [ $(adb shell "[ -d /proc/$PID ] && echo -n yes") ]; do 916 printf "\tSending SIG%s to %d...\n" $SIG $PID; 917 adb shell kill -$SIG $PID; 918 sleep 1; 919 done; 920 921 adb shell "while [ ! -f $COREPATH ] ; do echo waiting for $COREPATH to be generated; sleep 1; done" 922 echo "Done: core is under $COREPATH on device."; 923} 924 925# systemstack - dump the current stack trace of all threads in the system process 926# to the usual ANR traces file 927function systemstack() 928{ 929 stacks system_server 930} 931 932# Read the ELF header from /proc/$PID/exe to determine if the process is 933# 64-bit. 934function is64bit() 935{ 936 local PID="$1" 937 if [ "$PID" ] ; then 938 if [[ "$(adb shell cat /proc/$PID/exe | xxd -l 1 -s 4 -p)" -eq "02" ]] ; then 939 echo "64" 940 else 941 echo "" 942 fi 943 else 944 echo "" 945 fi 946} 947 948case `uname -s` in 949 Darwin) 950 function sgrep() 951 { 952 find -E . -name .repo -prune -o -name .git -prune -o -type f -iregex '.*\.(c|h|cc|cpp|hpp|S|java|xml|sh|mk|aidl|vts)' \ 953 -exec grep --color -n "$@" {} + 954 } 955 956 ;; 957 *) 958 function sgrep() 959 { 960 find . -name .repo -prune -o -name .git -prune -o -type f -iregex '.*\.\(c\|h\|cc\|cpp\|hpp\|S\|java\|xml\|sh\|mk\|aidl\|vts\)' \ 961 -exec grep --color -n "$@" {} + 962 } 963 ;; 964esac 965 966function gettargetarch 967{ 968 get_build_var TARGET_ARCH 969} 970 971function ggrep() 972{ 973 find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -type f -name "*\.gradle" \ 974 -exec grep --color -n "$@" {} + 975} 976 977function gogrep() 978{ 979 find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -type f -name "*\.go" \ 980 -exec grep --color -n "$@" {} + 981} 982 983function jgrep() 984{ 985 find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -type f -name "*\.java" \ 986 -exec grep --color -n "$@" {} + 987} 988 989function cgrep() 990{ 991 find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -type f \( -name '*.c' -o -name '*.cc' -o -name '*.cpp' -o -name '*.h' -o -name '*.hpp' \) \ 992 -exec grep --color -n "$@" {} + 993} 994 995function resgrep() 996{ 997 local dir 998 for dir in `find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -name res -type d`; do 999 find $dir -type f -name '*\.xml' -exec grep --color -n "$@" {} + 1000 done 1001} 1002 1003function mangrep() 1004{ 1005 find . -name .repo -prune -o -name .git -prune -o -path ./out -prune -o -type f -name 'AndroidManifest.xml' \ 1006 -exec grep --color -n "$@" {} + 1007} 1008 1009function owngrep() 1010{ 1011 find . -name .repo -prune -o -name .git -prune -o -path ./out -prune -o -type f -name 'OWNERS' \ 1012 -exec grep --color -n "$@" {} + 1013} 1014 1015function sepgrep() 1016{ 1017 find . -name .repo -prune -o -name .git -prune -o -path ./out -prune -o -name sepolicy -type d \ 1018 -exec grep --color -n -r --exclude-dir=\.git "$@" {} + 1019} 1020 1021function rcgrep() 1022{ 1023 find . -name .repo -prune -o -name .git -prune -o -name out -prune -o -type f -name "*\.rc*" \ 1024 -exec grep --color -n "$@" {} + 1025} 1026 1027case `uname -s` in 1028 Darwin) 1029 function mgrep() 1030 { 1031 find -E . -name .repo -prune -o -name .git -prune -o -path ./out -prune -o \( -iregex '.*/(Makefile|Makefile\..*|.*\.make|.*\.mak|.*\.mk|.*\.bp)' -o -regex '(.*/)?(build|soong)/.*[^/]*\.go' \) -type f \ 1032 -exec grep --color -n "$@" {} + 1033 } 1034 1035 function treegrep() 1036 { 1037 find -E . -name .repo -prune -o -name .git -prune -o -type f -iregex '.*\.(c|h|cpp|hpp|S|java|xml)' \ 1038 -exec grep --color -n -i "$@" {} + 1039 } 1040 1041 ;; 1042 *) 1043 function mgrep() 1044 { 1045 find . -name .repo -prune -o -name .git -prune -o -path ./out -prune -o \( -regextype posix-egrep -iregex '(.*\/Makefile|.*\/Makefile\..*|.*\.make|.*\.mak|.*\.mk|.*\.bp)' -o -regextype posix-extended -regex '(.*/)?(build|soong)/.*[^/]*\.go' \) -type f \ 1046 -exec grep --color -n "$@" {} + 1047 } 1048 1049 function treegrep() 1050 { 1051 find . -name .repo -prune -o -name .git -prune -o -regextype posix-egrep -iregex '.*\.(c|h|cpp|hpp|S|java|xml)' -type f \ 1052 -exec grep --color -n -i "$@" {} + 1053 } 1054 1055 ;; 1056esac 1057 1058function getprebuilt 1059{ 1060 get_abs_build_var ANDROID_PREBUILTS 1061} 1062 1063function tracedmdump() 1064{ 1065 local T=$(gettop) 1066 if [ ! "$T" ]; then 1067 echo "Couldn't locate the top of the tree. Try setting TOP." 1068 return 1069 fi 1070 local prebuiltdir=$(getprebuilt) 1071 local arch=$(gettargetarch) 1072 local KERNEL=$T/prebuilts/qemu-kernel/$arch/vmlinux-qemu 1073 1074 local TRACE=$1 1075 if [ ! "$TRACE" ] ; then 1076 echo "usage: tracedmdump tracename" 1077 return 1078 fi 1079 1080 if [ ! -r "$KERNEL" ] ; then 1081 echo "Error: cannot find kernel: '$KERNEL'" 1082 return 1083 fi 1084 1085 local BASETRACE=$(basename $TRACE) 1086 if [ "$BASETRACE" = "$TRACE" ] ; then 1087 TRACE=$ANDROID_PRODUCT_OUT/traces/$TRACE 1088 fi 1089 1090 echo "post-processing traces..." 1091 rm -f $TRACE/qtrace.dexlist 1092 post_trace $TRACE 1093 if [ $? -ne 0 ]; then 1094 echo "***" 1095 echo "*** Error: malformed trace. Did you remember to exit the emulator?" 1096 echo "***" 1097 return 1098 fi 1099 echo "generating dexlist output..." 1100 /bin/ls $ANDROID_PRODUCT_OUT/system/framework/*.jar $ANDROID_PRODUCT_OUT/system/app/*.apk $ANDROID_PRODUCT_OUT/data/app/*.apk 2>/dev/null | xargs dexlist > $TRACE/qtrace.dexlist 1101 echo "generating dmtrace data..." 1102 q2dm -r $ANDROID_PRODUCT_OUT/symbols $TRACE $KERNEL $TRACE/dmtrace || return 1103 echo "generating html file..." 1104 dmtracedump -h $TRACE/dmtrace >| $TRACE/dmtrace.html || return 1105 echo "done, see $TRACE/dmtrace.html for details" 1106 echo "or run:" 1107 echo " traceview $TRACE/dmtrace" 1108} 1109 1110# communicate with a running device or emulator, set up necessary state, 1111# and run the hat command. 1112function runhat() 1113{ 1114 # process standard adb options 1115 local adbTarget="" 1116 if [ "$1" = "-d" -o "$1" = "-e" ]; then 1117 adbTarget=$1 1118 shift 1 1119 elif [ "$1" = "-s" ]; then 1120 adbTarget="$1 $2" 1121 shift 2 1122 fi 1123 local adbOptions=${adbTarget} 1124 #echo adbOptions = ${adbOptions} 1125 1126 # runhat options 1127 local targetPid=$1 1128 1129 if [ "$targetPid" = "" ]; then 1130 echo "Usage: runhat [ -d | -e | -s serial ] target-pid" 1131 return 1132 fi 1133 1134 # confirm hat is available 1135 if [ -z $(which hat) ]; then 1136 echo "hat is not available in this configuration." 1137 return 1138 fi 1139 1140 # issue "am" command to cause the hprof dump 1141 local devFile=/data/local/tmp/hprof-$targetPid 1142 echo "Poking $targetPid and waiting for data..." 1143 echo "Storing data at $devFile" 1144 adb ${adbOptions} shell am dumpheap $targetPid $devFile 1145 echo "Press enter when logcat shows \"hprof: heap dump completed\"" 1146 echo -n "> " 1147 read 1148 1149 local localFile=/tmp/$$-hprof 1150 1151 echo "Retrieving file $devFile..." 1152 adb ${adbOptions} pull $devFile $localFile 1153 1154 adb ${adbOptions} shell rm $devFile 1155 1156 echo "Running hat on $localFile" 1157 echo "View the output by pointing your browser at http://localhost:7000/" 1158 echo "" 1159 hat -JXmx512m $localFile 1160} 1161 1162function getbugreports() 1163{ 1164 local reports=(`adb shell ls /sdcard/bugreports | tr -d '\r'`) 1165 1166 if [ ! "$reports" ]; then 1167 echo "Could not locate any bugreports." 1168 return 1169 fi 1170 1171 local report 1172 for report in ${reports[@]} 1173 do 1174 echo "/sdcard/bugreports/${report}" 1175 adb pull /sdcard/bugreports/${report} ${report} 1176 gunzip ${report} 1177 done 1178} 1179 1180function getsdcardpath() 1181{ 1182 adb ${adbOptions} shell echo -n \$\{EXTERNAL_STORAGE\} 1183} 1184 1185function getscreenshotpath() 1186{ 1187 echo "$(getsdcardpath)/Pictures/Screenshots" 1188} 1189 1190function getlastscreenshot() 1191{ 1192 local screenshot_path=$(getscreenshotpath) 1193 local screenshot=`adb ${adbOptions} ls ${screenshot_path} | grep Screenshot_[0-9-]*.*\.png | sort -rk 3 | cut -d " " -f 4 | head -n 1` 1194 if [ "$screenshot" = "" ]; then 1195 echo "No screenshots found." 1196 return 1197 fi 1198 echo "${screenshot}" 1199 adb ${adbOptions} pull ${screenshot_path}/${screenshot} 1200} 1201 1202function startviewserver() 1203{ 1204 local port=4939 1205 if [ $# -gt 0 ]; then 1206 port=$1 1207 fi 1208 adb shell service call window 1 i32 $port 1209} 1210 1211function stopviewserver() 1212{ 1213 adb shell service call window 2 1214} 1215 1216function isviewserverstarted() 1217{ 1218 adb shell service call window 3 1219} 1220 1221function key_home() 1222{ 1223 adb shell input keyevent 3 1224} 1225 1226function key_back() 1227{ 1228 adb shell input keyevent 4 1229} 1230 1231function key_menu() 1232{ 1233 adb shell input keyevent 82 1234} 1235 1236function smoketest() 1237{ 1238 if [ ! "$ANDROID_PRODUCT_OUT" ]; then 1239 echo "Couldn't locate output files. Try running 'lunch' first." >&2 1240 return 1241 fi 1242 local T=$(gettop) 1243 if [ ! "$T" ]; then 1244 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 1245 return 1246 fi 1247 1248 (\cd "$T" && mmm tests/SmokeTest) && 1249 adb uninstall com.android.smoketest > /dev/null && 1250 adb uninstall com.android.smoketest.tests > /dev/null && 1251 adb install $ANDROID_PRODUCT_OUT/data/app/SmokeTestApp.apk && 1252 adb install $ANDROID_PRODUCT_OUT/data/app/SmokeTest.apk && 1253 adb shell am instrument -w com.android.smoketest.tests/android.test.InstrumentationTestRunner 1254} 1255 1256# simple shortcut to the runtest command 1257function runtest() 1258{ 1259 local T=$(gettop) 1260 if [ ! "$T" ]; then 1261 echo "Couldn't locate the top of the tree. Try setting TOP." >&2 1262 return 1263 fi 1264 ("$T"/development/testrunner/runtest.py $@) 1265} 1266 1267function godir () { 1268 if [[ -z "$1" ]]; then 1269 echo "Usage: godir <regex>" 1270 return 1271 fi 1272 local T=$(gettop) 1273 local FILELIST 1274 if [ ! "$OUT_DIR" = "" ]; then 1275 mkdir -p $OUT_DIR 1276 FILELIST=$OUT_DIR/filelist 1277 else 1278 FILELIST=$T/filelist 1279 fi 1280 if [[ ! -f $FILELIST ]]; then 1281 echo -n "Creating index..." 1282 (\cd $T; find . -wholename ./out -prune -o -wholename ./.repo -prune -o -type f > $FILELIST) 1283 echo " Done" 1284 echo "" 1285 fi 1286 local lines 1287 lines=($(\grep "$1" $FILELIST | sed -e 's/\/[^/]*$//' | sort | uniq)) 1288 if [[ ${#lines[@]} = 0 ]]; then 1289 echo "Not found" 1290 return 1291 fi 1292 local pathname 1293 local choice 1294 if [[ ${#lines[@]} > 1 ]]; then 1295 while [[ -z "$pathname" ]]; do 1296 local index=1 1297 local line 1298 for line in ${lines[@]}; do 1299 printf "%6s %s\n" "[$index]" $line 1300 index=$(($index + 1)) 1301 done 1302 echo 1303 echo -n "Select one: " 1304 unset choice 1305 read choice 1306 if [[ $choice -gt ${#lines[@]} || $choice -lt 1 ]]; then 1307 echo "Invalid choice" 1308 continue 1309 fi 1310 pathname=${lines[@]:$(($choice-1)):1} 1311 done 1312 else 1313 pathname=${lines[@]:0:1} 1314 fi 1315 \cd $T/$pathname 1316} 1317 1318# Update module-info.json in out. 1319function refreshmod() { 1320 if [ ! "$ANDROID_PRODUCT_OUT" ]; then 1321 echo "No ANDROID_PRODUCT_OUT. Try running 'lunch' first." >&2 1322 return 1 1323 fi 1324 1325 echo "Refreshing modules (building module-info.json). Log at $ANDROID_PRODUCT_OUT/module-info.json.build.log." >&2 1326 1327 # for the output of the next command 1328 mkdir -p $ANDROID_PRODUCT_OUT || return 1 1329 1330 # Note, can't use absolute path because of the way make works. 1331 m out/target/product/$(get_build_var TARGET_DEVICE)/module-info.json \ 1332 > $ANDROID_PRODUCT_OUT/module-info.json.build.log 2>&1 1333} 1334 1335# List all modules for the current device, as cached in module-info.json. If any build change is 1336# made and it should be reflected in the output, you should run 'refreshmod' first. 1337function allmod() { 1338 if [ ! "$ANDROID_PRODUCT_OUT" ]; then 1339 echo "No ANDROID_PRODUCT_OUT. Try running 'lunch' first." >&2 1340 return 1 1341 fi 1342 1343 if [ ! -f "$ANDROID_PRODUCT_OUT/module-info.json" ]; then 1344 echo "Could not find module-info.json. It will only be built once, and it can be updated with 'refreshmod'" >&2 1345 refreshmod || return 1 1346 fi 1347 1348 python -c "import json; print('\n'.join(sorted(json.load(open('$ANDROID_PRODUCT_OUT/module-info.json')).keys())))" 1349} 1350 1351# Get the path of a specific module in the android tree, as cached in module-info.json. If any build change 1352# is made, and it should be reflected in the output, you should run 'refreshmod' first. 1353function pathmod() { 1354 if [ ! "$ANDROID_PRODUCT_OUT" ]; then 1355 echo "No ANDROID_PRODUCT_OUT. Try running 'lunch' first." >&2 1356 return 1 1357 fi 1358 1359 if [[ $# -ne 1 ]]; then 1360 echo "usage: pathmod <module>" >&2 1361 return 1 1362 fi 1363 1364 if [ ! -f "$ANDROID_PRODUCT_OUT/module-info.json" ]; then 1365 echo "Could not find module-info.json. It will only be built once, and it can be updated with 'refreshmod'" >&2 1366 refreshmod || return 1 1367 fi 1368 1369 local relpath=$(python -c "import json, os 1370module = '$1' 1371module_info = json.load(open('$ANDROID_PRODUCT_OUT/module-info.json')) 1372if module not in module_info: 1373 exit(1) 1374print(module_info[module]['path'][0])" 2>/dev/null) 1375 1376 if [ -z "$relpath" ]; then 1377 echo "Could not find module '$1' (try 'refreshmod' if there have been build changes?)." >&2 1378 return 1 1379 else 1380 echo "$ANDROID_BUILD_TOP/$relpath" 1381 fi 1382} 1383 1384# Go to a specific module in the android tree, as cached in module-info.json. If any build change 1385# is made, and it should be reflected in the output, you should run 'refreshmod' first. 1386function gomod() { 1387 if [[ $# -ne 1 ]]; then 1388 echo "usage: gomod <module>" >&2 1389 return 1 1390 fi 1391 1392 local path="$(pathmod $@)" 1393 if [ -z "$path" ]; then 1394 return 1 1395 fi 1396 cd $path 1397} 1398 1399function _complete_android_module_names() { 1400 local word=${COMP_WORDS[COMP_CWORD]} 1401 COMPREPLY=( $(allmod | grep -E "^$word") ) 1402} 1403 1404# Print colored exit condition 1405function pez { 1406 "$@" 1407 local retval=$? 1408 if [ $retval -ne 0 ] 1409 then 1410 echo $'\E'"[0;31mFAILURE\e[00m" 1411 else 1412 echo $'\E'"[0;32mSUCCESS\e[00m" 1413 fi 1414 return $retval 1415} 1416 1417function get_make_command() 1418{ 1419 # If we're in the top of an Android tree, use soong_ui.bash instead of make 1420 if [ -f build/soong/soong_ui.bash ]; then 1421 # Always use the real make if -C is passed in 1422 for arg in "$@"; do 1423 if [[ $arg == -C* ]]; then 1424 echo command make 1425 return 1426 fi 1427 done 1428 echo build/soong/soong_ui.bash --make-mode 1429 else 1430 echo command make 1431 fi 1432} 1433 1434function _wrap_build() 1435{ 1436 if [[ "${ANDROID_QUIET_BUILD:-}" == true ]]; then 1437 "$@" 1438 return $? 1439 fi 1440 local start_time=$(date +"%s") 1441 "$@" 1442 local ret=$? 1443 local end_time=$(date +"%s") 1444 local tdiff=$(($end_time-$start_time)) 1445 local hours=$(($tdiff / 3600 )) 1446 local mins=$((($tdiff % 3600) / 60)) 1447 local secs=$(($tdiff % 60)) 1448 local ncolors=$(tput colors 2>/dev/null) 1449 if [ -n "$ncolors" ] && [ $ncolors -ge 8 ]; then 1450 color_failed=$'\E'"[0;31m" 1451 color_success=$'\E'"[0;32m" 1452 color_reset=$'\E'"[00m" 1453 else 1454 color_failed="" 1455 color_success="" 1456 color_reset="" 1457 fi 1458 echo 1459 if [ $ret -eq 0 ] ; then 1460 echo -n "${color_success}#### build completed successfully " 1461 else 1462 echo -n "${color_failed}#### failed to build some targets " 1463 fi 1464 if [ $hours -gt 0 ] ; then 1465 printf "(%02g:%02g:%02g (hh:mm:ss))" $hours $mins $secs 1466 elif [ $mins -gt 0 ] ; then 1467 printf "(%02g:%02g (mm:ss))" $mins $secs 1468 elif [ $secs -gt 0 ] ; then 1469 printf "(%s seconds)" $secs 1470 fi 1471 echo " ####${color_reset}" 1472 echo 1473 return $ret 1474} 1475 1476function _trigger_build() 1477( 1478 local -r bc="$1"; shift 1479 if T="$(gettop)"; then 1480 _wrap_build "$T/build/soong/soong_ui.bash" --build-mode --${bc} --dir="$(pwd)" "$@" 1481 else 1482 echo "Couldn't locate the top of the tree. Try setting TOP." 1483 fi 1484) 1485 1486function m() 1487( 1488 _trigger_build "all-modules" "$@" 1489) 1490 1491function mm() 1492( 1493 _trigger_build "modules-in-a-dir-no-deps" "$@" 1494) 1495 1496function mmm() 1497( 1498 _trigger_build "modules-in-dirs-no-deps" "$@" 1499) 1500 1501function mma() 1502( 1503 _trigger_build "modules-in-a-dir" "$@" 1504) 1505 1506function mmma() 1507( 1508 _trigger_build "modules-in-dirs" "$@" 1509) 1510 1511function make() 1512{ 1513 _wrap_build $(get_make_command "$@") "$@" 1514} 1515 1516function provision() 1517{ 1518 if [ ! "$ANDROID_PRODUCT_OUT" ]; then 1519 echo "Couldn't locate output files. Try running 'lunch' first." >&2 1520 return 1 1521 fi 1522 if [ ! -e "$ANDROID_PRODUCT_OUT/provision-device" ]; then 1523 echo "There is no provisioning script for the device." >&2 1524 return 1 1525 fi 1526 1527 # Check if user really wants to do this. 1528 if [ "$1" = "--no-confirmation" ]; then 1529 shift 1 1530 else 1531 echo "This action will reflash your device." 1532 echo "" 1533 echo "ALL DATA ON THE DEVICE WILL BE IRREVOCABLY ERASED." 1534 echo "" 1535 echo -n "Are you sure you want to do this (yes/no)? " 1536 read 1537 if [[ "${REPLY}" != "yes" ]] ; then 1538 echo "Not taking any action. Exiting." >&2 1539 return 1 1540 fi 1541 fi 1542 "$ANDROID_PRODUCT_OUT/provision-device" "$@" 1543} 1544 1545# Zsh needs bashcompinit called to support bash-style completion. 1546function enable_zsh_completion() { 1547 # Don't override user's options if bash-style completion is already enabled. 1548 if ! declare -f complete >/dev/null; then 1549 autoload -U compinit && compinit 1550 autoload -U bashcompinit && bashcompinit 1551 fi 1552} 1553 1554function validate_current_shell() { 1555 local current_sh="$(ps -o command -p $$)" 1556 case "$current_sh" in 1557 *bash*) 1558 function check_type() { type -t "$1"; } 1559 ;; 1560 *zsh*) 1561 function check_type() { type "$1"; } 1562 enable_zsh_completion ;; 1563 *) 1564 echo -e "WARNING: Only bash and zsh are supported.\nUse of other shell would lead to erroneous results." 1565 ;; 1566 esac 1567} 1568 1569# Execute the contents of any vendorsetup.sh files we can find. 1570# Unless we find an allowed-vendorsetup_sh-files file, in which case we'll only 1571# load those. 1572# 1573# This allows loading only approved vendorsetup.sh files 1574function source_vendorsetup() { 1575 unset VENDOR_PYTHONPATH 1576 allowed= 1577 for f in $(find -L device vendor product -maxdepth 4 -name 'allowed-vendorsetup_sh-files' 2>/dev/null | sort); do 1578 if [ -n "$allowed" ]; then 1579 echo "More than one 'allowed_vendorsetup_sh-files' file found, not including any vendorsetup.sh files:" 1580 echo " $allowed" 1581 echo " $f" 1582 return 1583 fi 1584 allowed="$f" 1585 done 1586 1587 allowed_files= 1588 [ -n "$allowed" ] && allowed_files=$(cat "$allowed") 1589 for dir in device vendor product; do 1590 for f in $(test -d $dir && \ 1591 find -L $dir -maxdepth 4 -name 'vendorsetup.sh' 2>/dev/null | sort); do 1592 1593 if [[ -z "$allowed" || "$allowed_files" =~ $f ]]; then 1594 echo "including $f"; . "$f" 1595 else 1596 echo "ignoring $f, not in $allowed" 1597 fi 1598 done 1599 done 1600} 1601 1602validate_current_shell 1603source_vendorsetup 1604addcompletions 1605