* add windows support via cygwin

* add openbsd and dragonfly support
* replace `` with $() in bash scripts
* misc other changes
This commit is contained in:
Thomas Pöchtrager 2015-07-19 22:28:10 +02:00
parent 6a35a0bf84
commit 29a5fee522
17 changed files with 567 additions and 148 deletions

View File

@ -2,8 +2,15 @@
changed: changed:
* improved and colorized wrapper error/warning/debug/info messages * improved and colorized wrapper error/warning/debug/info messages
* updated cctools to 870
* updated ld64 to 242
added: added:
* Windows support via Cygwin
* OpenBSD and DragonFlyBSD support
* Linux ARM support
* Linux PPC/PPC64 support: Totally untested, but compiles
* gcc compiler support: OSXCross can now be built with gcc
* 'osxcross-man' man page tool * 'osxcross-man' man page tool
* p7zip sdk packaging script * p7zip sdk packaging script
* a minimalistic xcrun tool * a minimalistic xcrun tool
@ -86,7 +93,7 @@ fixed:
/******************************* v0.4 *******************************/ /******************************* v0.4 *******************************/
added: added:
* gcc support * gcc build script
* a workaround for buggy unistd.h headers * a workaround for buggy unistd.h headers
/******************************* v0.3 *******************************/ /******************************* v0.3 *******************************/

View File

@ -1,8 +1,8 @@
## OS X Cross toolchain for Linux, FreeBSD and NetBSD ## ## OS X Cross toolchain for Linux, *BSD and Cygwin ##
### WHAT IS THE GOAL OF OSXCROSS? ### ### WHAT IS THE GOAL OF OSXCROSS? ###
The goal of OSXCross is to provide a well working OS X cross toolchain for Linux, FreeBSD and NetBSD. The goal of OSXCross is to provide a well working OS X cross toolchain for Linux, *BSD and Cygwin.
### HOW DOES IT WORK? ### ### HOW DOES IT WORK? ###
@ -27,7 +27,7 @@ Please see [README.MACPORTS](https://github.com/tpoechtrager/osxcross/blob/maste
Move your packaged SDK to the tarballs/ directory. Move your packaged SDK to the tarballs/ directory.
Then ensure you have the following installed on your Linux/BSD box: Then ensure you have the following installed on your system:
`Clang 3.2+`, `patch`, `libxml2-devel` (<=10.6 only) and the `bash shell`. `Clang 3.2+`, `patch`, `libxml2-devel` (<=10.6 only) and the `bash shell`.
@ -56,7 +56,7 @@ That's it. See usage examples below.
##### Building GCC: ##### ##### Building GCC: #####
If you want to build GCC as well, then you can do this by running: If you want to build GCC as well, then you can do this by running:
`[GCC_VERSION=5.1.0] [ENABLE_FORTRAN=1] ./build_gcc.sh`. `[GCC_VERSION=5.2.0] [ENABLE_FORTRAN=1] ./build_gcc.sh`.
\[A gfortran usage example can be found [here](https://github.com/tpoechtrager/osxcross/issues/28#issuecomment-67047134)] \[A gfortran usage example can be found [here](https://github.com/tpoechtrager/osxcross/issues/28#issuecomment-67047134)]
@ -91,7 +91,7 @@ You can turn this behavior off with `OSXCROSS_GCC_NO_STATIC_RUNTIME=1` (env).
Step 1. and 2. can be skipped if you have Xcode installed. Step 1. and 2. can be skipped if you have Xcode installed.
##### Packing the SDK on Linux (and others), Method 1 (works with Xcode >= 4.3): ##### ##### Packing the SDK on Linux, Cygwin (and others), Method 1 (works with Xcode >= 4.3): #####
1. Download Xcode like described in 'Packaging the SDK on Mac OS X' 1. Download Xcode like described in 'Packaging the SDK on Mac OS X'
2. Ensure you have `clang` and `make` installed 2. Ensure you have `clang` and `make` installed

View File

@ -13,23 +13,23 @@ function guess_sdk_version()
file= file=
sdk= sdk=
guess_sdk_version_result= guess_sdk_version_result=
sdkcount=`find -L tarballs/ -type f | grep MacOSX | wc -l` sdkcount=$(find -L tarballs/ -type f | grep MacOSX | wc -l)
if [ $sdkcount -eq 0 ]; then if [ $sdkcount -eq 0 ]; then
echo no SDK found in 'tarballs/'. please see README.md echo no SDK found in 'tarballs/'. please see README.md
exit 1 exit 1
elif [ $sdkcount -gt 1 ]; then elif [ $sdkcount -gt 1 ]; then
sdks=`find -L tarballs/ -type f | grep MacOSX` sdks=$(find -L tarballs/ -type f | grep MacOSX)
for sdk in $sdks; do echo $sdk; done for sdk in $sdks; do echo $sdk; done
echo 'more than one MacOSX SDK tarball found. please set' echo 'more than one MacOSX SDK tarball found. please set'
echo 'SDK_VERSION environment variable for the one you want' echo 'SDK_VERSION environment variable for the one you want'
echo '(for example: SDK_VERSION=10.x [OSX_VERSION_MIN=10.x] ./build.sh)' echo '(for example: SDK_VERSION=10.x [OSX_VERSION_MIN=10.x] ./build.sh)'
exit 1 exit 1
else else
sdk=`find -L tarballs/ -type f | grep MacOSX` sdk=$(find -L tarballs/ -type f | grep MacOSX)
tmp2=`echo ${sdk/bz2/} | sed s/[^0-9.]//g` tmp2=$(echo ${sdk/bz2/} | sed s/[^0-9.]//g)
tmp3=`echo $tmp2 | sed s/\\\.*$//g` tmp3=$(echo $tmp2 | sed s/\\\.*$//g)
guess_sdk_version_result=$tmp3 guess_sdk_version_result=$tmp3
echo 'found SDK version' $guess_sdk_version_result 'at tarballs/'`basename $sdk` echo 'found SDK version' $guess_sdk_version_result 'at tarballs/'$(basename $sdk)
fi fi
if [ $guess_sdk_version_result ]; then if [ $guess_sdk_version_result ]; then
if [ $guess_sdk_version_result = 10.4 ]; then if [ $guess_sdk_version_result = 10.4 ]; then
@ -44,7 +44,7 @@ function verify_sdk_version()
{ {
sdkv=$1 sdkv=$1
for file in tarballs/*; do for file in tarballs/*; do
if [ -f "$file" ] && [ `echo $file | grep OSX.*$sdkv` ]; then if [ -f "$file" ] && [ $(echo $file | grep OSX.*$sdkv) ]; then
echo "verified at "$file echo "verified at "$file
sdk=$file sdk=$file
fi fi
@ -119,7 +119,6 @@ require clang
require patch require patch
require sed require sed
require gunzip require gunzip
require cpio
pushd $BUILD_DIR &>/dev/null pushd $BUILD_DIR &>/dev/null
@ -171,6 +170,11 @@ pushd .. &>/dev/null
popd &>/dev/null popd &>/dev/null
patch -p0 < $PATCH_DIR/cctools-ld64-1.patch patch -p0 < $PATCH_DIR/cctools-ld64-1.patch
patch -p0 < $PATCH_DIR/cctools-ld64-2.patch patch -p0 < $PATCH_DIR/cctools-ld64-2.patch
if [ $PLATFORM == "OpenBSD" ] || [ $PLATFORM == "DragonFly" ]; then
pushd .. &>/dev/null
patch -p0 < $PATCH_DIR/cctools-ld64-epath.patch
popd &>/dev/null
fi
echo "" echo ""
CONFFLAGS="--prefix=$TARGET_DIR --target=x86_64-apple-$TARGET" CONFFLAGS="--prefix=$TARGET_DIR --target=x86_64-apple-$TARGET"
[ -n "$DISABLE_LTO_SUPPORT" ] && CONFFLAGS+=" --enable-lto=no" [ -n "$DISABLE_LTO_SUPPORT" ] && CONFFLAGS+=" --enable-lto=no"
@ -180,16 +184,16 @@ $MAKE install -j$JOBS
popd &>/dev/null popd &>/dev/null
pushd $TARGET_DIR/bin &>/dev/null pushd $TARGET_DIR/bin &>/dev/null
CCTOOLS=`find . -name "x86_64-apple-darwin*"` CCTOOLS=$(find . -name "x86_64-apple-darwin*")
CCTOOLS=($CCTOOLS) CCTOOLS=($CCTOOLS)
if [ $X86_64H_SUPPORTED -eq 1 ]; then if [ $X86_64H_SUPPORTED -eq 1 ]; then
for CCTOOL in ${CCTOOLS[@]}; do for CCTOOL in ${CCTOOLS[@]}; do
CCTOOL_X86_64H=`echo "$CCTOOL" | sed 's/x86_64/x86_64h/g'` CCTOOL_X86_64H=$(echo "$CCTOOL" | sed 's/x86_64/x86_64h/g')
ln -sf $CCTOOL $CCTOOL_X86_64H ln -sf $CCTOOL $CCTOOL_X86_64H
done done
fi fi
for CCTOOL in ${CCTOOLS[@]}; do for CCTOOL in ${CCTOOLS[@]}; do
CCTOOL_I386=`echo "$CCTOOL" | sed 's/x86_64/i386/g'` CCTOOL_I386=$(echo "$CCTOOL" | sed 's/x86_64/i386/g')
ln -sf $CCTOOL $CCTOOL_I386 ln -sf $CCTOOL $CCTOOL_I386
done done
popd &>/dev/null popd &>/dev/null
@ -204,7 +208,7 @@ ln -sf ../../tools/osxcross-macports osxcross-mp
ln -sf ../../tools/osxcross-macports omp ln -sf ../../tools/osxcross-macports omp
popd &>/dev/null popd &>/dev/null
SDK=`ls $TARBALL_DIR/MacOSX$SDK_VERSION*` SDK=$(ls $TARBALL_DIR/MacOSX$SDK_VERSION*)
# XAR # XAR
if [[ $SDK == *.pkg ]]; then if [[ $SDK == *.pkg ]]; then
@ -233,12 +237,12 @@ if [ ! -f "have_cctools_${CCTOOLS_REVHASH}_$TARGET" ]; then
function check_cctools() function check_cctools()
{ {
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-lipo" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-lipo" ] || exit 1
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-ld" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-ld" ] || exit 1
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-nm" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-nm" ] || exit 1
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-ar" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-ar" ] || exit 1
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-ranlib" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-ranlib" ] || exit 1
[ -f "/$TARGET_DIR/bin/$1-apple-$TARGET-strip" ] || exit 1 [ -f "$TARGET_DIR/bin/$1-apple-$TARGET-strip" ] || exit 1
} }
check_cctools i386 check_cctools i386
@ -274,7 +278,7 @@ extract $SDK 1 1
rm -rf $SDK_DIR/MacOSX$SDK_VERSION* 2>/dev/null rm -rf $SDK_DIR/MacOSX$SDK_VERSION* 2>/dev/null
if [ "`ls -l SDKs/*$SDK_VERSION* 2>/dev/null | wc -l | tr -d ' '`" != "0" ]; then if [ "$(ls -l SDKs/*$SDK_VERSION* 2>/dev/null | wc -l | tr -d ' ')" != "0" ]; then
mv -f SDKs/*$SDK_VERSION* $SDK_DIR mv -f SDKs/*$SDK_VERSION* $SDK_DIR
else else
mv -f *OSX*$SDK_VERSION*sdk* $SDK_DIR mv -f *OSX*$SDK_VERSION*sdk* $SDK_DIR
@ -309,7 +313,7 @@ export OSXCROSS_LINKER_VERSION=$LINKER_VERSION
if [ "$PLATFORM" != "Darwin" ]; then if [ "$PLATFORM" != "Darwin" ]; then
# libLTO.so # libLTO.so
set +e set +e
eval `cat $BUILD_DIR/cctools*/cctools/config.log | grep LLVM_LIB_DIR | head -n1` eval $(cat $BUILD_DIR/cctools*/cctools/config.log | grep LLVM_LIB_DIR | head -n1)
set -e set -e
export OSXCROSS_LIBLTO_PATH=$LLVM_LIB_DIR export OSXCROSS_LIBLTO_PATH=$LLVM_LIB_DIR
fi fi
@ -318,11 +322,11 @@ $BASE_DIR/wrapper/build.sh 1>/dev/null
echo "" echo ""
if [ `osxcross-cmp ${SDK_VERSION/u/} "<" $OSX_VERSION_MIN` -eq 1 ]; then if [ $(osxcross-cmp ${SDK_VERSION/u/} "<" $OSX_VERSION_MIN) -eq 1 ]; then
echo "OSX_VERSION_MIN must be <= SDK_VERSION" echo "OSX_VERSION_MIN must be <= SDK_VERSION"
trap "" EXIT trap "" EXIT
exit 1 exit 1
elif [ `osxcross-cmp $OSX_VERSION_MIN "<" 10.4` -eq 1 ]; then elif [ $(osxcross-cmp $OSX_VERSION_MIN "<" 10.4) -eq 1 ]; then
echo "OSX_VERSION_MIN must be >= 10.4" echo "OSX_VERSION_MIN must be >= 10.4"
trap "" EXIT trap "" EXIT
exit 1 exit 1
@ -336,7 +340,7 @@ test_compiler o64-clang $BASE_DIR/oclang/test.c
test_compiler o32-clang++ $BASE_DIR/oclang/test.cpp test_compiler o32-clang++ $BASE_DIR/oclang/test.cpp
test_compiler o64-clang++ $BASE_DIR/oclang/test.cpp test_compiler o64-clang++ $BASE_DIR/oclang/test.cpp
if [ `osxcross-cmp ${SDK_VERSION/u/} ">=" 10.7` -eq 1 ]; then if [ $(osxcross-cmp ${SDK_VERSION/u/} ">=" 10.7) -eq 1 ]; then
if [ ! -d "$SDK_DIR/MacOSX$SDK_VERSION.sdk/usr/include/c++/v1" ]; then if [ ! -d "$SDK_DIR/MacOSX$SDK_VERSION.sdk/usr/include/c++/v1" ]; then
echo "" echo ""
echo -n "Given SDK does not contain libc++ headers " echo -n "Given SDK does not contain libc++ headers "

View File

@ -31,17 +31,21 @@ set -e
CLANG_VERSION=$(echo "__clang_major__ __clang_minor__ __clang_patchlevel__" | \ CLANG_VERSION=$(echo "__clang_major__ __clang_minor__ __clang_patchlevel__" | \
clang -xc -E - | tail -n1 | tr ' ' '.') clang -xc -E - | tail -n1 | tr ' ' '.')
set +e if [[ $PLATFORM == CYGWIN* ]] && [[ $(which clang) == "/usr/bin/clang" ]]; then
which llvm-config &>/dev/null && { CLANG_LIB_DIR=$(llvm-config --libdir); } CLANG_LIB_DIR="/usr/lib/clang/$(uname -m)-pc-cygwin"
set -e else
set +e
which llvm-config &>/dev/null && { CLANG_LIB_DIR=$(llvm-config --libdir); }
set -e
if [ -z "$CLANG_LIB_DIR" ]; then if [ -z "$CLANG_LIB_DIR" ]; then
require $READLINK require $READLINK
CLANG_LIB_DIR="$(dirname $($READLINK -f $(which clang)))/../lib" CLANG_LIB_DIR="$(dirname $($READLINK -f $(which clang)))/../lib"
fi
CLANG_LIB_DIR+="/clang"
fi fi
CLANG_LIB_DIR+="/clang"
if [ ! -d "$CLANG_LIB_DIR" ]; then if [ ! -d "$CLANG_LIB_DIR" ]; then
echo "$CLANG_LIB_DIR does not exist!" 1>&2 echo "$CLANG_LIB_DIR does not exist!" 1>&2
echo "Installing llvm-dev may help" 1>&2 echo "Installing llvm-dev may help" 1>&2
@ -84,10 +88,10 @@ git clean -fdx
touch .clone_complete touch .clone_complete
git pull git pull
sed -i "s/Configs += ios//g" make/platform/clang_darwin.mk $SED -i "s/Configs += ios//g" make/platform/clang_darwin.mk
sed -i "s/Configs += cc_kext_ios5//g" make/platform/clang_darwin.mk $SED -i "s/Configs += cc_kext_ios5//g" make/platform/clang_darwin.mk
sed -i "s/Configs += profile_ios//g" make/platform/clang_darwin.mk $SED -i "s/Configs += profile_ios//g" make/platform/clang_darwin.mk
sed -i "s/Configs += asan_iossim_dynamic//g" make/platform/clang_darwin.mk $SED -i "s/Configs += asan_iossim_dynamic//g" make/platform/clang_darwin.mk
# Unbreak the -Werror build. # Unbreak the -Werror build.
if [ -f lib/asan/asan_mac.h ]; then if [ -f lib/asan/asan_mac.h ]; then

View File

@ -102,7 +102,7 @@ pushd $OSXCROSS_TARGET_DIR/x86_64-apple-$OSXCROSS_TARGET/include &>/dev/null
pushd c++/${GCC_VERSION}* &>/dev/null pushd c++/${GCC_VERSION}* &>/dev/null
cat $OSXCROSS_TARGET_DIR/../patches/libstdcxx.patch | \ cat $OSXCROSS_TARGET_DIR/../patches/libstdcxx.patch | \
sed "s/darwin13/$OSXCROSS_TARGET/g" | \ $SED "s/darwin13/$OSXCROSS_TARGET/g" | \
patch -p0 -l &>/dev/null || true patch -p0 -l &>/dev/null || true
popd &>/dev/null popd &>/dev/null

View File

@ -0,0 +1,343 @@
diff --git cctools/ld64/src/3rd/helper.c cctools/ld64/src/3rd/helper.c
index ef33219..6983e52 100644
--- cctools/ld64/src/3rd/helper.c
+++ cctools/ld64/src/3rd/helper.c
@@ -17,11 +17,17 @@ const char ldVersionString[] = "134.9\n";
#include <mach/host_info.h>
#include <sys/time.h>
#include <assert.h>
-
-#if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__)
+
+#if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__)
#include <sys/sysctl.h>
#endif
+#ifdef __OpenBSD__
+#include <sys/types.h>
+#include <sys/user.h>
+#include <sys/stat.h>
+#endif
+
#include "helper.h"
void __assert_rtn(const char *func, const char *file, int line, const char *msg)
@@ -36,39 +42,75 @@ void __assert_rtn(const char *func, const char *file, int line, const char *msg)
}
-int _NSGetExecutablePath(char *path, unsigned int *size)
+int _NSGetExecutablePath(char *epath, unsigned int *size)
{
-#ifdef __FreeBSD__
+#if defined(__FreeBSD__) || defined(__DragonFly__)
int mib[4];
- mib[0] = CTL_KERN;
+ mib[0] = CTL_KERN;
mib[1] = KERN_PROC;
mib[2] = KERN_PROC_PATHNAME;
mib[3] = -1;
size_t cb = *size;
- if (sysctl(mib, 4, path, &cb, NULL, 0) != 0)
+ if (sysctl(mib, 4, epath, &cb, NULL, 0) != 0)
return -1;
*size = cb;
- return 0;
+ return 0;
#elif defined(__OpenBSD__)
int mib[4];
- const char *tmp[100];
- size_t l = sizeof(tmp);
+ char **argv;
+ size_t len;
+ const char *comm;
+ int ok = 0;
mib[0] = CTL_KERN;
mib[1] = KERN_PROC_ARGS;
mib[2] = getpid();
mib[3] = KERN_PROC_ARGV;
- if (sysctl(mib, 4, tmp, &l, NULL, 0) != 0)
- return -1;
- *size = strlcpy(path, tmp[0], *size);
- return 0;
+ if (sysctl(mib, 4, NULL, &len, NULL, 0) < 0)
+ abort();
+ if (!(argv = malloc(len)))
+ abort();
+ if (sysctl(mib, 4, argv, &len, NULL, 0) < 0)
+ abort();
+ comm = argv[0];
+ if (*comm == '/' || *comm == '.') {
+ char *rpath;
+ if ((rpath = realpath(comm, NULL))) {
+ snprintf(epath, *size, "%s", rpath);
+ free(rpath);
+ ok = 1;
+ }
+ } else {
+ char *sp;
+ char *xpath = strdup(getenv("PATH"));
+ char *path = strtok_r(xpath, ":", &sp);
+ struct stat st;
+ if (!xpath)
+ abort();
+ while (path) {
+ snprintf(epath, *size, "%s/%s", path, comm);
+ if (!stat(epath, &st) && (st.st_mode & S_IXUSR)) {
+ ok = 1;
+ break;
+ }
+ path = strtok_r(NULL, ":", &sp);
+ }
+ free(xpath);
+ }
+ free(argv);
+ if (ok) {
+ *strrchr(epath, '/') = '\0';
+ *size = strlen(epath);
+ return 0;
+ }
+ return -1;
#else
int bufsize = *size;
int ret_size;
- ret_size = readlink("/proc/self/exe", path, bufsize-1);
+ ret_size = readlink("/proc/self/exe", epath, bufsize-1);
if (ret_size != -1)
{
*size = ret_size;
- path[ret_size]=0;
+ epath[ret_size]=0;
return 0;
}
else
diff --git cctools/libstuff/emulated.c cctools/libstuff/emulated.c
index 1aa355c..b8c52e4 100644
--- cctools/libstuff/emulated.c
+++ cctools/libstuff/emulated.c
@@ -14,46 +14,88 @@
#include <mach/host_info.h>
#include <sys/time.h>
-#if defined(__FreeBSD__) || defined(__OpenBSD__)
+#if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__)
#include <sys/sysctl.h>
#endif
-int _NSGetExecutablePath(char *path, unsigned int *size)
+#ifdef __OpenBSD__
+#include <sys/types.h>
+#include <sys/user.h>
+#include <sys/stat.h>
+#endif
+
+int _NSGetExecutablePath(char *epath, unsigned int *size)
{
-#ifdef __FreeBSD__
- int mib[4];
- mib[0] = CTL_KERN;
- mib[1] = KERN_PROC;
- mib[2] = KERN_PROC_PATHNAME;
- mib[3] = -1;
- size_t cb = *size;
- if (sysctl(mib, 4, path, &cb, NULL, 0) != 0)
+#if defined(__FreeBSD__) || defined(__DragonFly__)
+ int mib[4];
+ mib[0] = CTL_KERN;
+ mib[1] = KERN_PROC;
+ mib[2] = KERN_PROC_PATHNAME;
+ mib[3] = -1;
+ size_t cb = *size;
+ if (sysctl(mib, 4, epath, &cb, NULL, 0) != 0)
return -1;
- *size = cb;
- return 0;
+ *size = cb;
+ return 0;
#elif defined(__OpenBSD__)
- int mib[4];
- const char *tmp[100];
- size_t l = sizeof(tmp);
- mib[0] = CTL_KERN;
- mib[1] = KERN_PROC_ARGS;
- mib[2] = getpid();
- mib[3] = KERN_PROC_ARGV;
- if (sysctl(mib, 4, tmp, &l, NULL, 0) != 0)
- return -1;
- *size = strlcpy(path, tmp[0], *size);
- return 0;
+ int mib[4];
+ char **argv;
+ size_t len;
+ const char *comm;
+ int ok = 0;
+ mib[0] = CTL_KERN;
+ mib[1] = KERN_PROC_ARGS;
+ mib[2] = getpid();
+ mib[3] = KERN_PROC_ARGV;
+ if (sysctl(mib, 4, NULL, &len, NULL, 0) < 0)
+ abort();
+ if (!(argv = malloc(len)))
+ abort();
+ if (sysctl(mib, 4, argv, &len, NULL, 0) < 0)
+ abort();
+ comm = argv[0];
+ if (*comm == '/' || *comm == '.') {
+ char *rpath;
+ if ((rpath = realpath(comm, NULL))) {
+ snprintf(epath, *size, "%s", rpath);
+ free(rpath);
+ ok = 1;
+ }
+ } else {
+ char *sp;
+ char *xpath = strdup(getenv("PATH"));
+ char *path = strtok_r(xpath, ":", &sp);
+ struct stat st;
+ if (!xpath)
+ abort();
+ while (path) {
+ snprintf(epath, *size, "%s/%s", path, comm);
+ if (!stat(epath, &st) && (st.st_mode & S_IXUSR)) {
+ ok = 1;
+ break;
+ }
+ path = strtok_r(NULL, ":", &sp);
+ }
+ free(xpath);
+ }
+ free(argv);
+ if (ok) {
+ *strrchr(epath, '/') = '\0';
+ *size = strlen(epath);
+ return 0;
+ }
+ return -1;
#else
- int bufsize = *size;
- int ret_size;
- ret_size = readlink("/proc/self/exe", path, bufsize-1);
- if (ret_size != -1)
- {
+ int bufsize = *size;
+ int ret_size;
+ ret_size = readlink("/proc/self/exe", epath, bufsize-1);
+ if (ret_size != -1)
+ {
*size = ret_size;
- path[ret_size]=0;
+ epath[ret_size]=0;
return 0;
- }
- else
+ }
+ else
return -1;
#endif
}
diff --git usage_examples/ios_toolchain/wrapper.c usage_examples/ios_toolchain/wrapper.c
index ed536b2..438032f 100644
--- usage_examples/ios_toolchain/wrapper.c
+++ usage_examples/ios_toolchain/wrapper.c
@@ -19,30 +19,79 @@
#include <mach-o/dyld.h>
#endif
-#ifdef __FreeBSD__
+#if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__)
#include <sys/sysctl.h>
#endif
-char *get_executable_path(char *buf, size_t len)
+#ifdef __OpenBSD__
+#include <sys/types.h>
+#include <sys/user.h>
+#include <sys/stat.h>
+#endif
+
+char *get_executable_path(char *epath, size_t buflen)
{
char *p;
#ifdef __APPLE__
- unsigned int l = len;
- if (_NSGetExecutablePath(buf, &l) != 0) return NULL;
-#elif defined(__FreeBSD__)
+ unsigned int l = buflen;
+ if (_NSGetExecutablePath(epath, &l) != 0) return NULL;
+#elif defined(__FreeBSD__) || defined(__DragonFly__)
int mib[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, -1 };
- size_t l = len;
- if (sysctl(mib, 4, buf, &l, NULL, 0) != 0) return NULL;
-#elif defined(_WIN32)
- size_t l = GetModuleFileName(NULL, buf, (DWORD)len);
+ size_t l = buflen;
+ if (sysctl(mib, 4, epath, &l, NULL, 0) != 0) return NULL;
+#elif defined(__OpenBSD__)
+ int mib[4];
+ char **argv;
+ size_t len;
+ size_t l;
+ const char *comm;
+ int ok = 0;
+ mib[0] = CTL_KERN;
+ mib[1] = KERN_PROC_ARGS;
+ mib[2] = getpid();
+ mib[3] = KERN_PROC_ARGV;
+ if (sysctl(mib, 4, NULL, &len, NULL, 0) < 0)
+ abort();
+ if (!(argv = malloc(len)))
+ abort();
+ if (sysctl(mib, 4, argv, &len, NULL, 0) < 0)
+ abort();
+ comm = argv[0];
+ if (*comm == '/' || *comm == '.') {
+ char *rpath;
+ if ((rpath = realpath(comm, NULL))) {
+ snprintf(epath, buflen, "%s", rpath);
+ free(rpath);
+ ok = 1;
+ }
+ } else {
+ char *sp;
+ char *xpath = strdup(getenv("PATH"));
+ char *path = strtok_r(xpath, ":", &sp);
+ struct stat st;
+ if (!xpath)
+ abort();
+ while (path) {
+ snprintf(epath, buflen, "%s/%s", path, comm);
+ if (!stat(epath, &st) && (st.st_mode & S_IXUSR)) {
+ ok = 1;
+ break;
+ }
+ path = strtok_r(NULL, ":", &sp);
+ }
+ free(xpath);
+ }
+ free(argv);
+ if (!ok) return NULL;
+ l = strlen(epath);
#else
- ssize_t l = readlink("/proc/self/exe", buf, len);
+ ssize_t l = readlink("/proc/self/exe", epath, buflen);
#endif
if (l <= 0) return NULL;
- buf[len - 1] = '\0';
- p = strrchr(buf, '/');
+ epath[buflen - 1] = '\0';
+ p = strrchr(epath, '/');
if (p) *p = '\0';
- return buf;
+ return epath;
}
char *get_filename(char *str)
@@ -88,7 +137,7 @@ int main(int argc, char *argv[])
target_info(argv, &target, &compiler);
if (!get_executable_path(execpath, sizeof(execpath))) abort();
snprintf(sdkpath, sizeof(sdkpath), "%s/../SDK", execpath);
-
+
snprintf(codesign_allocate, sizeof(codesign_allocate),
"%s-codesign_allocate", target);

View File

@ -37,7 +37,8 @@
#endif /* __linux__ */ #endif /* __linux__ */
#if defined(__FreeBSD__) || defined(__NetBSD__) || \ #if defined(__FreeBSD__) || defined(__NetBSD__) || \
defined(__OpenBSD__) || defined(__APPLE__) defined(__OpenBSD__) || defined(__DragonFly__) || \
defined(__APPLE__)
#include <unistd.h> #include <unistd.h>
#include <sys/param.h> #include <sys/param.h>
#include <sys/types.h> #include <sys/types.h>
@ -70,7 +71,8 @@ int getcpucount() {
return cpucount ? cpucount : 1; return cpucount ? cpucount : 1;
#else #else
#if defined(__FreeBSD__) || defined(__NetBSD__) || \ #if defined(__FreeBSD__) || defined(__NetBSD__) || \
defined(__OpenBSD__) || defined(__APPLE__) defined(__OpenBSD__) || defined(__DragonFly__) || \
defined(__APPLE__)
int cpucount = 0; int cpucount = 0;
int mib[4]; int mib[4];
size_t len = sizeof(cpucount); size_t len = sizeof(cpucount);

View File

@ -306,7 +306,8 @@ installPkg()
echo "installing $pkgname ..." echo "installing $pkgname ..."
verboseMsg " extracting $pkgfile ..." verboseMsg " extracting $pkgfile ..."
tar xf "$CACHE/$pkgfile"
bzip2 -dc "$CACHE/$pkgfile" | tar xf -
if [ -d opt/local ]; then if [ -d opt/local ]; then
verboseMsg " fixing permissions ..." verboseMsg " fixing permissions ..."

View File

@ -3,9 +3,10 @@
pushd "${0%/*}" &>/dev/null pushd "${0%/*}" &>/dev/null
OSXCROSS_CONF="../target/bin/osxcross-conf" OSXCROSS_CONF="../target/bin/osxcross-conf"
test -f $OSXCROSS_CONF || { OSXCROSS_CONF=`which osxcross-conf 2>/dev/null` || exit 1; } [ -f $OSXCROSS_CONF ] || { OSXCROSS_CONF=$(which osxcross-conf 2>/dev/null) || exit 1; }
$OSXCROSS_CONF || exit 1 $OSXCROSS_CONF || exit 1
`dirname $OSXCROSS_CONF`/osxcross-env
$(dirname $OSXCROSS_CONF)/osxcross-env
popd &>/dev/null popd &>/dev/null

View File

@ -10,6 +10,10 @@ TARGET_DIR=$BASE_DIR/target
PATCH_DIR=$BASE_DIR/patches PATCH_DIR=$BASE_DIR/patches
SDK_DIR=$TARGET_DIR/SDK SDK_DIR=$TARGET_DIR/SDK
PLATFORM=$(uname -s)
SCRIPT=$(basename $0)
ARCH=$(uname -m)
if [ -z "$USESYSTEMCOMPILER" ]; then if [ -z "$USESYSTEMCOMPILER" ]; then
# Default to gcc on some OSs rather than clang due to either # Default to gcc on some OSs rather than clang due to either
# libstdc++ issues (clang uses an outdated version on those) # libstdc++ issues (clang uses an outdated version on those)
@ -53,18 +57,15 @@ fi
# enable debug messages # enable debug messages
test -n "$OCDEBUG" && set -x test -n "$OCDEBUG" && set -x
PLATFORM="`uname -s`"
SCRIPT="`basename $0`"
if [[ $SCRIPT != *wrapper/build.sh ]]; then if [[ $SCRIPT != *wrapper/build.sh ]]; then
# how many concurrent jobs should be used for compiling? # how many concurrent jobs should be used for compiling?
JOBS=${JOBS:=`tools/get_cpu_count.sh`} JOBS=${JOBS:=$(tools/get_cpu_count.sh)}
if [ $SCRIPT != "build.sh" -a $SCRIPT != "build_clang.sh" -a \ if [ $SCRIPT != "build.sh" -a $SCRIPT != "build_clang.sh" -a \
$SCRIPT != "mount_xcode_image.sh" -a \ $SCRIPT != "mount_xcode_image.sh" -a \
$SCRIPT != "gen_sdk_package_darling_dmg.sh" -a \ $SCRIPT != "gen_sdk_package_darling_dmg.sh" -a \
$SCRIPT != "gen_sdk_package_p7zip.sh" ]; then $SCRIPT != "gen_sdk_package_p7zip.sh" ]; then
`tools/osxcross_conf.sh` eval $(tools/osxcross_conf.sh)
if [ $? -ne 0 ]; then if [ $? -ne 0 ]; then
echo -n "you need to complete ./build.sh first, before you can start " echo -n "you need to complete ./build.sh first, before you can start "
@ -92,25 +93,31 @@ function require()
set -e set -e
} }
if [[ $PLATFORM == *BSD ]]; then if [[ $PLATFORM == *BSD ]] || [ $PLATFORM == "DragonFly" ]; then
MAKE=gmake MAKE=gmake
else else
MAKE=make MAKE=make
fi fi
if [[ $PLATFORM == OpenBSD ]]; then
SED=gsed
else
SED=sed
fi
if [[ $PLATFORM == *BSD ]] || [ $PLATFORM == "Darwin" ]; then if [[ $PLATFORM == *BSD ]] || [ $PLATFORM == "Darwin" ]; then
READLINK=greadlink READLINK=greadlink
else else
READLINK=readlink READLINK=readlink
fi fi
require $SED
require $MAKE require $MAKE
function extract() function extract()
{ {
test $# -ge 2 -a $# -lt 4 && test $2 -eq 2 && echo "" test $# -ge 2 -a $# -lt 4 && test $2 -eq 2 && echo ""
echo "extracting `basename $1` ..." echo "extracting $(basename $1) ..."
local tarflags local tarflags
@ -119,6 +126,7 @@ function extract()
case $1 in case $1 in
*.pkg) *.pkg)
require cpio
which xar &>/dev/null || exit 1 which xar &>/dev/null || exit 1
xar -xf $1 xar -xf $1
cat Payload | gunzip -dc | cpio -i 2>/dev/null && rm Payload cat Payload | gunzip -dc | cpio -i 2>/dev/null && rm Payload
@ -143,6 +151,17 @@ function extract()
fi fi
} }
if [[ $PLATFORM == CYGWIN* ]]; then
# Work around Cygwin brokenness.
function ln() {
[[ $1 == -* ]] && rm -f $3
$(which ln) $@
}
export -f ln
fi
function verbose_cmd() function verbose_cmd()
{ {
echo "$@" echo "$@"

View File

@ -30,9 +30,18 @@ ifneq (,$(findstring FreeBSD, $(PLATFORM)))
else ifneq (,$(findstring Darwin, $(PLATFORM))) else ifneq (,$(findstring Darwin, $(PLATFORM)))
override CXXFLAGS+=-Wno-deprecated override CXXFLAGS+=-Wno-deprecated
override LDFLAGS+=-framework CoreServices -Wno-deprecated override LDFLAGS+=-framework CoreServices -Wno-deprecated
else ifeq (,$(findstring Windows, $(PLATFORM))) else ifneq (,$(findstring CYGWIN, $(PLATFORM)))
# -std=gnu++0x doesn't work, so work around...
override CXXFLAGS+=-U__STRICT_ANSI__
else
ifeq (,$(findstring Windows, $(PLATFORM)))
ifeq (,$(findstring OpenBSD, $(PLATFORM)))
override LDFLAGS+=-lrt override LDFLAGS+=-lrt
endif endif
endif
endif
BIN=wrapper BIN=wrapper

View File

@ -7,10 +7,10 @@ popd &>/dev/null
set +e set +e
if [ -z "$OSXCROSS_VERSION" ]; then if [ -z "$OSXCROSS_VERSION" ]; then
`../target/bin/osxcross-conf 2>/dev/null` eval $(../target/bin/osxcross-conf 2>/dev/null)
if [ -n "$OSXCROSS_SDK_VERSION" ] && if [ -n "$OSXCROSS_SDK_VERSION" ] &&
[ `osxcross-cmp $OSXCROSS_SDK_VERSION ">=" 10.8` -eq 1 ]; then [ $(osxcross-cmp $OSXCROSS_SDK_VERSION ">=" 10.8) -eq 1 ]; then
X86_64H_SUPPORTED=1 X86_64H_SUPPORTED=1
fi fi
fi fi
@ -97,7 +97,6 @@ if [ -n "$BWPLATFORM" ]; then
[ -z "$BWCOMPILEONLY" ] && BWCOMPILEONLY=1 [ -z "$BWCOMPILEONLY" ] && BWCOMPILEONLY=1
else else
PLATFORM=$(uname -s)
[ -z "$PORTABLE"] && FLAGS="-march=native $CXXFLAGS " [ -z "$PORTABLE"] && FLAGS="-march=native $CXXFLAGS "
fi fi

View File

@ -777,7 +777,14 @@ int main(int argc, char **argv) {
} }
} }
#ifdef __DragonFly__
// Escape DragonFlyBSD's weird PFS paths.
std::string escapedexecpath;
escapePath(target.execpath, escapedexecpath);
concatEnvVariable("COMPILER_PATH", escapedexecpath);
#else
concatEnvVariable("COMPILER_PATH", target.execpath); concatEnvVariable("COMPILER_PATH", target.execpath);
#endif
if (target.targetarch.size() > 1 && (target.usegcclibs || target.isGCC())) if (target.targetarch.size() > 1 && (target.usegcclibs || target.isGCC()))
generateMultiArchObjectFile(rc, argc, argv, target, debug); generateMultiArchObjectFile(rc, argc, argv, target, debug);

View File

@ -37,43 +37,6 @@ int env(int argc, char **argv) {
if (!getExecutablePath(epath, sizeof(epath))) if (!getExecutablePath(epath, sizeof(epath)))
exit(EXIT_FAILURE); exit(EXIT_FAILURE);
// TODO: escape?
auto containsBadChars = [](const char * p, const char * desc)->bool {
if (!p)
return false;
const char *pp = p;
do {
auto badChar = [&](const char *p) {
err << desc << " should not contain '" << *p << "'" << warn.endl();
const char *start = p - std::min<size_t>(p - pp, 30);
size_t len = std::min<size_t>(strlen(start), 60);
std::cerr << std::endl;
std::cerr << std::string(start, len) << std::endl;
while (start++ != p)
std::cerr << " ";
std::cerr << "^" << std::endl;
};
switch (*p) {
case '"':
case '\'':
case '$':
case ' ':
case ';':
badChar(p);
return true;
}
} while (*p && *++p);
return false;
};
if (argc <= 1) { if (argc <= 1) {
const std::string &pname = getParentProcessName(); const std::string &pname = getParentProcessName();
@ -86,58 +49,15 @@ int env(int argc, char **argv) {
} }
} }
auto hasPath = [](const char * ov, const char * v, const char * vs)->bool { std::vector<std::string> path;
// ov = old value
// v = value
// vs = value suffix
if (!ov || !v)
return false;
bool hasPathSeparator = false;
for (auto p = ov; *p; ++p) {
if (*p == ':') {
hasPathSeparator = true;
break;
}
}
static std::string tmp;
auto check = [&](int t)->bool {
tmp.clear();
if (t == 0)
tmp = ':';
tmp += v;
if (vs)
tmp += vs;
if (t == 1)
tmp += ':';
return strstr(ov, tmp.c_str()) != nullptr;
};
return ((hasPathSeparator && (check(0) || check(1))) || check(-1));
};
if (containsBadChars(oldpath, "PATH"))
return 1;
std::stringstream path;
std::stringstream librarypath;
std::map<std::string, std::string> vars; std::map<std::string, std::string> vars;
path << oldpath; splitPath(oldpath, path);
if (!hasPath(oldpath, epath, nullptr)) if (!hasPath(path, epath))
path << ":" << epath; path.push_back(epath);
vars["PATH"] = path.str(); vars["PATH"] = joinPath(path);
auto printVariable = [&](const std::string & var)->bool { auto printVariable = [&](const std::string & var)->bool {
auto it = vars.find(var); auto it = vars.find(var);

View File

@ -359,6 +359,14 @@ do { \
#define TRYDIR2(libdir) TRYDIR(clangbindir, libdir) #define TRYDIR2(libdir) TRYDIR(clangbindir, libdir)
#define TRYDIR3(libdir) TRYDIR(std::string(), libdir) #define TRYDIR3(libdir) TRYDIR(std::string(), libdir)
#ifdef __CYGWIN__
#ifdef __x86_64__
TRYDIR2("/../lib/clang/x86_64-pc-cygwin");
#else
TRYDIR2("/../lib/clang/i686-pc-cygwin");
#endif
#endif
TRYDIR2("/../lib/clang"); TRYDIR2("/../lib/clang");
#ifdef __linux__ #ifdef __linux__

View File

@ -52,10 +52,13 @@
#include <libproc.h> #include <libproc.h>
#endif #endif
#ifdef __FreeBSD__ #if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__)
#include <sys/sysctl.h> #include <sys/sysctl.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/user.h> #include <sys/user.h>
#endif
#ifdef __FreeBSD__
#include <libutil.h> #include <libutil.h>
#endif #endif
@ -93,23 +96,60 @@ char *getExecutablePath(char *buf, size_t len) {
unsigned int l = len; unsigned int l = len;
if (_NSGetExecutablePath(buf, &l) != 0) if (_NSGetExecutablePath(buf, &l) != 0)
return nullptr; return nullptr;
#elif defined(__FreeBSD__) #elif defined(__FreeBSD__) || defined(__DragonFly__)
int mib[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, -1 }; int mib[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, -1 };
size_t l = len; size_t l = len;
if (sysctl(mib, 4, buf, &l, nullptr, 0) != 0) if (sysctl(mib, 4, buf, &l, nullptr, 0) != 0)
return nullptr; return nullptr;
#elif defined(__OpenBSD__)
int mib[4] = {CTL_KERN, KERN_PROC_ARGS, getpid(), KERN_PROC_ARGV};
char **argv;
size_t l;
const char *comm;
int ok = 0;
if (sysctl(mib, 4, NULL, &l, NULL, 0) < 0)
abort();
argv = new char *[l];
if (sysctl(mib, 4, argv, &l, NULL, 0) < 0)
abort();
comm = argv[0];
if (*comm == '/' || *comm == '.') {
if (realpath(comm, buf))
ok = 1;
} else {
char *sp;
char *xpath = strdup(getenv("PATH"));
char *path = strtok_r(xpath, ":", &sp);
struct stat st;
if (!xpath)
abort();
while (path) {
snprintf(buf, len, "%s/%s", path, comm);
if (!stat(buf, &st) && (st.st_mode & S_IXUSR)) {
ok = 1;
break;
}
path = strtok_r(NULL, ":", &sp);
}
free(xpath);
}
if (ok)
l = strlen(buf);
else
l = 0;
delete[] argv;
#elif defined(_WIN32) #elif defined(_WIN32)
size_t l = GetModuleFileName(nullptr, buf, (DWORD)len); size_t l = GetModuleFileName(nullptr, buf, (DWORD)len);
#else #else
ssize_t l = readlink("/proc/self/exe", buf, len); ssize_t l = readlink("/proc/self/exe", buf, len);
assert(l > 0 && "/proc not mounted?");
#endif #endif
if (l <= 0) if (l <= 0)
return nullptr; return nullptr;
buf[len - 1] = '\0'; buf[len - 1] = '\0';
p = strrchr(buf, PATHDIV); p = strrchr(buf, PATHDIV);
if (p) { if (p)
*p = '\0'; *p = '\0';
}
return buf; return buf;
} }
@ -234,6 +274,57 @@ void concatEnvVariable(const char *var, const std::string &val) {
setenv(var, nval.c_str(), 1); setenv(var, nval.c_str(), 1);
} }
std::string &escapePath(const std::string &path, std::string &escapedpath) {
for (const char *p = path.c_str(); *p; ++p) {
switch (*p) {
case '"':
case '\'':
case '\\':
case '$':
case '(':
case ')':
case ' ':
case ';':
case ':':
escapedpath += '\\';
}
escapedpath += *p;
}
return escapedpath;
}
void splitPath(const char *path, std::vector<std::string> &result) {
char *sp;
char *xpath = strdup(path);
char *p = strtok_r(xpath, ":", &sp);
if (!xpath)
abort();
while (p) {
result.push_back(p);
p = strtok_r(NULL, ":", &sp);
}
free(xpath);
}
std::string joinPath(const std::vector<std::string> &path) {
std::string tmp;
std::string escaped;
for (size_t i = 0; i < path.size(); ++i) {
escaped.clear();
tmp += escapePath(path[i], escaped);
if (i != path.size() - 1)
tmp += ":";
}
return tmp;
}
bool hasPath(const std::vector<std::string> &path, const char *find) {
for (const std::string &p : path)
if (p == find)
return true;
return false;
}
// //
// Files and Directories // Files and Directories
// //

View File

@ -127,6 +127,10 @@ std::string &fixPathDiv(std::string &path);
// //
void concatEnvVariable(const char *var, const std::string &val); void concatEnvVariable(const char *var, const std::string &val);
std::string &escapePath(const std::string &path, std::string &escapedpath);
void splitPath(const char *path, std::vector<std::string> &result);
std::string joinPath(const std::vector<std::string> &path);
bool hasPath(const std::vector<std::string> &path, const char *find);
// //
// Files and directories // Files and directories