Merge the save-sample branch to trunk:

- reorder most of the environment setup,
 - geting, extracting and patching are now components' sub-actions,
 - save the current config as a sample to be used as a pre-configured target.
This commit is contained in:
Yann E. MORIN" 2007-05-07 09:04:02 +00:00
parent 45e6df196b
commit 58b4c6d0a4
17 changed files with 724 additions and 595 deletions

View File

@ -13,10 +13,11 @@ all: _ct_build
HOST_CC = gcc -funsigned-char
help::
@echo 'Available make targets (*: default target):'
@echo 'Available make targets:'
@echo
include $(CT_TOP_DIR)/kconfig/Makefile
include $(CT_TOP_DIR)/samples/Makefile
help::
@echo 'Build targets:'
@ -26,6 +27,9 @@ help::
include $(CT_TOP_DIR)/tools/Makefile
help::
@echo 'Execute "make" or "make all" to build all targets marked with [*]'
.config: $(shell find $(CT_TOP_DIR)/config -type f -name '*.in')
@make menuconfig
@# Because exiting menuconfig without saving is not an error to menuconfig

View File

@ -162,34 +162,29 @@ config REMOVE_DOCS
Remove the installed documentation (man and info pages).
Gains around 8MiB for a uClibc-based, C and C++ compiler.
comment "Downloading and extracting"
config NO_DOWNLOAD
bool
prompt "Avoid downloads"
default n
help
Avoid downloading anything. Bail out if a tarball is missing.
config ONLY_DOWNLOAD
bool
prompt "Only download tarballs"
default n
depends on ! NO_DOWNLOAD
help
Only download the tarballs. Exit once it done.
Usefull to pre-retrieve the tarballs before going off-line.
comment "Downloading"
config FORCE_DOWNLOAD
bool
prompt "Force downloads"
default n
depends on ! NO_DOWNLOAD
help
Force downloading tarballs, even if one already exists.
Usefull if you suspect a tarball to be damaged.
config ONLY_DOWNLOAD
bool
prompt "Stop after downloading tarballs"
default n
help
Only download the tarballs. Exit once it done.
Usefull to pre-retrieve the tarballs before going off-line.
comment "Extracting"
depends on ! ONLY_DOWNLOAD
config FORCE_EXTRACT
bool
prompt "Force extractions"
@ -201,6 +196,16 @@ config FORCE_EXTRACT
Usefull if you suspect a previous extract did not complete (eg. broken
tarball), or you added a new set of patches for this component.
config ONLY_EXTRACT
bool
prompt "Stop after extracting tarballs"
depends on ! ONLY_DOWNLOAD
default n
help
Exit after unpacking and patching tarballs.
Usefull to look at the code before doing the build itself.
comment "Logging"
choice

View File

@ -25,24 +25,14 @@ config: $(obj)/conf
oldconfig: $(obj)/conf
@$< -s $(KCONFIG_TOP)
# Build a list of all available samples
SAMPLES = $(patsubst $(CT_TOP_DIR)/samples/%,%,$(filter-out %Makefile,$(wildcard $(CT_TOP_DIR)/samples/*)))
.PHONY: $(SAMPLES)
$(SAMPLES):
@cp "$(CT_TOP_DIR)/samples/$(@)/crosstool.config" "$(CT_TOP_DIR)/.config"
@$(MAKE) oldconfig
# Help text used by make help
help::
@echo 'General purpose configuration targets:'
@echo ' config - Update current config using a line-oriented program'
@echo ' menuconfig - Update current config using a menu based program'
@echo ' oldconfig - Update current config using a provided .config as base'
@echo
@echo 'Preconfigured targets:'
@for s in $(SAMPLES); do \
echo " $${s}"; \
done
@# saveconfig is listed here for homogeneity, but implemented in samples/Makefile
@echo ' saveconfig - Save current config as a preconfigured target'
@echo ''
# Cheesy build

17
samples/Makefile Normal file
View File

@ -0,0 +1,17 @@
# Build a list of all available samples
SAMPLES = $(patsubst $(CT_TOP_DIR)/samples/%,%,$(filter-out %Makefile,$(wildcard $(CT_TOP_DIR)/samples/*)))
.PHONY: $(SAMPLES)
$(SAMPLES):
@cp "$(CT_TOP_DIR)/samples/$(@)/crosstool.config" "$(CT_TOP_DIR)/.config"
@$(MAKE) oldconfig
help::
@echo 'Preconfigured targets:'
@for s in $(SAMPLES); do \
echo " $${s}"; \
done
@echo ''
saveconfig:
@$(CT_TOP_DIR)/scripts/saveSample.sh

View File

@ -2,6 +2,19 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download binutils
do_binutils_get() {
CT_GetFile "${CT_BINUTILS_FILE}" \
ftp://ftp.gnu.org/gnu/binutils \
ftp://ftp.kernel.org/pub/linux/devel/binutils
}
# Extract binutils
do_binutils_extract() {
CT_ExtractAndPatch "${CT_BINUTILS_FILE}"
}
# Build binutils
do_binutils() {
mkdir -p "${CT_BUILD_DIR}/build-binutils"
cd "${CT_BUILD_DIR}/build-binutils"

View File

@ -2,6 +2,26 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download core gcc
do_cc_core_get() {
# Ah! gcc folks are kind of 'different': they store the tarballs in
# subdirectories of the same name! That's because gcc is such /crap/ that
# it is such /big/ that it needs being splitted for distribution! Sad. :-(
# Arrgghh! Some of those versions does not follow this convention:
# gcc-3.3.3 lives in releases/gcc-3.3.3, while gcc-2.95.* isn't in a
# subdirectory! You bastard!
CT_GetFile "${CT_CC_CORE_FILE}" \
ftp://ftp.gnu.org/gnu/gcc/${CT_CC_CORE_FILE} \
ftp://ftp.gnu.org/gnu/gcc/releases/${CT_CC_CORE_FILE} \
ftp://ftp.gnu.org/gnu/gcc
}
# Extract core gcc
do_cc_core_extract() {
CT_ExtractAndPatch "${CT_CC_CORE_FILE}"
}
# Build core gcc
do_cc_core() {
mkdir -p "${CT_BUILD_DIR}/build-cc-core"
cd "${CT_BUILD_DIR}/build-cc-core"

View File

@ -2,6 +2,26 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download final gcc
do_cc_get() {
# Ah! gcc folks are kind of 'different': they store the tarballs in
# subdirectories of the same name! That's because gcc is such /crap/ that
# it is such /big/ that it needs being splitted for distribution! Sad. :-(
# Arrgghh! Some of those versions does not follow this convention:
# gcc-3.3.3 lives in releases/gcc-3.3.3, while gcc-2.95.* isn't in a
# subdirectory! You bastard!
CT_GetFile "${CT_CC_FILE}" \
ftp://ftp.gnu.org/gnu/gcc/${CT_CC_FILE} \
ftp://ftp.gnu.org/gnu/gcc/releases/${CT_CC_FILE} \
ftp://ftp.gnu.org/gnu/gcc
}
# Extract final gcc
do_cc_extract() {
CT_ExtractAndPatch "${CT_CC_FILE}"
}
# Build final gcc
do_cc() {
CT_DoStep INFO "Installing final compiler"

View File

@ -2,6 +2,27 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download the kernel
do_kernel_get() {
if [ "${CT_KERNEL_LINUX_HEADERS_USE_CUSTOM_DIR}" != "y" ]; then
CT_GetFile "${CT_KERNEL_FILE}" \
ftp://ftp.kernel.org/pub/linux/kernel/v2.6 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.4 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.2 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.6/testing \
http://ep09.pld-linux.org/~mmazur/linux-libc-headers
fi
return 0
}
# Extract kernel
do_kernel_extract() {
if [ "${CT_KERNEL_LINUX_HEADERS_USE_CUSTOM_DIR}" != "y" ]; then
CT_ExtractAndPatch "${CT_KERNEL_FILE}"
fi
return 0
}
# Check kernel configuration
do_kernel_check_config() {
CT_DoStep INFO "Checking kernel configuration"

View File

@ -2,6 +2,33 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download glibc
do_libc_download() {
# Ah! Not all GNU folks seem stupid. All glibc releases are in the same
# directory. Good. Alas, there is no snapshot there. I'll deal with them
# later on... :-/
CT_GetFile "${CT_LIBC_FILE}" ftp://ftp.gnu.org/gnu/glibc
# C library addons
addons_list=`echo "${CT_LIBC_ADDONS}" |sed -r -e 's/,/ /g; s/ $//g;'`
for addon in ${addons_list}; do
CT_GetFile "${CT_LIBC}-${addon}-${CT_LIBC_VERSION}" ftp://ftp.gnu.org/gnu/glibc
done
[ "${CT_LIBC_GLIBC_USE_PORTS}" = "y" ] && CT_GetFile "${CT_LIBC}-ports-${CT_LIBC_VERSION}" ftp://ftp.gnu.org/gnu/glibc
}
# Extract glibc
do_libc_extract() {
CT_ExtractAndPatch "${CT_LIBC_FILE}"
# C library addons
addons_list=`echo "${CT_LIBC_ADDONS}" |sed -r -e 's/,/ /g; s/ $//g;'`
for addon in ${addons_list}; do
CT_ExtractAndPatch "${CT_LIBC}-${addon}-${CT_LIBC_VERSION}"
done
[ "${CT_LIBC_GLIBC_USE_PORTS}" = "y" ] && CT_ExtractAndPatch "${CT_LIBC}-ports-${CT_LIBC_VERSION}"
}
# There is nothing to do for glibc check config
do_libc_check_config() {
CT_DoStep INFO "Checking C library configuration"
@ -44,7 +71,8 @@ do_libc_headers() {
--host="${CT_TARGET}" \
--prefix=/usr \
--with-headers="${CT_HEADERS_DIR}" \
--without-cvs --disable-sanity-checks \
--without-cvs \
--disable-sanity-checks \
--enable-hacker-mode \
--enable-add-ons="" \
--without-nptl 2>&1 |CT_DoLog DEBUG
@ -142,7 +170,7 @@ do_libc() {
CT_DoLog DEBUG "Extra config args passed: \"${extra_config}\""
# Add some default CC args
extra_cc_args=
extra_cc_args="${CT_CFLAGS_FOR_HOST}"
case "${CT_LIBC_EXTRA_CC_ARGS}" in
*-mbig-endian*) ;;
*-mlittle-endian*) ;;

View File

@ -2,6 +2,34 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Define libfloat functions depending on wether it is selected or not
if [ "${CT_ARCH_FLOAT_SW_LIBFLOAT}" = "y" ]; then
# Download libfloat
do_libfloat_get() {
# Please note: because the file we download, and the file we store on the
# file system don't have the same name, CT_GetFile will always try to
# download the file over and over.
# To avoid this, we check that the file we want already exists in the
# tarball directory first. This is an ugly hack that overrides the standard
# CT_GetFile behavior... Sight...
lib_float_url="ftp://ftp.de.debian.org/debian/pool/main/libf/libfloat/"
ext=`CT_GetFileExtension "${CT_LIBFLOAT_FILE}"`
if [ -z "${ext}" ]; then
CT_GetFile libfloat_990616.orig "${lib_float_url}"
ext=`CT_GetFileExtension "libfloat_990616.orig"`
# Hack: remove the .orig extension, and change _ to -
mv -v "${CT_TARBALLS_DIR}/libfloat_990616.orig${ext}" \
"${CT_TARBALLS_DIR}/libfloat-990616${ext}" 2>&1 |CT_DoLog DEBUG
fi
}
# Extract libfloat
do_libfloat_extract() {
[ "${CT_ARCH_FLOAT_SW_LIBFLOAT}" = "y" ] && CT_ExtractAndPatch "${CT_LIBFLOAT_FILE}"
}
# Build libfloat
do_libfloat() {
# Here we build and install libfloat for the target, so that the C library
# builds OK with those versions of gcc that have severed softfloat support
@ -29,3 +57,17 @@ do_libfloat() {
CT_EndStep
}
else # "${CT_ARCH_FLOAT_SW_LIBFLOAT}" != "y"
do_libfloat_get() {
true
}
do_libfloat_extract() {
true
}
do_libfloat() {
true
}
fi

View File

@ -2,6 +2,25 @@
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download uClibc
do_libc_get() {
libc_src="http://www.uclibc.org/downloads
http://www.uclibc.org/downloads/snapshots
http://www.uclibc.org/downloads/old-releases"
# For uClibc, we have almost every thing: releases, and snapshots
# for the last month or so. We'll have to deal with svn revisions
# later...
CT_GetFile "${CT_LIBC_FILE}" ${libc_src}
# uClibc locales
[ "${CT_LIBC_UCLIBC_LOCALES}" = "y" ] && CT_GetFile "uClibc-locale-030818" ${libc_src}
}
# Extract uClibc
do_libc_extract() {
CT_ExtractAndPatch "${CT_LIBC_FILE}"
# uClibc locales
[ "${CT_LIBC_UCLIBC_LOCALES}" = "y" ] && CT_ExtractAndPatch "uClibc-locale-030818"
}
# Check that uClibc has been previously configured
do_libc_check_config() {

View File

@ -1,133 +0,0 @@
# This scripts calls each component's build script.
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Parse all build files to have the needed functions.
. "${CT_TOP_DIR}/scripts/build/kernel_${CT_KERNEL}.sh"
. "${CT_TOP_DIR}/scripts/build/binutils.sh"
. "${CT_TOP_DIR}/scripts/build/libc_libfloat.sh"
. "${CT_TOP_DIR}/scripts/build/libc_${CT_LIBC}.sh"
. "${CT_TOP_DIR}/scripts/build/cc_core_${CT_CC_CORE}.sh"
. "${CT_TOP_DIR}/scripts/build/cc_${CT_CC}.sh"
# Arrange paths depending on wether we use sys-root or not.
if [ "${CT_USE_SYSROOT}" = "y" ]; then
CT_SYSROOT_DIR="${CT_PREFIX_DIR}/${CT_TARGET}/sys-root"
CT_HEADERS_DIR="${CT_SYSROOT_DIR}/usr/include"
BINUTILS_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
CC_CORE_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
CC_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
LIBC_SYSROOT_ARG=""
# glibc's prefix must be exactly /usr, else --with-sysroot'd gcc will get
# confused when $sysroot/usr/include is not present.
# Note: --prefix=/usr is magic!
# See http://www.gnu.org/software/libc/FAQ.html#s-2.2
else
# plain old way. All libraries in prefix/target/lib
CT_SYSROOT_DIR="${CT_PREFIX_DIR}/${CT_TARGET}"
CT_HEADERS_DIR="${CT_SYSROOT_DIR}/include"
# hack! Always use --with-sysroot for binutils.
# binutils 2.14 and later obey it, older binutils ignore it.
# Lets you build a working 32->64 bit cross gcc
BINUTILS_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
# Use --with-headers, else final gcc will define disable_glibc while
# building libgcc, and you'll have no profiling
CC_CORE_SYSROOT_ARG="--without-headers"
CC_SYSROOT_ARG="--with-headers=${CT_HEADERS_DIR}"
LIBC_SYSROOT_ARG="prefix="
fi
# Prepare the 'lib' directories in sysroot, else the ../lib64 hack used by
# 32 -> 64 bit crosscompilers won't work, and build of final gcc will fail with
# "ld: cannot open crti.o: No such file or directory"
mkdir -p "${CT_SYSROOT_DIR}/lib"
mkdir -p "${CT_SYSROOT_DIR}/usr/lib"
# Canadian-cross are really picky on the way they are built. Tweak the values.
if [ "${CT_CANADIAN}" = "y" ]; then
# Arrange so that gcc never, ever think that build system == host system
CT_CANADIAN_OPT="--build=`echo \"${CT_BUILD}\" |sed -r -e 's/-/-build_/'`"
# We shall have a compiler for this target!
# Do test here...
else
CT_HOST="${CT_BUILD}"
CT_CANADIAN_OPT=
# Add the target toolchain in the path so that we can build the C library
export PATH="${CT_PREFIX_DIR}/bin:${CT_CC_CORE_PREFIX_DIR}/bin:${PATH}"
fi
# Modify GCC_HOST to never be equal to $BUILD or $TARGET
# This strange operation causes gcc to always generate a cross-compiler
# even if the build machine is the same kind as the host.
# This is why CC has to be set when doing a canadian cross; you can't find a
# host compiler by appending -gcc to our whacky $GCC_HOST
# Kludge: it is reported that the above causes canadian crosses with cygwin
# hosts to fail, so avoid it just in that one case. It would be cleaner to
# just move this into the non-canadian case above, but I'm afraid that might
# cause some configure script somewhere to decide that since build==host, they
# could run host binaries.
# (Copied almost as-is from original crosstool):
case "${CT_KERNEL},${CT_CANADIAN}" in
cygwin,y) ;;
*) CT_HOST="`echo \"${CT_HOST}\" |sed -r -e 's/-/-host_/;'`";;
esac
# Ah! Recent versions of binutils need some of the build and/or host system
# (read CT_BUILD and CT_HOST) tools to be accessible (ar is but an example).
# Do that:
CT_DoLog EXTRA "Making build system tools available"
mkdir -p "${CT_PREFIX_DIR}/bin"
for tool in ar; do
ln -s "`which ${tool}`" "${CT_PREFIX_DIR}/bin/${CT_BUILD}-${tool}"
ln -s "`which ${tool}`" "${CT_PREFIX_DIR}/bin/${CT_HOST}-${tool}"
done
# Ha. cygwin host have an .exe suffix (extension) for executables.
[ "${CT_KERNEL}" = "cygwin" ] && EXEEXT=".exe" || EXEEXT=""
# Transform the ARCH into a kernel-understandable ARCH
case "${CT_ARCH}" in
x86) CT_KERNEL_ARCH=i386;;
ppc) CT_KERNEL_ARCH=powerpc;;
*) CT_KERNEL_ARCH="${CT_ARCH}";;
esac
# Build up the TARGET_CFLAGS from user-provided options
tmp_target_CFLAGS=
[ -n "${CT_ARCH_CPU}" ] && tmp_target_CFLAGS="${tmp_target_CFLAGS} -mcpu=${CT_ARCH_CPU}"
[ -n "${CT_ARCH_TUNE}" ] && tmp_target_CFLAGS="${tmp_target_CFLAGS} -mtune=${CT_ARCH_TUNE}"
[ -n "${CT_ARCH_ARCH}" ] && tmp_target_CFLAGS="${tmp_target_CFLAGS} -march=${CT_ARCH_ARCH}"
[ -n "${CT_ARCH_FPU}" ] && tmp_target_CFLAGS="${tmp_target_CFLAGS} -mfpu=${CT_ARCH_FPU}"
# Override with user-specified CFLAGS
CT_TARGET_CFLAGS="${tmp_target_CFLAGS} ${CT_TARGET_CFLAGS}"
# Help gcc
CT_CFLAGS_FOR_HOST=
[ "${CT_USE_PIPES}" = "y" ] && CT_CFLAGS_FOR_HOST="${CT_CFLAGS_FOR_HOST} -pipe"
# And help make go faster
PARALLELMFLAGS=
[ ${CT_PARALLEL_JOBS} -ne 0 ] && PARALLELMFLAGS="${PARALLELMFLAGS} -j${CT_PARALLEL_JOBS}"
[ ${CT_LOAD} -ne 0 ] && PARALLELMFLAGS="${PARALLELMFLAGS} -l${CT_LOAD}"
CT_DoStep EXTRA "Dumping internal crosstool-NG configuration"
CT_DoLog EXTRA "Building a toolchain for:"
CT_DoLog EXTRA " build = ${CT_BUILD}"
CT_DoLog EXTRA " host = ${CT_HOST}"
CT_DoLog EXTRA " target = ${CT_TARGET}"
set |egrep '^CT_.+=' |sort |CT_DoLog DEBUG
CT_EndStep
# Now for the job by itself.
# Check the C library config ASAP, before the user gets bored, and is
# gone having his/her coffee
do_libc_check_config
do_kernel_check_config
do_kernel_headers
do_binutils
do_libc_headers
do_cc_core
do_libfloat
do_libc
do_cc
do_libc_finish

View File

@ -28,7 +28,7 @@ CT_STAR_DATE=`CT_DoDate +%s%N`
CT_STAR_DATE_HUMAN=`CT_DoDate +%Y%m%d.%H%M%S`
# Log to a temporary file until we have built our environment
CT_ACTUAL_LOG_FILE="`pwd`/$$.log"
CT_ACTUAL_LOG_FILE="${CT_TOP_DIR}/$$.log"
# CT_TOP_DIR should be an absolute path.
CT_TOP_DIR="`CT_MakeAbsolutePath \"${CT_TOP_DIR}\"`"
@ -73,6 +73,9 @@ fi
# Yes! We can do full logging from now on!
CT_DoLog INFO "Build started ${CT_STAR_DATE_HUMAN}"
# renice oursleves
renice ${CT_NICE} $$ |CT_DoLog DEBUG
# Some sanity checks in the environment and needed tools
CT_DoLog INFO "Checking environment sanity"
@ -109,50 +112,8 @@ CT_EndStep
CT_DoLog INFO "Building environment variables"
# This should go in buildToolchain.sh, but we might need it because it could
# be used by the user in his/her paths definitions.
# Target triplet: CT_TARGET needs a little love:
case "${CT_ARCH_BE},${CT_ARCH_LE}" in
y,) target_endian_eb=eb; target_endian_el=;;
,y) target_endian_eb=; target_endian_el=el;;
esac
case "${CT_ARCH}" in
arm) CT_TARGET="${CT_ARCH}${target_endian_eb}";;
mips) CT_TARGET="${CT_ARCH}${target_endian_el}";;
x86*) # Much love for this one :-(
# Ultimately, we should use config.sub to output the correct
# procesor name. Work for later...
arch="${CT_ARCH_ARCH}"
[ -z "${arch}" ] && arch="${CT_ARCH_TUNE}"
case "${CT_ARCH}" in
x86_64) CT_TARGET=x86_64;;
*) case "${arch}" in
"") CT_TARGET=i386;;
i386|i486|i586|i686) CT_TARGET="${arch}";;
winchip*) CT_TARGET=i486;;
pentium|pentium-mmx|c3*) CT_TARGET=i586;;
nocona|athlon*64|k8|athlon-fx|opteron) CT_TARGET=x86_64;;
pentiumpro|pentium*|athlon*) CT_TARGET=i686;;
*) CT_TARGET=i586;;
esac;;
esac;;
esac
case "${CT_TARGET_VENDOR}" in
"") CT_TARGET="${CT_TARGET}-unknown";;
*) CT_TARGET="${CT_TARGET}-${CT_TARGET_VENDOR}";;
esac
case "${CT_KERNEL}" in
linux*) CT_TARGET="${CT_TARGET}-linux";;
cygwin*) CT_TARGET="${CT_TARGET}-cygwin";;
esac
case "${CT_LIBC}" in
glibc) CT_TARGET="${CT_TARGET}-gnu";;
uClibc) CT_TARGET="${CT_TARGET}-uclibc";;
esac
case "${CT_ARCH_ABI}" in
eabi) CT_TARGET="${CT_TARGET}eabi";;
esac
CT_TARGET="`${CT_TOP_DIR}/tools/config.sub ${CT_TARGET}`"
CT_DoBuildTargetTriplet
# Now, build up the variables from the user-configured options.
CT_KERNEL_FILE="${CT_KERNEL}-${CT_KERNEL_VERSION}"
@ -171,50 +132,6 @@ CT_LIBC_FILE="${CT_LIBC}-${CT_LIBC_VERSION}"
# then rescan the options file now:
. "${CT_TOP_DIR}/.config"
# Determine build system if not set by the user
CT_Test "You did not specify the build system. Guessing." -z "${CT_BUILD}"
CT_BUILD="`${CT_TOP_DIR}/tools/config.sub \"${CT_BUILD:-\`${CT_TOP_DIR}/tools/config.guess\`}\"`"
# Get rid of pre-existing installed toolchain and previous build directories.
# We need to do that _before_ we can safely log, because the log file will
# most probably be in the toolchain directory.
if [ -d "${CT_PREFIX_DIR}" ]; then
mv "${CT_PREFIX_DIR}" "${CT_PREFIX_DIR}.$$"
nohup rm -rf "${CT_PREFIX_DIR}.$$" >/dev/null 2>&1 &
fi
mkdir -p "${CT_PREFIX_DIR}"
if [ -d "${CT_BUILD_DIR}" ]; then
mv "${CT_BUILD_DIR}" "${CT_BUILD_DIR}.$$"
nohup rm -rf "${CT_BUILD_DIR}.$$" >/dev/null 2>&1 &
fi
mkdir -p "${CT_BUILD_DIR}"
# Check now if we can write to the destination directory:
if [ -d "${CT_PREFIX_DIR}" ]; then
CT_TestAndAbort "Destination directory \"${CT_INSTALL_DIR}\" is not writeable" ! -w "${CT_PREFIX_DIR}"
else
mkdir -p "${CT_PREFIX_DIR}" || CT_Abort "Could not create destination directory \"${CT_PREFIX_DIR}\""
fi
# Redirect log to the actual log file now we can
# It's quite understandable that the log file will be installed in the
# install directory, so we must first ensure it exists and is writeable (above)
# before we can log there
t="${CT_ACTUAL_LOG_FILE}"
case "${CT_LOG_TO_FILE},${CT_LOG_FILE}" in
,*) CT_ACTUAL_LOG_FILE=/dev/null
rm -f "${t}"
;;
y,/*) mkdir -p "`dirname \"${CT_LOG_FILE}\"`"
CT_ACTUAL_LOG_FILE="${CT_LOG_FILE}"
mv "${t}" "${CT_ACTUAL_LOG_FILE}"
;;
y,*) mkdir -p "`pwd`/`dirname \"${CT_LOG_FILE}\"`"
CT_ACTUAL_LOG_FILE="`pwd`/${CT_LOG_FILE}"
mv "${t}" "${CT_ACTUAL_LOG_FILE}"
;;
esac
# Some more sanity checks now that we have all paths set up
case "${CT_TARBALLS_DIR},${CT_SRC_DIR},${CT_BUILD_DIR},${CT_PREFIX_DIR},${CT_INSTALL_DIR}" in
*" "*) CT_Abort "Don't use spaces in paths, it breaks things.";;
@ -233,7 +150,7 @@ CT_SYS_HOSTNAME="${CT_SYS_HOSTNAME:-`uname -n`}"
CT_SYS_KERNEL=`uname -s`
CT_SYS_REVISION=`uname -r`
# MacOS X lacks '-o' :
CT_SYS_OS=`uname -o || echo Unkown`
CT_SYS_OS=`uname -o || echo "Unknown (maybe MacOS-X)"`
CT_SYS_MACHINE=`uname -m`
CT_SYS_PROCESSOR=`uname -p`
CT_SYS_USER="`id -un`"
@ -241,14 +158,212 @@ CT_SYS_DATE=`CT_DoDate +%Y%m%d.%H%M%S`
CT_SYS_GCC=`gcc -dumpversion`
CT_TOOLCHAIN_ID="crosstool-${CT_VERSION} build ${CT_SYS_DATE} by ${CT_SYS_USER}@${CT_SYS_HOSTNAME} for ${CT_TARGET}"
# renice oursleves
renice ${CT_NICE} $$ |CT_DoLog DEBUG
# Check now if we can write to the destination directory:
if [ -d "${CT_INSTALL_DIR}" ]; then
CT_TestAndAbort "Destination directory \"${CT_INSTALL_DIR}\" is not removable" ! -w `dirname "${CT_INSTALL_DIR}"`
fi
# Get rid of pre-existing installed toolchain and previous build directories.
# We need to do that _before_ we can safely log, because the log file will
# most probably be in the toolchain directory.
if [ -d "${CT_INSTALL_DIR}" ]; then
mv "${CT_INSTALL_DIR}" "${CT_INSTALL_DIR}.$$"
nohup rm -rf "${CT_INSTALL_DIR}.$$" >/dev/null 2>&1 &
fi
if [ -d "${CT_BUILD_DIR}" ]; then
mv "${CT_BUILD_DIR}" "${CT_BUILD_DIR}.$$"
nohup rm -rf "${CT_BUILD_DIR}.$$" >/dev/null 2>&1 &
fi
if [ "${CT_FORCE_EXTRACT}" = "y" -a -d "${CT_SRC_DIR}" ]; then
mv "${CT_SRC_DIR}" "${CT_SRC_DIR}.$$"
nohup rm -rf "${CT_SRC_DIR}.$$" >/dev/null 2>&1 &
fi
mkdir -p "${CT_INSTALL_DIR}"
mkdir -p "${CT_BUILD_DIR}"
mkdir -p "${CT_TARBALLS_DIR}"
mkdir -p "${CT_SRC_DIR}"
# Make all path absolute, it so much easier!
# Now we have had the directories created, we even will get rid of embedded .. in paths:
CT_SRC_DIR="`CT_MakeAbsolutePath \"${CT_SRC_DIR}\"`"
CT_TARBALLS_DIR="`CT_MakeAbsolutePath \"${CT_TARBALLS_DIR}\"`"
# Redirect log to the actual log file now we can
# It's quite understandable that the log file will be installed in the install
# directory, so we must first ensure it exists and is writeable (above) before
# we can log there
case "${CT_LOG_TO_FILE},${CT_LOG_FILE}" in
,*) rm -f "${CT_ACTUAL_LOG_FILE}"
CT_ACTUAL_LOG_FILE=/dev/null
;;
y,/*) mkdir -p "`dirname \"${CT_LOG_FILE}\"`"
mv "${CT_ACTUAL_LOG_FILE}" "${CT_LOG_FILE}"
CT_ACTUAL_LOG_FILE="${CT_LOG_FILE}"
;;
y,*) mkdir -p "`pwd`/`dirname \"${CT_LOG_FILE}\"`"
mv "${CT_ACTUAL_LOG_FILE}" "`pwd`/${CT_LOG_FILE}"
CT_ACTUAL_LOG_FILE="`pwd`/${CT_LOG_FILE}"
;;
esac
# Determine build system if not set by the user
CT_Test "You did not specify the build system. Guessing." -z "${CT_BUILD}"
CT_BUILD="`${CT_TOP_DIR}/tools/config.sub \"${CT_BUILD:-\`${CT_TOP_DIR}/tools/config.guess\`}\"`"
# Arrange paths depending on wether we use sys-root or not.
if [ "${CT_USE_SYSROOT}" = "y" ]; then
CT_SYSROOT_DIR="${CT_PREFIX_DIR}/${CT_TARGET}/sys-root"
CT_HEADERS_DIR="${CT_SYSROOT_DIR}/usr/include"
BINUTILS_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
CC_CORE_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
CC_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
LIBC_SYSROOT_ARG=""
# glibc's prefix must be exactly /usr, else --with-sysroot'd gcc will get
# confused when $sysroot/usr/include is not present.
# Note: --prefix=/usr is magic!
# See http://www.gnu.org/software/libc/FAQ.html#s-2.2
else
# plain old way. All libraries in prefix/target/lib
CT_SYSROOT_DIR="${CT_PREFIX_DIR}/${CT_TARGET}"
CT_HEADERS_DIR="${CT_SYSROOT_DIR}/include"
# hack! Always use --with-sysroot for binutils.
# binutils 2.14 and later obey it, older binutils ignore it.
# Lets you build a working 32->64 bit cross gcc
BINUTILS_SYSROOT_ARG="--with-sysroot=${CT_SYSROOT_DIR}"
# Use --with-headers, else final gcc will define disable_glibc while
# building libgcc, and you'll have no profiling
CC_CORE_SYSROOT_ARG="--without-headers"
CC_SYSROOT_ARG="--with-headers=${CT_HEADERS_DIR}"
LIBC_SYSROOT_ARG="prefix="
fi
# Prepare the 'lib' directories in sysroot, else the ../lib64 hack used by
# 32 -> 64 bit crosscompilers won't work, and build of final gcc will fail with
# "ld: cannot open crti.o: No such file or directory"
mkdir -p "${CT_SYSROOT_DIR}/lib"
mkdir -p "${CT_SYSROOT_DIR}/usr/lib"
# Canadian-cross are really picky on the way they are built. Tweak the values.
if [ "${CT_CANADIAN}" = "y" ]; then
# Arrange so that gcc never, ever think that build system == host system
CT_CANADIAN_OPT="--build=`echo \"${CT_BUILD}\" |sed -r -e 's/-/-build_/'`"
# We shall have a compiler for this target!
# Do test here...
else
CT_HOST="${CT_BUILD}"
CT_CANADIAN_OPT=
# Add the target toolchain in the path so that we can build the C library
export PATH="${CT_PREFIX_DIR}/bin:${CT_CC_CORE_PREFIX_DIR}/bin:${PATH}"
fi
# Modify GCC_HOST to never be equal to $BUILD or $TARGET
# This strange operation causes gcc to always generate a cross-compiler
# even if the build machine is the same kind as the host.
# This is why CC has to be set when doing a canadian cross; you can't find a
# host compiler by appending -gcc to our whacky $GCC_HOST
# Kludge: it is reported that the above causes canadian crosses with cygwin
# hosts to fail, so avoid it just in that one case. It would be cleaner to
# just move this into the non-canadian case above, but I'm afraid that might
# cause some configure script somewhere to decide that since build==host, they
# could run host binaries.
# (Copied almost as-is from original crosstool):
case "${CT_KERNEL},${CT_CANADIAN}" in
cygwin,y) ;;
*) CT_HOST="`echo \"${CT_HOST}\" |sed -r -e 's/-/-host_/;'`";;
esac
# Ah! Recent versions of binutils need some of the build and/or host system
# (read CT_BUILD and CT_HOST) tools to be accessible (ar is but an example).
# Do that:
CT_DoLog EXTRA "Making build system tools available"
mkdir -p "${CT_PREFIX_DIR}/bin"
for tool in ar; do
ln -s "`which ${tool}`" "${CT_PREFIX_DIR}/bin/${CT_BUILD}-${tool}"
ln -s "`which ${tool}`" "${CT_PREFIX_DIR}/bin/${CT_HOST}-${tool}"
done
# Ha. cygwin host have an .exe suffix (extension) for executables.
[ "${CT_KERNEL}" = "cygwin" ] && EXEEXT=".exe" || EXEEXT=""
# Transform the ARCH into a kernel-understandable ARCH
case "${CT_ARCH}" in
x86) CT_KERNEL_ARCH=i386;;
ppc) CT_KERNEL_ARCH=powerpc;;
*) CT_KERNEL_ARCH="${CT_ARCH}";;
esac
# Build up the TARGET_CFLAGS from user-provided options
# Override with user-specified CFLAGS
[ -n "${CT_ARCH_CPU}" ] && CT_TARGET_CFLAGS="-mcpu=${CT_ARCH_CPU} ${CT_TARGET_CFLAGS}"
[ -n "${CT_ARCH_TUNE}" ] && CT_TARGET_CFLAGS="-mtune=${CT_ARCH_TUNE} ${CT_TARGET_CFLAGS}"
[ -n "${CT_ARCH_ARCH}" ] && CT_TARGET_CFLAGS="-march=${CT_ARCH_ARCH} ${CT_TARGET_CFLAGS}"
[ -n "${CT_ARCH_FPU}" ] && CT_TARGET_CFLAGS="-mfpu=${CT_ARCH_FPU} ${CT_TARGET_CFLAGS}"
# Help gcc
CT_CFLAGS_FOR_HOST=
[ "${CT_USE_PIPES}" = "y" ] && CT_CFLAGS_FOR_HOST="${CT_CFLAGS_FOR_HOST} -pipe"
# And help make go faster
PARALLELMFLAGS=
[ ${CT_PARALLEL_JOBS} -ne 0 ] && PARALLELMFLAGS="${PARALLELMFLAGS} -j${CT_PARALLEL_JOBS}"
[ ${CT_LOAD} -ne 0 ] && PARALLELMFLAGS="${PARALLELMFLAGS} -l${CT_LOAD}"
CT_DoStep EXTRA "Dumping internal crosstool-NG configuration"
CT_DoLog EXTRA "Building a toolchain for:"
CT_DoLog EXTRA " build = ${CT_BUILD}"
CT_DoLog EXTRA " host = ${CT_HOST}"
CT_DoLog EXTRA " target = ${CT_TARGET}"
set |egrep '^CT_.+=' |sort |CT_DoLog DEBUG
CT_EndStep
# Include sub-scripts instead of calling them: that way, we do not have to
# export any variable, nor re-parse the configuration and functions files.
. "${CT_TOP_DIR}/scripts/getExtractPatch.sh"
. "${CT_TOP_DIR}/scripts/buildToolchain.sh"
#. "${CT_TOP_DIR}/scripts/testToolchain.sh"
. "${CT_TOP_DIR}/scripts/build/kernel_${CT_KERNEL}.sh"
. "${CT_TOP_DIR}/scripts/build/binutils.sh"
. "${CT_TOP_DIR}/scripts/build/libc_libfloat.sh"
. "${CT_TOP_DIR}/scripts/build/libc_${CT_LIBC}.sh"
. "${CT_TOP_DIR}/scripts/build/cc_core_${CT_CC_CORE}.sh"
. "${CT_TOP_DIR}/scripts/build/cc_${CT_CC}.sh"
# Now for the job by itself. Go have a coffee!
if [ "${CT_NO_DOWNLOAD}" != "y" ]; then
CT_DoStep INFO "Retrieving needed toolchain components' tarballs"
do_kernel_get
do_binutils_get
do_libc_get
do_libfloat_get
do_cc_core_get
do_cc_get
CT_EndStep
fi
if [ "${CT_ONLY_DOWNLOAD}" != "y" ]; then
if [ "${CT_FORCE_EXTRACT}" = "y" ]; then
mv "${CT_SRC_DIR}" "${CT_SRC_DIR}.$$"
nohup rm -rf "${CT_SRC_DIR}.$$" >/dev/null 2>&1
fi
CT_DoStep INFO "Extracting and patching toolchain components"
do_kernel_extract
do_binutils_extract
do_libc_extract
do_libfloat_extract
do_cc_core_extract
do_cc_extract
CT_EndStep
if [ "${CT_ONLY_EXTRACT}" != "y" ]; then
do_libc_check_config
do_kernel_check_config
do_kernel_headers
do_binutils
do_libc_headers
do_cc_core
do_libfloat
do_libc
do_cc
do_libc_finish
fi
fi
if [ -n "${CT_TARGET_ALIAS}" ]; then
CT_DoLog EXTRA "Creating symlinks from \"${CT_TARGET}-*\" to \"${CT_TARGET_ALIAS}-*\""

View File

@ -218,3 +218,234 @@ CT_MktempDir() {
CT_DoYes() {
yes "$1" || true
}
# Download an URL using wget
# Usage: CT_DoGetFileWget <URL>
CT_DoGetFileWget() {
# Need to return true because it is legitimate to not find the tarball at
# some of the provided URLs (think about snapshots, different layouts for
# different gcc versions, etc...)
# Some (very old!) FTP server might not support the passive mode, thus
# retry without
# With automated download as we are doing, it can be very dangerous to use
# -c to continue the downloads. It's far better to simply overwrite the
# destination file
wget -nc --progress=dot:binary --tries=3 --passive-ftp "$1" || wget -nc --progress=dot:binary --tries=3 "$1" || true
}
# Download an URL using curl
# Usage: CT_DoGetFileCurl <URL>
CT_DoGetFileCurl() {
# Note: comments about wget method are also valid here
# Plus: no good progreess indicator is available with curl,
# so output is consigned to oblivion
curl --ftp-pasv -O --retry 3 "$1" >/dev/null || curl -O --retry 3 "$1" >/dev/null || true
}
# Wrapper function to call one of curl or wget
# Usage: CT_DoGetFile <URL>
CT_DoGetFile() {
local _wget=`which wget`
local _curl=`which curl`
case "${_wget},${_curl}" in
,) CT_DoError "Could find neither wget nor curl";;
,*) CT_DoGetFileCurl "$1";;
*) CT_DoGetFileWget "$1";;
esac
}
# Download the file from one of the URLs passed as argument
# Usage: CT_GetFile <filename> <url> [<url> ...]
CT_GetFile() {
local got_it
local ext
local url
local file="$1"
shift
# Do we already have it?
ext=`CT_GetFileExtension "${file}"`
if [ -n "${ext}" ]; then
if [ "${CT_FORCE_DOWNLOAD}" = "y" ]; then
rm -f "${CT_TARBALLS_DIR}/${file}${ext}"
else
return 0
fi
fi
CT_DoLog EXTRA "Retrieving \"${file}\""
CT_Pushd "${CT_TARBALLS_DIR}"
# File not yet downloaded, try to get it
got_it=0
if [ "${got_it}" != "y" ]; then
# We'd rather have a bzip2'ed tarball, then gzipped, and finally plain tar.
for ext in .tar.bz2 .tar.gz .tgz .tar; do
# Try all urls in turn
for url in "$@"; do
case "${url}" in
*) CT_DoLog EXTRA "Trying \"${url}/${file}${ext}\""
CT_DoGetFile "${url}/${file}${ext}" 2>&1 |CT_DoLog DEBUG
;;
esac
[ -f "${file}${ext}" ] && got_it=1 && break 2 || true
done
done
fi
CT_Popd
CT_TestAndAbort "Could not download \"${file}\", and not present in \"${CT_TARBALLS_DIR}\"" ${got_it} -eq 0
}
# Get the file name extension of a component
# Usage: CT_GetFileExtension <component_name-component_version>
# If found, echoes the extension to stdout
# If not found, echoes nothing on stdout.
CT_GetFileExtension() {
local ext
local file="$1"
local got_it=1
CT_Pushd "${CT_TARBALLS_DIR}"
for ext in .tar.gz .tar.bz2 .tgz .tar; do
if [ -f "${file}${ext}" ]; then
echo "${ext}"
got_it=0
break
fi
done
CT_Popd
return 0
}
# Extract a tarball and patch the resulting sources if necessary.
# Some tarballs need to be extracted in specific places. Eg.: glibc addons
# must be extracted in the glibc directory; uCLibc locales must be extracted
# in the extra/locale sub-directory of uClibc.
CT_ExtractAndPatch() {
local file="$1"
local base_file=`echo "${file}" |cut -d - -f 1`
local ver_file=`echo "${file}" |cut -d - -f 2-`
local official_patch_dir
local custom_patch_dir
local libc_addon
local ext=`CT_GetFileExtension "${file}"`
CT_TestAndAbort "\"${file}\" not found in \"${CT_TARBALLS_DIR}\"" -z "${ext}"
local full_file="${CT_TARBALLS_DIR}/${file}${ext}"
CT_Pushd "${CT_SRC_DIR}"
# Add-ons need a little love, really.
case "${file}" in
glibc-[a-z]*-*)
CT_TestAndAbort "Trying to extract the C-library addon/locales \"${file}\" when C-library not yet extracted" ! -d "${CT_LIBC_FILE}"
cd "${CT_LIBC_FILE}"
libc_addon=y
[ -f ".${file}.extracted" ] && return 0
touch ".${file}.extracted"
;;
uClibc-locale-*)
CT_TestAndAbort "Trying to extract the C-library addon/locales \"${file}\" when C-library not yet extracted" ! -d "${CT_LIBC_FILE}"
cd "${CT_LIBC_FILE}/extra/locale"
libc_addon=y
[ -f ".${file}.extracted" ] && return 0
touch ".${file}.extracted"
;;
esac
# If the directory exists, then consider extraction and patching done
[ -d "${file}" ] && return 0
CT_DoLog EXTRA "Extracting \"${file}\""
case "${ext}" in
.tar.bz2) tar xvjf "${full_file}" |CT_DoLog DEBUG;;
.tar.gz|.tgz) tar xvzf "${full_file}" |CT_DoLog DEBUG;;
.tar) tar xvf "${full_file}" |CT_DoLog DEBUG;;
*) CT_Abort "Don't know how to handle \"${file}\": unknown extension" ;;
esac
# Snapshots might not have the version number in the extracted directory
# name. This is also the case for some (old) packages, such as libfloat.
# Overcome this issue by symlink'ing the directory.
if [ ! -d "${file}" -a "${libc_addon}" != "y" ]; then
case "${ext}" in
.tar.bz2) base=`tar tjf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
.tar.gz|.tgz) base=`tar tzf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
.tar) base=`tar tf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
esac
CT_TestOrAbort "There was a problem when extracting \"${file}\"" -d "${base}" -o "${base}" != "${file}"
ln -s "${base}" "${file}"
fi
# Kludge: outside this function, we wouldn't know if we had just extracted
# a libc addon, or a plain package. Apply patches now.
CT_DoLog EXTRA "Patching \"${file}\""
# If libc addon, we're already in the correct place.
[ -z "${libc_addon}" ] && cd "${file}"
[ "${CUSTOM_PATCH_ONLY}" = "y" ] || official_patch_dir="${CT_TOP_DIR}/patches/${base_file}/${ver_file}"
[ "${CT_CUSTOM_PATCH}" = "y" ] && custom_patch_dir="${CT_CUSTOM_PATCH_DIR}/${base_file}/${ver_file}"
for patch_dir in "${official_patch_dir}" "${custom_patch_dir}"; do
if [ -n "${patch_dir}" -a -d "${patch_dir}" ]; then
for p in "${patch_dir}"/*.patch; do
if [ -f "${p}" ]; then
CT_DoLog DEBUG "Applying patch \"${p}\""
patch -g0 -F1 -p1 -f <"${p}" |CT_DoLog DEBUG
CT_TestAndAbort "Failed while applying patch file \"${p}\"" ${PIPESTATUS[0]} -ne 0
fi
done
fi
done
CT_Popd
}
# Compute the target triplet from what is provided by the user
# Usage: CT_DoBuildTargetTriplet
# In fact this function takes the environment variables to build the target
# triplet. It is needed both by the normal build sequence, as well as the
# sample saving sequence.
CT_DoBuildTargetTriplet() {
case "${CT_ARCH_BE},${CT_ARCH_LE}" in
y,) target_endian_eb=eb; target_endian_el=;;
,y) target_endian_eb=; target_endian_el=el;;
esac
case "${CT_ARCH}" in
arm) CT_TARGET="${CT_ARCH}${target_endian_eb}";;
mips) CT_TARGET="${CT_ARCH}${target_endian_el}";;
x86*) # Much love for this one :-(
# Ultimately, we should use config.sub to output the correct
# procesor name. Work for later...
arch="${CT_ARCH_ARCH}"
[ -z "${arch}" ] && arch="${CT_ARCH_TUNE}"
case "${CT_ARCH}" in
x86_64) CT_TARGET=x86_64;;
*) case "${arch}" in
"") CT_TARGET=i386;;
i386|i486|i586|i686) CT_TARGET="${arch}";;
winchip*) CT_TARGET=i486;;
pentium|pentium-mmx|c3*) CT_TARGET=i586;;
nocona|athlon*64|k8|athlon-fx|opteron) CT_TARGET=x86_64;;
pentiumpro|pentium*|athlon*) CT_TARGET=i686;;
*) CT_TARGET=i586;;
esac;;
esac;;
esac
case "${CT_TARGET_VENDOR}" in
"") CT_TARGET="${CT_TARGET}-unknown";;
*) CT_TARGET="${CT_TARGET}-${CT_TARGET_VENDOR}";;
esac
case "${CT_KERNEL}" in
linux*) CT_TARGET="${CT_TARGET}-linux";;
cygwin*) CT_TARGET="${CT_TARGET}-cygwin";;
esac
case "${CT_LIBC}" in
glibc) CT_TARGET="${CT_TARGET}-gnu";;
uClibc) CT_TARGET="${CT_TARGET}-uclibc";;
esac
case "${CT_ARCH_ABI}" in
eabi) CT_TARGET="${CT_TARGET}eabi";;
esac
CT_TARGET="`${CT_TOP_DIR}/tools/config.sub ${CT_TARGET}`"
}

View File

@ -1,334 +0,0 @@
# This script will download tarballs, extract them and patch the source.
# Copyright 2007 Yann E. MORIN
# Licensed under the GPL v2. See COPYING in the root of this package
# Download tarballs in sequence. Once we have everything, start extracting
# and patching the tarballs.
#-----------------------------------------------------------------------------
_wget=`which wget || true`
_curl=`which curl || true`
#_svn=`which svn ||true`
#_cvs=`which cvs || true`
case "${_wget},${_curl}" in
,) CT_Abort "Found neither curl nor wget. Please install one.";;
,*) CT_DoLog DEBUG "Using curl to retrieve tarballs"; CT_DoGetFile=CT_DoGetFileCurl;;
*) CT_DoLog DEBUG "Using wget to retrieve tarballs"; CT_DoGetFile=CT_DoGetFileWget;;
esac
CT_DoGetFileWget() {
# Need to return true because it is legitimate to not find the tarball at
# some of the provided URLs (think about snapshots, different layouts for
# different gcc versions, etc...)
# Some (very old!) FTP server might not support the passive mode, thus
# retry without
# With automated download as we are doing, it can be very dangerous to use
# -c to continue the downloads. It's far better to simply overwrite the
# destination file
wget -nc --progress=dot:binary --tries=3 --passive-ftp "$1" || wget -nc --progress=dot:binary --tries=3 "$1" || true
}
CT_DoGetFileCurl() {
# Note: comments about wget method are also valid here
# Plus: no good progreess indicator is available with curl,
# so output is consigned to oblivion
curl --ftp-pasv -O --retry 3 "$1" >/dev/null || curl -O --retry 3 "$1" >/dev/null || true
}
# For those wanting bleading edge, or to retrieve old uClibc snapshots
# Usage: CT_GetFileSVN basename url
#CT_DoGetFileSVN() {
# local basename="$1"
# local url="`echo \"$2\" |cut -d : -f 2-`"
# local tmp_dir
#
# CT_TestOrAbort "You don't have subversion" -n "${_svn}"
# CT_MktempDir tmp_dir
# CT_Pushd "${tmp_dir}"
# svn export --force "${url}" "${basename}"
# tar cfj "${CT_TARBALLS_DIR}/${basename}.tar.bz2" "${basename}"
# CT_Popd
# rm -rf "${tmp_dir}"
#}
#
#CT_DoGetFileCVS() {
# :
#}
# Download the file from one of the URLs passed as argument
# Usage: CT_GetFile <filename> <url> [<url> ...]
CT_GetFile() {
local got_it
local ext
local url
local file="$1"
shift
# Do we already have it?
ext=`CT_GetFileExtension "${file}"`
if [ -n "${ext}" ]; then
if [ "${CT_FORCE_DOWNLOAD}" = "y" ]; then
rm -f "${CT_TARBALLS_DIR}/${file}${ext}"
else
return 0
fi
fi
CT_DoLog EXTRA "Retrieving \"${file}\""
CT_Pushd "${CT_TARBALLS_DIR}"
# File not yet downloaded, try to get it
got_it=0
if [ "${got_it}" != "y" ]; then
# We'd rather have a bzip2'ed tarball, then gzipped, and finally plain tar.
for ext in .tar.bz2 .tar.gz .tgz .tar; do
# Try all urls in turn
for url in "$@"; do
case "${url}" in
# svn://*) CT_DoGetFileSVN "${file}" ${url}";;
# cvs://*) CT_DoGetFileCVS "${file}" ${url}";;
*) CT_DoLog EXTRA "Trying \"${url}/${file}${ext}\""
${CT_DoGetFile} "${url}/${file}${ext}" 2>&1 |CT_DoLog DEBUG
;;
esac
[ -f "${file}${ext}" ] && got_it=1 && break 2 || true
done
done
fi
CT_Popd
CT_TestAndAbort "Could not download \"${file}\", and not present in \"${CT_TARBALLS_DIR}\"" ${got_it} -eq 0
}
#-----------------------------------------------------------------------------
# Extract a tarball and patch.
# Some tarballs need to be extracted in specific places. Eg.: glibc addons
# must be extracted in the glibc directory; uCLibc locales must be extracted
# in the extra/locale sub-directory of uClibc.
CT_ExtractAndPatch() {
local file="$1"
local base_file=`echo "${file}" |cut -d - -f 1`
local ver_file=`echo "${file}" |cut -d - -f 2-`
local official_patch_dir
local custom_patch_dir
local libc_addon
local ext=`CT_GetFileExtension "${file}"`
CT_TestAndAbort "\"${file}\" not found in \"${CT_TARBALLS_DIR}\"" -z "${ext}"
local full_file="${CT_TARBALLS_DIR}/${file}${ext}"
CT_Pushd "${CT_SRC_DIR}"
# Add-ons need a little love, really.
case "${file}" in
glibc-[a-z]*-*)
CT_TestAndAbort "Trying to extract the C-library addon/locales \"${file}\" when C-library not yet extracted" ! -d "${CT_LIBC_FILE}"
cd "${CT_LIBC_FILE}"
libc_addon=y
[ -f ".${file}.extracted" ] && return 0
touch ".${file}.extracted"
;;
uClibc-locale-*)
CT_TestAndAbort "Trying to extract the C-library addon/locales \"${file}\" when C-library not yet extracted" ! -d "${CT_LIBC_FILE}"
cd "${CT_LIBC_FILE}/extra/locale"
libc_addon=y
[ -f ".${file}.extracted" ] && return 0
touch ".${file}.extracted"
;;
esac
# If the directory exists, then consider extraction and patching done
[ -d "${file}" ] && return 0
CT_DoLog EXTRA "Extracting \"${file}\""
case "${ext}" in
.tar.bz2) tar xvjf "${full_file}" |CT_DoLog DEBUG;;
.tar.gz|.tgz) tar xvzf "${full_file}" |CT_DoLog DEBUG;;
.tar) tar xvf "${full_file}" |CT_DoLog DEBUG;;
*) CT_Abort "Don't know how to handle \"${file}\": unknown extension" ;;
esac
# Snapshots might not have the version number in the extracted directory
# name. This is also the case for some (old) packages, such as libfloat.
# Overcome this issue by symlink'ing the directory.
if [ ! -d "${file}" -a "${libc_addon}" != "y" ]; then
case "${ext}" in
.tar.bz2) base=`tar tjf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
.tar.gz|.tgz) base=`tar tzf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
.tar) base=`tar tf "${full_file}" |head -n 1 |cut -d / -f 1 || true`;;
esac
CT_TestOrAbort "There was a problem when extracting \"${file}\"" -d "${base}" -o "${base}" != "${file}"
ln -s "${base}" "${file}"
fi
# Kludge: outside this function, we wouldn't know if we had just extracted
# a libc addon, or a plain package. Apply patches now.
CT_DoLog EXTRA "Patching \"${file}\""
# If libc addon, we're already in the correct place.
[ -z "${libc_addon}" ] && cd "${file}"
[ "${CUSTOM_PATCH_ONLY}" = "y" ] || official_patch_dir="${CT_TOP_DIR}/patches/${base_file}/${ver_file}"
[ "${CT_CUSTOM_PATCH}" = "y" ] && custom_patch_dir="${CT_CUSTOM_PATCH_DIR}/${base_file}/${ver_file}"
for patch_dir in "${official_patch_dir}" "${custom_patch_dir}"; do
if [ -n "${patch_dir}" -a -d "${patch_dir}" ]; then
for p in "${patch_dir}"/*.patch; do
if [ -f "${p}" ]; then
CT_DoLog DEBUG "Applying patch \"${p}\""
patch -g0 -F1 -p1 -f <"${p}" |CT_DoLog DEBUG
CT_TestAndAbort "Failed while applying patch file \"${p}\"" ${PIPESTATUS[0]} -ne 0
fi
done
fi
done
CT_Popd
}
#-----------------------------------------------------------------------------
# Get the file name extension of a component
# Usage: CT_GetFileExtension <component-version>
# If found, echoes the extension to stdout
# If not found, echoes nothing on stdout.
CT_GetFileExtension() {
local ext
local file="$1"
local got_it=1
CT_Pushd "${CT_TARBALLS_DIR}"
for ext in .tar.gz .tar.bz2 .tgz .tar; do
if [ -f "${file}${ext}" ]; then
echo "${ext}"
got_it=0
break
fi
done
CT_Popd
return 0
}
#-----------------------------------------------------------------------------
# Create needed directories, remove old ones
mkdir -p "${CT_TARBALLS_DIR}"
if [ "${CT_FORCE_EXTRACT}" = "y" -a -d "${CT_SRC_DIR}" ]; then
mv "${CT_SRC_DIR}" "${CT_SRC_DIR}.$$"
nohup rm -rf "${CT_SRC_DIR}.$$" >/dev/null 2>&1 &
fi
mkdir -p "${CT_SRC_DIR}"
# Make all path absolute, it so much easier!
# Now we have had the directories created, we even will get rid of embedded .. in paths:
CT_SRC_DIR="`CT_MakeAbsolutePath \"${CT_SRC_DIR}\"`"
CT_TARBALLS_DIR="`CT_MakeAbsolutePath \"${CT_TARBALLS_DIR}\"`"
# Prepare the addons list to be parsable:
addons_list="`echo \"${CT_LIBC_ADDONS_LIST}\" |sed -r -e 's/,/ /g; s/ $//g;'`"
if [ "${CT_NO_DOWNLOAD}" != "y" ]; then
CT_DoStep INFO "Retrieving needed toolchain components' tarballs"
# Kernel: for now, I don't care about cygwin.
if [ "${CT_KERNEL_LINUX_HEADERS_USE_CUSTOM_DIR}" != "y" ]; then
CT_GetFile "${CT_KERNEL_FILE}" \
ftp://ftp.kernel.org/pub/linux/kernel/v2.6 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.4 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.2 \
ftp://ftp.kernel.org/pub/linux/kernel/v2.6/testing \
http://ep09.pld-linux.org/~mmazur/linux-libc-headers
fi
# binutils
CT_GetFile "${CT_BINUTILS_FILE}" \
ftp://ftp.gnu.org/gnu/binutils \
ftp://ftp.kernel.org/pub/linux/devel/binutils
# Core and final gcc
# Ah! gcc folks are kind of 'different': they store the tarballs in
# subdirectories of the same name! That's because gcc is such /crap/ that
# it is such /big/ that it needs being splitted for distribution! Sad. :-(
# Arrgghh! Some of those versions does not follow this convention:
# gcc-3.3.3 lives in releases/gcc-3.3.3, while gcc-2.95.* isn't in a
# subdirectory! You bastard!
CT_GetFile "${CT_CC_CORE_FILE}" \
ftp://ftp.gnu.org/gnu/gcc/${CT_CC_CORE_FILE} \
ftp://ftp.gnu.org/gnu/gcc/releases/${CT_CC_CORE_FILE} \
ftp://ftp.gnu.org/gnu/gcc
CT_GetFile "${CT_CC_FILE}" \
ftp://ftp.gnu.org/gnu/gcc/${CT_CC_FILE} \
ftp://ftp.gnu.org/gnu/gcc/releases/${CT_CC_FILE} \
ftp://ftp.gnu.org/gnu/gcc
# C library
case "${CT_LIBC}" in
glibc)
# Ah! Not all GNU folks seem stupid. All glibc releases are in the same
# directory. Good. Alas, there is no snapshot there. I'll deal with them
# later on... :-/
libc_src="ftp://ftp.gnu.org/gnu/glibc"
;;
uClibc)
# For uClibc, we have almost every thing: releases, and snapshots
# for the last month or so. We'll have to deal with svn revisions
# later...
libc_src="http://www.uclibc.org/downloads
http://www.uclibc.org/downloads/snapshots
http://www.uclibc.org/downloads/old-releases"
;;
esac
CT_GetFile "${CT_LIBC_FILE}" ${libc_src}
# C library addons
addons_list=`echo "${CT_LIBC_ADDONS}" |sed -r -e 's/,/ /g; s/ $//g;'`
for addon in ${addons_list}; do
CT_GetFile "${CT_LIBC}-${addon}-${CT_LIBC_VERSION}" ${libc_src}
done
[ "${CT_LIBC_GLIBC_USE_PORTS}" = "y" ] && CT_GetFile "${CT_LIBC}-ports-${CT_LIBC_VERSION}" ${libc_src}
[ "${CT_LIBC_UCLIBC_LOCALES}" = "y" ] && CT_GetFile "uClibc-locale-030818" ${libc_src}
# libfloat if asked for
if [ "${CT_ARCH_FLOAT_SW_LIBFLOAT}" = "y" ]; then
lib_float_url="ftp://ftp.de.debian.org/debian/pool/main/libf/libfloat/"
# Please note: because the file we download, and the file we store on the
# file system don't have the same name, CT_GetFile will always try to
# download the file over and over.
# To avoid this, we check that the file we want already exists in the
# tarball directory first. This is an ugly hack that overrides the standard
# CT_GetFile behavior... Sight...
ext=`CT_GetFileExtension "${CT_LIBFLOAT_FILE}"`
if [ -z "${ext}" ]; then
CT_GetFile libfloat_990616.orig "${lib_float_url}"
ext=`CT_GetFileExtension "libfloat_990616.orig"`
# Hack: remove the .orig extension, and change _ to -
mv -v "${CT_TARBALLS_DIR}/libfloat_990616.orig${ext}" \
"${CT_TARBALLS_DIR}/libfloat-990616${ext}" 2>&1 |CT_DoLog DEBUG
fi
fi
CT_EndStep
fi # CT_NO_DOWNLOAD
if [ "${CT_ONLY_DOWNLOAD}" != "y" ]; then
CT_DoStep INFO "Extracting and patching toolchain components"
if [ "${CT_KERNEL_LINUX_HEADERS_USE_CUSTOM_DIR}" != "y" ]; then
CT_ExtractAndPatch "${CT_KERNEL_FILE}"
fi
CT_ExtractAndPatch "${CT_BINUTILS_FILE}"
CT_ExtractAndPatch "${CT_CC_CORE_FILE}"
CT_ExtractAndPatch "${CT_CC_FILE}"
CT_ExtractAndPatch "${CT_LIBC_FILE}"
for addon in ${addons_list}; do
CT_ExtractAndPatch "${CT_LIBC}-${addon}-${CT_LIBC_VERSION}"
done
[ "${CT_LIBC_GLIBC_USE_PORTS}" = "y" ] && CT_ExtractAndPatch "${CT_LIBC}-ports-${CT_LIBC_VERSION}"
[ "${CT_LIBC_UCLIBC_LOCALES}" = "y" ] && CT_ExtractAndPatch "uClibc-locale-030818"
[ "${CT_ARCH_FLOAT_SW_LIBFLOAT}" = "y" ] && CT_ExtractAndPatch "${CT_LIBFLOAT_FILE}"
CT_EndStep
fi

70
scripts/saveSample.sh Executable file
View File

@ -0,0 +1,70 @@
#!/bin/bash
# This script is responsible for saving the current configuration into a
# sample to be used later on as a pre-configured target.
# What we need to save:
# - the .config file
# - the kernel .config file if specified
# - the uClibc .config file if uClibc selected
. "${CT_TOP_DIR}/scripts/functions"
# Log to a temporary file until we have built our environment
CT_ACTUAL_LOG_FILE="${CT_TOP_DIR}/$$.log"
CT_LOG_INFO=y
CT_LOG_LEVEL_MAX="INFO"
# Parse the configuration file
CT_TestOrAbort "Configuration file not found. Please create one." -f "${CT_TOP_DIR}/.config"
. "${CT_TOP_DIR}/.config"
# Override log level
unset CT_LOG_ERROR CT_LOG_WARN CT_LOG_EXTRA CT_LOG_DEBUG
CT_LOG_INFO=y
CT_LOG_LEVEL_MAX="INFO"
# Target triplet: CT_TARGET needs a little love:
CT_DoBuildTargetTriplet
# Create the sample directory
[ -d "${CT_TOP_DIR}/samples/${CT_TARGET}" ] || svn mkdir "${CT_TOP_DIR}/samples/${CT_TARGET}" >/dev/null 2>&1
# Save the crosstool-NG config file
cp "${CT_TOP_DIR}/.config" "${CT_TOP_DIR}/samples/${CT_TARGET}/crosstool.config"
# Save the kernel .config file
if [ -n "${CT_KERNEL_LINUX_CONFIG_FILE}" ]; then
# We save the file, and then point the saved sample to this file
cp "${CT_KERNEL_LINUX_CONFIG_FILE}" "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_KERNEL}-${CT_KERNEL_VERSION}.config"
svn add "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_KERNEL}-${CT_KERNEL_VERSION}.config" >/dev/null 2>&1
sed -r -i -e 's|^(CT_KERNEL_LINUX_CONFIG_FILE=).+$|\1"${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_KERNEL}-${CT_KERNEL_VERSION}.config"|;' \
"${CT_TOP_DIR}/samples/${CT_TARGET}/crosstool.config"
else
# remove any dangling files
for f in "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_KERNEL}-"*.config; do
if [ -f "${f}" ]; then svn rm --force "${f}" >/dev/null 2>&1; fi
done
fi
# Save the uClibc .config file
if [ -n "${CT_LIBC_UCLIBC_CONFIG_FILE}" ]; then
# We save the file, and then point the saved sample to this file
cp "${CT_LIBC_UCLIBC_CONFIG_FILE}" "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_LIBC}-${CT_LIBC_VERSION}.config"
svn add "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_LIBC}-${CT_LIBC_VERSION}.config" >/dev/null 2>&1
sed -r -i -e 's|^(CT_LIBC_UCLIBC_CONFIG_FILE=).+$|\1"${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_LIBC}-${CT_LIBC_VERSION}.config"|;' \
"${CT_TOP_DIR}/samples/${CT_TARGET}/crosstool.config"
else
# remove any dangling files
for f in "${CT_TOP_DIR}/samples/${CT_TARGET}/${CT_LIBC}-"*.config; do
if [ -f "${f}" ]; then svn rm --force "${f}" >/dev/null 2>&1; fi
done
fi
# We could svn add earlier, but it's better to
# add a frozen file than modifying it later
svn add "${CT_TOP_DIR}/samples/${CT_TARGET}/crosstool.config" >/dev/null 2>&1
svn stat "${CT_TOP_DIR}/samples/${CT_TARGET}" 2>/dev/null |CT_DoLog INFO
rm -f "${CT_ACTUAL_LOG_FILE}"

View File

@ -9,3 +9,4 @@ updatetools:
help::
@echo ' updatetools - Update the config tools'
@echo ''