| #!/bin/sh |
| |
| # Abort execution as soon as an error is encountered |
| # That way the script do not let the user think the process completed correctly |
| # and leave the opportunity to fix the problem and restart compilation where |
| # it stopped |
| set -e |
| |
| # this is where this script will store downloaded files and check for already |
| # downloaded files |
| dlwhere="${RBDEV_DOWNLOAD:-/tmp/rbdev-dl}" |
| |
| # will append the target string to the prefix dir mentioned here |
| # Note that the user running this script must be able to do make install in |
| # this given prefix directory. Also make sure that this given root dir |
| # exists. |
| prefix="${RBDEV_PREFIX:-/usr/local}" |
| |
| # This directory is used to extract all files and to build everything in. It |
| # must not exist before this script is invoked (as a security measure). |
| builddir="${RBDEV_BUILD:-/tmp/rbdev-build}" |
| |
| # This script needs to use GNU Make. On Linux systems, GNU Make is invoked |
| # by running the "make" command, on most BSD systems, GNU Make is invoked |
| # by running the "gmake" command. Set the "make" variable accordingly. |
| if [ -f "`which gmake 2>/dev/null`" ]; then |
| make="gmake" |
| else |
| make="make" |
| fi |
| |
| if [ -z $GNU_MIRROR ] ; then |
| GNU_MIRROR=http://mirrors.kernel.org/gnu |
| fi |
| |
| # These are the tools this script requires and depends upon. |
| reqtools="gcc bzip2 gzip make patch makeinfo automake libtool autoconf flex bison" |
| |
| ############################################################################## |
| # Functions: |
| |
| findtool(){ |
| file="$1" |
| |
| IFS=":" |
| for path in $PATH |
| do |
| # echo "Checks for $file in $path" >&2 |
| if test -f "$path/$file"; then |
| echo "$path/$file" |
| return |
| fi |
| done |
| } |
| |
| input() { |
| read response |
| echo $response |
| } |
| |
| #$1 file |
| #$2 URL"root |
| getfile() { |
| if test -f $dlwhere/$1; then |
| echo "ROCKBOXDEV: Skipping download of $2/$1: File already exists" |
| return |
| fi |
| tool=`findtool curl` |
| if test -z "$tool"; then |
| tool=`findtool wget` |
| if test -n "$tool"; then |
| # wget download |
| echo "ROCKBOXDEV: Downloading $2/$1 using wget" |
| $tool -T 60 -O $dlwhere/$1 $2/$1 |
| fi |
| else |
| # curl download |
| echo "ROCKBOXDEV: Downloading $2/$1 using curl" |
| $tool -Lo $dlwhere/$1 $2/$1 |
| fi |
| |
| if [ $? -ne 0 ] ; then |
| echo "ROCKBOXDEV: couldn't download the file!" |
| echo "ROCKBOXDEV: check your internet connection" |
| exit |
| fi |
| |
| if test -z "$tool"; then |
| echo "ROCKBOXDEV: No downloader tool found!" |
| echo "ROCKBOXDEV: Please install curl or wget and re-run the script" |
| exit |
| fi |
| } |
| |
| |
| build() { |
| toolname="$1" |
| target="$2" |
| version="$3" |
| patch="$4" |
| configure_params="$5" |
| needs_libs="$6" |
| |
| patch_url="http://www.rockbox.org/gcc" |
| |
| case $toolname in |
| gcc) |
| file="gcc-core-$version.tar.bz2" |
| url="$GNU_MIRROR/gcc/gcc-$version" |
| ;; |
| |
| binutils) |
| file="binutils-$version.tar.bz2" |
| url="$GNU_MIRROR/binutils" |
| ;; |
| |
| ctng) |
| file="crosstool-ng-$version.tar.bz2" |
| url="http://crosstool-ng.org/download/crosstool-ng" |
| ;; |
| *) |
| echo "ROCKBOXDEV: Bad toolname $toolname" |
| exit |
| ;; |
| esac |
| |
| # create build directory |
| if test -d $builddir; then |
| if test ! -w $builddir; then |
| echo "ROCKBOXDEV: No write permission for $builddir" |
| exit |
| fi |
| else |
| mkdir -p $builddir |
| fi |
| |
| # download source tarball |
| if test ! -f "$dlwhere/$file"; then |
| getfile "$file" "$url" |
| fi |
| |
| # download patch |
| for p in $patch; do |
| if test ! -f "$dlwhere/$p"; then |
| getfile "$p" "$patch_url" |
| fi |
| done |
| |
| cd $builddir |
| |
| echo "ROCKBOXDEV: extracting $file" |
| tar xjf $dlwhere/$file |
| |
| # do we have a patch? |
| for p in $patch; do |
| echo "ROCKBOXDEV: applying patch $p" |
| |
| # apply the patch |
| (cd $builddir/$toolname-$version && patch -p1 < "$dlwhere/$p") |
| |
| # check if the patch applied cleanly |
| if [ $? -gt 0 ]; then |
| echo "ROCKBOXDEV: failed to apply patch $p" |
| exit |
| fi |
| done |
| |
| # kludge to avoid having to install GMP, MPFR and MPC, for new gcc |
| if test -n "$needs_libs"; then |
| cd "gcc-$version" |
| if (echo $needs_libs | grep -q gmp && test ! -d gmp); then |
| echo "ROCKBOXDEV: Getting GMP" |
| if test ! -f $dlwhere/gmp-4.3.2.tar.bz2; then |
| getfile "gmp-4.3.2.tar.bz2" "$GNU_MIRROR/gmp" |
| fi |
| tar xjf $dlwhere/gmp-4.3.2.tar.bz2 |
| ln -s gmp-4.3.2 gmp |
| fi |
| |
| if (echo $needs_libs | grep -q mpfr && test ! -d mpfr); then |
| echo "ROCKBOXDEV: Getting MPFR" |
| if test ! -f $dlwhere/mpfr-2.4.2.tar.bz2; then |
| getfile "mpfr-2.4.2.tar.bz2" "$GNU_MIRROR/mpfr" |
| fi |
| tar xjf $dlwhere/mpfr-2.4.2.tar.bz2 |
| ln -s mpfr-2.4.2 mpfr |
| fi |
| |
| if (echo $needs_libs | grep -q mpc && test ! -d mpc); then |
| echo "ROCKBOXDEV: Getting MPC" |
| if test ! -f $dlwhere/mpc-0.8.1.tar.gz; then |
| getfile "mpc-0.8.1.tar.gz" "http://www.multiprecision.org/mpc/download" |
| fi |
| tar xzf $dlwhere/mpc-0.8.1.tar.gz |
| ln -s mpc-0.8.1 mpc |
| fi |
| cd $builddir |
| fi |
| |
| echo "ROCKBOXDEV: mkdir build-$toolname" |
| mkdir build-$toolname |
| |
| echo "ROCKBOXDEV: cd build-$toolname" |
| cd build-$toolname |
| |
| echo "ROCKBOXDEV: $toolname/configure" |
| case $toolname in |
| ctng) # ct-ng doesnt support out-of-tree build and the src folder is named differently |
| toolname="crosstool-ng" |
| cp -r ../$toolname-$version/* ../$toolname-$version/.version . |
| ./configure --prefix=$prefix $configure_params |
| ;; |
| *) |
| CFLAGS=-U_FORTIFY_SOURCE ../$toolname-$version/configure --target=$target --prefix=$prefix --enable-languages=c --disable-libssp --disable-docs $configure_params |
| ;; |
| esac |
| |
| echo "ROCKBOXDEV: $toolname/make" |
| $make |
| |
| echo "ROCKBOXDEV: $toolname/make install" |
| $make install |
| |
| echo "ROCKBOXDEV: rm -rf build-$toolname $toolname-$version" |
| cd .. |
| rm -rf build-$toolname $toolname-$version |
| } |
| |
| |
| make_ctng() { |
| if test -f "`which ct-ng 2>/dev/null`"; then |
| ctng="ct-ng" |
| else |
| ctng="" |
| fi |
| |
| if test ! -n "$ctng"; then |
| if test ! -f "$prefix/bin/ct-ng"; then # look if we build it already |
| build "ctng" "" "1.13.2" |
| fi |
| fi |
| ctng=`PATH=$prefix/bin:$PATH which ct-ng` |
| } |
| |
| build_ctng() { |
| ctng_target="$1" |
| extra="$2" |
| tc_arch="$3" |
| tc_host="$4" |
| |
| make_ctng |
| |
| dlurl="http://www.rockbox.org/gcc/$ctng_target" |
| |
| # download |
| getfile "ct-ng-config" "$dlurl" |
| |
| test -n "$extra" && getfile "$extra" "$dlurl" |
| |
| # create build directory |
| if test -d $builddir; then |
| if test ! -w $builddir; then |
| echo "ROCKBOXDEV: No write permission for $builddir" |
| exit |
| fi |
| else |
| mkdir -p $builddir |
| fi |
| |
| # copy config and cd to $builddir |
| mkdir $builddir/build-$ctng_target |
| ctng_config="$builddir/build-$ctng_target/.config" |
| cat "$dlwhere/ct-ng-config" | sed -e "s,\(CT_PREFIX_DIR=\).*,\1$prefix," > $ctng_config |
| cd $builddir/build-$ctng_target |
| |
| $ctng "build" |
| |
| # install extras |
| if test -e "$dlwhere/$extra"; then |
| # verify the toolchain has sysroot support |
| if test -n `cat $ctng_config | grep CT_USE_SYSROOT\=y`; then |
| sysroot=`cat $ctng_config | grep CT_SYSROOT_NAME | sed -e 's,CT_SYSROOT_NAME\=\"\([a-zA-Z0-9]*\)\",\1,'` |
| tar xf "$dlwhere/$extra" -C "$prefix/$tc_arch-$ctng_target-$tc_host/$sysroot" |
| fi |
| fi |
| |
| # cleanup |
| cd $builddir |
| rm -rf $builddir/build-$ctng_target |
| } |
| |
| ############################################################################## |
| # Code: |
| |
| # Verify required tools |
| for t in $reqtools; do |
| tool=`findtool $t` |
| if test -z "$tool"; then |
| echo "ROCKBOXDEV: \"$t\" is required for this script to work." |
| echo "ROCKBOXDEV: Please install \"$t\" and re-run the script." |
| exit |
| fi |
| done |
| |
| echo "Download directory : $dlwhere (set RBDEV_DOWNLOAD to change)" |
| echo "Install prefix : $prefix (set RBDEV_PREFIX to change)" |
| echo "Build dir : $builddir (set RBDEV_BUILD to change)" |
| echo "Make options : $MAKEFLAGS (set MAKEFLAGS to change)" |
| echo "" |
| |
| # Verify download directory |
| if test -d "$dlwhere"; then |
| if ! test -w "$dlwhere"; then |
| echo "ROCKBOXDEV: No write permission for $dlwhere" |
| exit |
| fi |
| else |
| mkdir $dlwhere |
| if test $? -ne 0; then |
| echo "ROCKBOXDEV: Failed creating directory $dlwhere" |
| exit |
| fi |
| fi |
| |
| |
| # Verify the prefix dir |
| if test ! -d $prefix; then |
| mkdir -p $prefix |
| if test $? -ne 0; then |
| echo "ROCKBOXDEV: Failed creating directory $prefix" |
| exit |
| fi |
| fi |
| if test ! -w $prefix; then |
| echo "ROCKBOXDEV: No write permission for $prefix" |
| exit |
| fi |
| |
| echo "Select target arch:" |
| echo "s - sh (Archos models)" |
| echo "m - m68k (iriver h1x0/h3x0, iaudio m3/m5/x5 and mpio hd200)" |
| echo "a - arm (ipods, iriver H10, Sansa, D2, Gigabeat, etc)" |
| echo "i - mips (Jz4740 and ATJ-based players)" |
| echo "r - arm-app (Samsung ypr0)" |
| echo "separate multiple targets with spaces" |
| echo "(Example: \"s m a\" will build sh, m68k and arm)" |
| echo "" |
| |
| selarch=`input` |
| system=`uname -s` |
| |
| # add target dir to path to ensure the new binutils are used in gcc build |
| PATH="$prefix/bin:${PATH}" |
| |
| for arch in $selarch |
| do |
| echo "" |
| case $arch in |
| [Ss]) |
| # For binutils 2.16.1 builtin rules conflict on some systems with a |
| # default rule for Objective C. Disable the builtin make rules. See |
| # http://sourceware.org/ml/binutils/2005-12/msg00259.html |
| export MAKEFLAGS="-r $MAKEFLAGS" |
| build "binutils" "sh-elf" "2.16.1" "binutils-2.16.1-texinfo-fix.diff" "--disable-werror" |
| build "gcc" "sh-elf" "4.0.3" "gcc-4.0.3-rockbox-1.diff" |
| ;; |
| |
| [Ii]) |
| build "binutils" "mipsel-elf" "2.17" "" "--disable-werror" |
| patch="" |
| if [ "$system" = "Interix" ]; then |
| patch="gcc-4.1.2-interix.diff" |
| fi |
| build "gcc" "mipsel-elf" "4.1.2" "$patch" |
| ;; |
| |
| [Mm]) |
| build "binutils" "m68k-elf" "2.20.1" "binutils-2.20.1-texinfo-fix.diff" "--disable-werror" |
| build "gcc" "m68k-elf" "4.5.2" "" "--with-arch=cf MAKEINFO=missing" "gmp mpfr mpc" |
| ;; |
| |
| [Aa]) |
| binopts="" |
| gccopts="" |
| case $system in |
| Darwin) |
| binopts="--disable-nls" |
| gccopts="--disable-nls" |
| ;; |
| esac |
| build "binutils" "arm-elf-eabi" "2.20.1" "binutils-2.20.1-ld-thumb-interwork-long-call.diff binutils-2.20.1-texinfo-fix.diff" "$binopts --disable-werror" |
| build "gcc" "arm-elf-eabi" "4.4.4" "rockbox-multilibs-noexceptions-arm-elf-eabi-gcc-4.4.2_1.diff" "$gccopts MAKEINFO=missing" "gmp mpfr" |
| ;; |
| [Rr]) |
| build_ctng "ypr0" "alsalib.tar.gz" "arm" "linux-gnueabi" |
| ;; |
| *) |
| echo "ROCKBOXDEV: Unsupported architecture option: $arch" |
| exit |
| ;; |
| esac |
| done |
| |
| echo "" |
| echo "ROCKBOXDEV: Done!" |
| echo "" |
| echo "ROCKBOXDEV: Make sure your PATH includes $prefix/bin" |
| echo "" |