1# Copyright (C) 2008 The Android Open Source Project 2# 3# Licensed under the Apache License, Version 2.0 (the "License"); 4# you may not use this file except in compliance with the License. 5# You may obtain a copy of the License at 6# 7# http://www.apache.org/licenses/LICENSE-2.0 8# 9# Unless required by applicable law or agreed to in writing, software 10# distributed under the License is distributed on an "AS IS" BASIS, 11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12# See the License for the specific language governing permissions and 13# limitations under the License. 14# 15# This file is included by other shell scripts; do not execute it directly. 16# It contains common definitions. 17# 18PROGNAME=`basename $0` 19 20## Logging support 21## 22VERBOSE=yes 23VERBOSE2=no 24 25log () 26{ 27 if [ "$VERBOSE" = "yes" ] ; then 28 echo "$1" 29 fi 30} 31 32log2 () 33{ 34 if [ "$VERBOSE2" = "yes" ] ; then 35 echo "$1" 36 fi 37} 38 39## Utilities 40## 41 42# return the value of a given named variable 43# $1: variable name 44# 45var_value () 46{ 47 # find a better way to do that ? 48 local result 49 eval result="$`echo $1`" 50 echo $result 51} 52 53# convert to uppercase 54to_uppercase () 55{ 56 echo $1 | tr "[:lower:]" "[:upper:]" 57} 58 59## Normalize OS and CPU 60## 61 62CPU=`uname -m` 63case "$CPU" in 64 i?86) CPU=x86 65 ;; 66 amd64) CPU=x86_64 67 ;; 68 powerpc) CPU=ppc 69 ;; 70esac 71 72log2 "CPU=$CPU" 73 74# at this point, the supported values for CPU are: 75# x86 76# x86_64 77# ppc 78# 79# other values may be possible but haven't been tested 80# 81 82EXE="" 83OS=`uname -s` 84case "$OS" in 85 Darwin) 86 OS=darwin-$CPU 87 ;; 88 Linux) 89 # note that building 32-bit binaries on x86_64 is handled later 90 OS=linux-$CPU 91 ;; 92 CYGWIN*|*_NT-*) 93 OS=windows 94 EXE=.exe 95 if [ "x$OSTYPE" = xcygwin ] ; then 96 OS=cygwin 97 HOST_CFLAGS="$CFLAGS -mno-cygwin" 98 HOST_LDFLAGS="$LDFLAGS -mno-cygwin" 99 fi 100 ;; 101esac 102 103log2 "OS=$OS" 104log2 "EXE=$EXE" 105 106# at this point, the value of OS should be one of the following: 107# linux-x86 108# linux-x86_64 109# darwin-x86 110# darwin-ppc 111# windows (MSys) 112# cygwin 113# 114# Note that cygwin is treated as a special case because it behaves very differently 115# for a few things 116# 117# other values may be possible but have not been tested 118 119# define HOST_OS as $OS without any cpu-specific suffix 120# 121case $OS in 122 linux-*) HOST_OS=linux 123 ;; 124 darwin-*) HOST_OS=darwin 125 ;; 126 *) HOST_OS=$OS 127esac 128 129# define HOST_ARCH as the $CPU 130HOST_ARCH=$CPU 131 132#### Toolchain support 133#### 134 135# Various probes are going to need to run a small C program 136TMPC=/tmp/android-$$-test.c 137TMPO=/tmp/android-$$-test.o 138TMPE=/tmp/android-$$-test$EXE 139TMPL=/tmp/android-$$-test.log 140 141# cleanup temporary files 142clean_temp () 143{ 144 rm -f $TMPC $TMPO $TMPL $TMPE 145} 146 147# cleanup temp files then exit with an error 148clean_exit () 149{ 150 clean_temp 151 exit 1 152} 153 154# this function should be called to enforce the build of 32-bit binaries on 64-bit systems 155# that support it. 156FORCE_32BIT=no 157force_32bit_binaries () 158{ 159 if [ $CPU = x86_64 ] ; then 160 FORCE_32BIT=yes 161 case $OS in 162 linux-x86_64) OS=linux-x86 ;; 163 darwin-x86_64) OS=darwin-x86 ;; 164 esac 165 HOST_ARCH=x86 166 CPU=x86 167 log "Check32Bits: Forcing generation of 32-bit binaries (--try-64 to disable)" 168 fi 169} 170 171# Cygwin is normally not supported, unless you call this function 172# 173enable_cygwin () 174{ 175 if [ $OS = cygwin ] ; then 176 CFLAGS="$CFLAGS -mno-cygwin" 177 LDFLAGS="$LDFLAGS -mno-cygwin" 178 OS=windows 179 HOST_OS=windows 180 fi 181} 182 183# this function will setup the compiler and linker and check that they work as advertized 184# note that you should call 'force_32bit_binaries' before this one if you want it to work 185# as advertized. 186# 187setup_toolchain () 188{ 189 if [ "$OS" = cygwin ] ; then 190 echo "Do not compile this program or library with Cygwin, use MSYS instead !!" 191 echo "As an experimental feature, you can try to --try-cygwin option to override this" 192 exit 2 193 fi 194 195 if [ -z "$CC" ] ; then 196 CC=gcc 197 if [ $CPU = "powerpc" ] ; then 198 CC=gcc-3.3 199 fi 200 fi 201 202 # check that we can compile a trivial C program with this compiler 203 cat > $TMPC <<EOF 204int main(void) {} 205EOF 206 207 if [ $FORCE_32BIT = yes ] ; then 208 CFLAGS="$CFLAGS -m32" 209 LDFLAGS="$LDFLAGS -m32" 210 compile 211 if [ $? != 0 ] ; then 212 # sometimes, we need to also tell the assembler to generate 32-bit binaries 213 # this is highly dependent on your GCC installation (and no, we can't set 214 # this flag all the time) 215 CFLAGS="$CFLAGS -Wa,--32" 216 compile 217 fi 218 fi 219 220 compile 221 if [ $? != 0 ] ; then 222 echo "your C compiler doesn't seem to work:" 223 cat $TMPL 224 clean_exit 225 fi 226 log "CC : compiler check ok ($CC)" 227 228 # check that we can link the trivial program into an executable 229 if [ -z "$LD" ] ; then 230 LD=$CC 231 fi 232 link 233 if [ $? != 0 ] ; then 234 OLD_LD=$LD 235 LD=gcc 236 compile 237 link 238 if [ $? != 0 ] ; then 239 LD=$OLD_LD 240 echo "your linker doesn't seem to work:" 241 cat $TMPL 242 clean_exit 243 fi 244 fi 245 log "LD : linker check ok ($LD)" 246} 247 248# try to compile the current source file in $TMPC into an object 249# stores the error log into $TMPL 250# 251compile () 252{ 253 log2 "Object : $CC -o $TMPO -c $CFLAGS $TMPC" 254 $CC -o $TMPO -c $CFLAGS $TMPC 2> $TMPL 255} 256 257# try to link the recently built file into an executable. error log in $TMPL 258# 259link() 260{ 261 log2 "Link : $LD -o $TMPE $TMPO $LDFLAGS" 262 $LD -o $TMPE $TMPO $LDFLAGS 2> $TMPL 263} 264 265# run a command 266# 267execute() 268{ 269 log2 "Running: $*" 270 $* 271} 272 273# perform a simple compile / link / run of the source file in $TMPC 274compile_exec_run() 275{ 276 log2 "RunExec : $CC -o $TMPE $CFLAGS $TMPC" 277 compile 278 if [ $? != 0 ] ; then 279 echo "Failure to compile test program" 280 cat $TMPC 281 cat $TMPL 282 clean_exit 283 fi 284 link 285 if [ $? != 0 ] ; then 286 echo "Failure to link test program" 287 cat $TMPC 288 echo "------" 289 cat $TMPL 290 clean_exit 291 fi 292 $TMPE 293} 294 295## Feature test support 296## 297 298# Each feature test allows us to check against a single target-specific feature 299# We run the feature checks in a Makefile in order to be able to do them in 300# parallel, and we also have some cached values in our output directory, just 301# in case. 302# 303# check that a given C program in $TMPC can be compiled on the host system 304# $1: variable name which will be set to "yes" or "no" depending on result 305# you can define EXTRA_CFLAGS for extra C compiler flags 306# for convenience, this variable will be unset by the function 307# 308feature_check_compile () 309{ 310 local result_cc=yes 311 local OLD_CFLAGS 312 OLD_CFLAGS="$CFLAGS" 313 CFLAGS="$CFLAGS $EXTRA_CFLAGS" 314 compile 315 if [ $? != 0 ] ; then 316 result_cc=no 317 fi 318 eval $1=$result_cc 319 EXTRA_CFLAGS= 320 CFLAGS=$OLD_CFLAGS 321} 322 323# check that a given C program $TMPC can be linked on the host system 324# $1: variable name which will be set to "yes" or "no" depending on result 325# you can define EXTRA_CFLAGS for extra C compiler flags 326# you can define EXTRA_LDFLAGS for extra linker flags 327# for convenience, these variables will be unset by the function 328# 329feature_check_link () 330{ 331 local result_cl=yes 332 local OLD_CFLAGS OLD_LDFLAGS 333 OLD_CFLAGS=$CFLAGS 334 OLD_LDFLAGS=$LDFLAGS 335 CFLAGS="$CFLAGS $EXTRA_CFLAGS" 336 LDFLAGS="$LDFLAGS $EXTRA_LDFLAGS" 337 compile 338 if [ $? != 0 ] ; then 339 result_cl=no 340 else 341 link 342 if [ $? != 0 ] ; then 343 result_cl=no 344 fi 345 fi 346 CFLAGS=$OLD_CFLAGS 347 LDFLAGS=$OLD_LDFLAGS 348 eval $1=$result_cl 349} 350 351# check that a given C header file exists on the host system 352# $1: variable name which will be set to "yes" or "no" depending on result 353# $2: header name 354# 355# you can define EXTRA_CFLAGS for extra C compiler flags 356# for convenience, this variable will be unset by the function. 357# 358feature_check_header () 359{ 360 local result_ch 361 log2 "HeaderChk : $2" 362 echo "#include $2" > $TMPC 363 cat >> $TMPC <<EOF 364 int main(void) { return 0; } 365EOF 366 feature_check_compile result_ch 367 eval $1=$result_ch 368 #eval result=$`echo $1` 369 #log "Host : $1=$result_ch" 370} 371 372# run the test program that is in $TMPC and set its exit status 373# in the $1 variable. 374# you can define EXTRA_CFLAGS and EXTRA_LDFLAGS 375# 376feature_run_exec () 377{ 378 local run_exec_result 379 local OLD_CFLAGS="$CFLAGS" 380 local OLD_LDFLAGS="$LDFLAGS" 381 CFLAGS="$CFLAGS $EXTRA_CFLAGS" 382 LDFLAGS="$LDFLAGS $EXTRA_LDFLAGS" 383 compile_exec_run 384 run_exec_result=$? 385 CFLAGS="$OLD_CFLAGS" 386 LDFLAGS="$OLD_LDFLAGS" 387 eval $1=$run_exec_result 388 log "Host : $1=$run_exec_result" 389} 390 391## Android build system auto-detection 392## 393 394# check whether we're running within the Android build system 395# sets the variable IN_ANDROID_BUILD to either "yes" or "no" 396# 397# in case of success, defines ANDROID_TOP to point to the top 398# of the Android source tree. 399# 400check_android_build () 401{ 402 unset ANDROID_TOP 403 IN_ANDROID_BUILD=no 404 405 if [ -z "$ANDROID_PRODUCT_OUT" ] ; then 406 return ; 407 fi 408 409 ANDROID_TOP=`cd $ANDROID_PRODUCT_OUT/../../../.. && pwd` 410 log "ANDROID_TOP found at $ANDROID_TOP" 411 # $ANDROID_TOP/config/envsetup.make is for the old tree layout 412 # $ANDROID_TOP/build/envsetup.sh is for the new one 413 ANDROID_CONFIG_MK=$ANDROID_TOP/build/core/config.mk 414 if [ ! -f $ANDROID_CONFIG_MK ] ; then 415 ANDROID_CONFIG_MK=$ANDROID_TOP/config/envsetup.make 416 fi 417 if [ ! -f $ANDROID_CONFIG_MK ] ; then 418 echo "Weird: Cannot find build system root defaulting to non-Android build" 419 unset ANDROID_TOP 420 return 421 fi 422 # normalize ANDROID_TOP, we don't want a trailing / 423 ANDROID_TOPDIR=`dirname $ANDROID_TOP` 424 if [ "$ANDROID_TOPDIR" != "." ] ; then 425 ANDROID_TOP=$ANDROID_TOPDIR/`basename $ANDROID_TOP` 426 fi 427 IN_ANDROID_BUILD=yes 428} 429 430# Get the value of an Android build variable as an absolute path. 431# you should only call this if IN_ANDROID_BUILD is "yes" 432# 433get_android_abs_build_var () 434{ 435 (cd $ANDROID_TOP && CALLED_FROM_SETUP=true BUILD_SYSTEM=build/core make -f $ANDROID_CONFIG_MK dumpvar-abs-$1) 436} 437 438# Locate the Android prebuilt directory for your os 439# you should only call this if IN_ANDROID_BUILD is "yes" 440# 441# This will set ANDROID_PREBUILT_HOST_TAG and ANDROID_PREBUILT 442# 443locate_android_prebuilt () 444{ 445 # locate prebuilt directory 446 ANDROID_PREBUILT_HOST_TAG=$OS 447 ANDROID_PREBUILT=$ANDROID_TOP/prebuilt/$ANDROID_PREBUILT_HOST_TAG 448 if [ ! -d $ANDROID_PREBUILT ] ; then 449 # this can happen when building on x86_64 450 case $OS in 451 linux-x86_64) 452 ANDROID_PREBUILT_HOST_TAG=linux-x86 453 ANDROID_PREBUILT=$ANDROID_TOP/prebuilt/$ANDROID_PREBUILT_HOST_TAG 454 log "Forcing usage of 32-bit prebuilts" 455 force_32bit_binaries 456 ;; 457 *) 458 esac 459 if [ ! -d $ANDROID_PREBUILT ] ; then 460 echo "Can't find the prebuilt directory $ANDROID_PREBUILT in Android build" 461 exit 1 462 fi 463 fi 464 log "Prebuilt : ANDROID_PREBUILT=$ANDROID_PREBUILT" 465} 466 467## Build configuration file support 468## you must define $config_mk before calling this function 469## 470create_config_mk () 471{ 472 # create the directory if needed 473 local config_dir 474 config_mk=${config_mk:-objs/config.make} 475 config_dir=`dirname $config_mk` 476 mkdir -p $config_dir 2> $TMPL 477 if [ $? != 0 ] ; then 478 echo "Can't create directory for build config file: $config_dir" 479 cat $TMPL 480 clean_exit 481 fi 482 483 # re-create the start of the configuration file 484 log "Generate : $config_mk" 485 486 echo "# This file was autogenerated by $PROGNAME. Do not edit !" > $config_mk 487 echo "OS := $OS" >> $config_mk 488 echo "HOST_OS := $HOST_OS" >> $config_mk 489 echo "HOST_ARCH := $HOST_ARCH" >> $config_mk 490 echo "CC := $CC" >> $config_mk 491 echo "HOST_CC := $CC" >> $config_mk 492 echo "LD := $LD" >> $config_mk 493 echo "CFLAGS := $CFLAGS" >> $config_mk 494 echo "LDFLAGS := $LDFLAGS" >> $config_mk 495} 496 497add_android_config_mk () 498{ 499 echo "" >> $config_mk 500 echo "TARGET_ARCH := arm" >> $config_mk 501 echo "HOST_PREBUILT_TAG := $ANDROID_PREBUILT_HOST_TAG" >> $config_mk 502 echo "PREBUILT := $ANDROID_PREBUILT" >> $config_mk 503} 504