mirror of
https://github.com/ilyakooo0/nixpkgs.git
synced 2024-11-19 02:44:17 +03:00
* Ensure that when building gcc, libstdc++ is linked against the
libgcc of the gcc being built, not the gcc building it. * Only include a directory in the rpath of an executable/library if it is actually used. Before, the `/lib' directory of every build input was added to the rpath, causing many unnecessary retained dependencies. For instance, Perl has a `/lib' directory, but most applications whose build process uses Perl don't actually link against Perl. (Also added a test for this.) * After building glibc, remove glibcbug, to prevent a retained dependency on gcc. * Add a newline after `building X' in GNU Make. svn path=/nixpkgs/trunk/; revision=911
This commit is contained in:
parent
0d4967fc35
commit
beaff0a892
30
pkgs/TODO
30
pkgs/TODO
@ -8,31 +8,5 @@
|
|||||||
|
|
||||||
* Inform freedesktop people that Xaw requires Xpm.
|
* Inform freedesktop people that Xaw requires Xpm.
|
||||||
|
|
||||||
* Only add --rpath FOO/lib if FOO/lib is actually used, otherwise we
|
* After building gcc, filter out references to /tmp/nix... in
|
||||||
get lots of unneccesarily retained dependencies.
|
.../lib/libsupc++.la and .../lib/libstdc++.la
|
||||||
|
|
||||||
* After building gcc, filter out this sillyness in .../lib/libsupc++.la and .../lib/libstdc++.la:
|
|
||||||
|
|
||||||
/nix/store/fd3dba2a24f0242af8ea7e896380be7e-gcc-3.3.3/lib/libsupc++.la:dependency_libs='
|
|
||||||
-L/tmp/nix-26124-33/build/i686-pc-linux-gnu/libstdc++-v3/src
|
|
||||||
-L/tmp/nix-26124-33/build/i686-pc-linux-gnu/libstdc++-v3/src/.libs -lm
|
|
||||||
-L/tmp/nix-26124-33/build/gcc
|
|
||||||
-L/nix/store/e173bb830ba5f727ae63e0673d929bc7-gcc-3.3.3/bin
|
|
||||||
-L/nix/store/23ef1e01b61105fee5ef8b47faf30675-glibc-2.3.2/lib
|
|
||||||
-L/nix/store/6d3bf84aeb18d6d92a25ce9692b0f4d2-gcc-3.3.3/lib -lgcc_s
|
|
||||||
-lc -lgcc_s'
|
|
||||||
|
|
||||||
/nix/store/fd3dba2a24f0242af8ea7e896380be7e-gcc-3.3.3/lib/libstdc++.la:dependency_libs='
|
|
||||||
-L/tmp/nix-26124-33/build/i686-pc-linux-gnu/libstdc++-v3/src
|
|
||||||
-L/tmp/nix-26124-33/build/i686-pc-linux-gnu/libstdc++-v3/src/.libs -lm
|
|
||||||
-lm -lm -L/tmp/nix-26124-33/build/gcc
|
|
||||||
-L/nix/store/e173bb830ba5f727ae63e0673d929bc7-gcc-3.3.3/bin
|
|
||||||
-L/nix/store/23ef1e01b61105fee5ef8b47faf30675-glibc-2.3.2/lib
|
|
||||||
-L/nix/store/6d3bf84aeb18d6d92a25ce9692b0f4d2-gcc-3.3.3/lib -lgcc_s
|
|
||||||
-lc -lgcc_s -lm -lgcc_s -lc -lgcc_s'
|
|
||||||
|
|
||||||
in particular references to /tmp/nix... and to /nix/store/...-
|
|
||||||
|
|
||||||
i.e., basically all -L... switches
|
|
||||||
|
|
||||||
this causes lots of unneccesarily retained dependencies
|
|
||||||
|
@ -10,14 +10,14 @@ if test -z "$nativeGlibc"; then
|
|||||||
# /usr/lib. The real solution is of course to prevent those paths
|
# /usr/lib. The real solution is of course to prevent those paths
|
||||||
# from being used by gcc in the first place.
|
# from being used by gcc in the first place.
|
||||||
cflagsCompile="$cflagsCompile -B$glibc/lib -isystem $glibc/include"
|
cflagsCompile="$cflagsCompile -B$glibc/lib -isystem $glibc/include"
|
||||||
ldflags="$ldflags -L$glibc/lib -rpath $glibc/lib -dynamic-linker $glibc/lib/ld-linux.so.2"
|
ldflags="$ldflags -L$glibc/lib -dynamic-linker $glibc/lib/ld-linux.so.2"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if test -n "$nativeTools"; then
|
if test -n "$nativeTools"; then
|
||||||
gccPath="$nativePrefix/bin"
|
gccPath="$nativePrefix/bin"
|
||||||
ldPath="$nativePrefix/bin"
|
ldPath="$nativePrefix/bin"
|
||||||
else
|
else
|
||||||
ldflags="$ldflags -L$gcc/lib -rpath $gcc/lib"
|
ldflags="$ldflags -L$gcc/lib"
|
||||||
gccPath="$gcc/bin"
|
gccPath="$gcc/bin"
|
||||||
ldPath="$binutils/bin"
|
ldPath="$binutils/bin"
|
||||||
fi
|
fi
|
||||||
|
@ -47,6 +47,84 @@ if test -z "$NIX_LDFLAGS_SET"; then
|
|||||||
extra=(${extra[@]} $NIX_LDFLAGS)
|
extra=(${extra[@]} $NIX_LDFLAGS)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
|
||||||
|
# Add all used dynamic libraries to the rpath.
|
||||||
|
if test "$NIX_DONT_SET_RPATH" != "1"; then
|
||||||
|
|
||||||
|
# First, find all -L... switches.
|
||||||
|
allParams=("${params[@]}" ${extra[@]})
|
||||||
|
libPath=""
|
||||||
|
addToLibPath() {
|
||||||
|
local path="$1"
|
||||||
|
if test "${path:0:1}" != "/"; then return 0; fi
|
||||||
|
case "$path" in
|
||||||
|
*..*|*./*|*/.*|*//*)
|
||||||
|
local path2
|
||||||
|
if path2=$(readlink -f "$path"); then
|
||||||
|
path="$path2"
|
||||||
|
fi
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
case $libPath in
|
||||||
|
*\ $path\ *) return 0 ;;
|
||||||
|
esac
|
||||||
|
libPath="$libPath $path "
|
||||||
|
}
|
||||||
|
n=0
|
||||||
|
while test $n -lt ${#allParams[*]}; do
|
||||||
|
p=${allParams[n]}
|
||||||
|
p2=${allParams[$((n+1))]}
|
||||||
|
if test "${p:0:3}" = "-L/"; then
|
||||||
|
addToLibPath ${p:2}
|
||||||
|
elif test "$p" = "-L"; then
|
||||||
|
addToLibPath ${p2}
|
||||||
|
n=$((n + 1))
|
||||||
|
fi
|
||||||
|
n=$((n + 1))
|
||||||
|
done
|
||||||
|
|
||||||
|
# Second, for each -l... switch, find the directory containing the
|
||||||
|
# library and add it to the rpath.
|
||||||
|
rpath=""
|
||||||
|
addToRPath() {
|
||||||
|
# If the path is not in the store, don't add it to the rpath.
|
||||||
|
# This typically happens for libraries in /tmp that are later
|
||||||
|
# copied to $out/lib. If not, we're screwed.
|
||||||
|
if test "${1:0:${#NIX_STORE}}" != "$NIX_STORE"; then return 0; fi
|
||||||
|
case $rpath in
|
||||||
|
*\ $1\ *) return 0 ;;
|
||||||
|
esac
|
||||||
|
rpath="$rpath $1 "
|
||||||
|
}
|
||||||
|
findLib() {
|
||||||
|
for i in $libPath; do
|
||||||
|
if test -f $i/lib$1.so; then
|
||||||
|
addToRPath $i
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
}
|
||||||
|
n=0
|
||||||
|
while test $n -lt ${#allParams[*]}; do
|
||||||
|
p=${allParams[n]}
|
||||||
|
p2=${allParams[$((n+1))]}
|
||||||
|
if test "${p:0:2}" = "-l"; then
|
||||||
|
findLib ${p:2}
|
||||||
|
elif test "$p" = "-l"; then
|
||||||
|
# I haven't seen `-l foo', but you never know...
|
||||||
|
findLib ${p2}
|
||||||
|
n=$((n + 1))
|
||||||
|
fi
|
||||||
|
n=$((n + 1))
|
||||||
|
done
|
||||||
|
|
||||||
|
# Finally, add `-rpath' switches.
|
||||||
|
for i in $rpath; do
|
||||||
|
extra=(${extra[@]} -rpath $i)
|
||||||
|
done
|
||||||
|
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
||||||
# Optionally print debug info.
|
# Optionally print debug info.
|
||||||
if test "$NIX_DEBUG" = "1"; then
|
if test "$NIX_DEBUG" = "1"; then
|
||||||
echo "original flags to @ld@:" >&2
|
echo "original flags to @ld@:" >&2
|
||||||
|
@ -4,7 +4,7 @@ addCVars () {
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
if test -d $1/lib; then
|
if test -d $1/lib; then
|
||||||
export NIX_LDFLAGS="$NIX_LDFLAGS -L$1/lib -rpath $1/lib"
|
export NIX_LDFLAGS="$NIX_LDFLAGS -L$1/lib"
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,21 +40,38 @@ postConfigure() {
|
|||||||
if test "$noSysDirs" = "1"; then
|
if test "$noSysDirs" = "1"; then
|
||||||
# Patch some of the makefiles to force linking against our own
|
# Patch some of the makefiles to force linking against our own
|
||||||
# glibc.
|
# glibc.
|
||||||
. $NIX_GCC/nix-support/add-flags # add glibc/gcc flags
|
if test -e $NIX_GCC/nix-support/orig-glibc; then
|
||||||
extraflags="-Wl,-s $NIX_CFLAGS_COMPILE $NIX_CFLAGS_LINK"
|
glibc=$(cat $NIX_GCC/nix-support/orig-glibc)
|
||||||
for i in $NIX_LDFLAGS; do
|
# Ugh. Copied from gcc-wrapper/builder.sh. We can't just
|
||||||
extraflags="$extraflags -Wl,$i"
|
# source in $NIX_GCC/nix-support/add-flags, since that
|
||||||
done
|
# would cause *this* GCC to be linked against the
|
||||||
|
# *previous* GCC. Need some more modularity there.
|
||||||
|
extraFlags="-Wl,-s -B$glibc/lib -isystem $glibc/include \
|
||||||
|
-L$glibc/lib -Wl,-dynamic-linker -Wl,$glibc/lib/ld-linux.so.2"
|
||||||
|
|
||||||
|
# Oh, what a hack. I should be shot for this.
|
||||||
|
# In stage 1, we should link against the previous GCC, but
|
||||||
|
# not afterwards. Otherwise we retain a dependency.
|
||||||
|
# However, ld-wrapper, which adds the linker flags for the
|
||||||
|
# previous GCC, is also used in stage 2/3. We can prevent
|
||||||
|
# it from adding them by NIX_GLIBC_FLAGS_SET, but then
|
||||||
|
# gcc-wrapper will also not add them, thereby causing
|
||||||
|
# stage 1 to fail. So we use a trick to only set the
|
||||||
|
# flags in gcc-wrapper.
|
||||||
|
hook=$(pwd)/ld-wrapper-hook
|
||||||
|
echo "NIX_GLIBC_FLAGS_SET=1" > $hook
|
||||||
|
export NIX_LD_WRAPPER_START_HOOK=$hook
|
||||||
|
fi
|
||||||
|
|
||||||
mf=Makefile
|
mf=Makefile
|
||||||
sed \
|
sed \
|
||||||
-e "s^FLAGS_FOR_TARGET =\(.*\)^FLAGS_FOR_TARGET = \1 $extraflags^" \
|
-e "s^FLAGS_FOR_TARGET =\(.*\)^FLAGS_FOR_TARGET = \1 $extraFlags^" \
|
||||||
< $mf > $mf.tmp
|
< $mf > $mf.tmp
|
||||||
mv $mf.tmp $mf
|
mv $mf.tmp $mf
|
||||||
|
|
||||||
mf=gcc/Makefile
|
mf=gcc/Makefile
|
||||||
sed \
|
sed \
|
||||||
-e "s^X_CFLAGS =\(.*\)^X_CFLAGS = \1 $extraflags^" \
|
-e "s^X_CFLAGS =\(.*\)^X_CFLAGS = \1 $extraFlags^" \
|
||||||
< $mf > $mf.tmp
|
< $mf > $mf.tmp
|
||||||
mv $mf.tmp $mf
|
mv $mf.tmp $mf
|
||||||
|
|
||||||
|
@ -4,13 +4,6 @@ export NIX_NO_SELF_RPATH=1
|
|||||||
. $stdenv/setup
|
. $stdenv/setup
|
||||||
|
|
||||||
|
|
||||||
# !!! Toss the linker flags. Any sort of rpath is fatal.
|
|
||||||
# This probably will cause a failure when building in a pure Nix
|
|
||||||
# environment.
|
|
||||||
export NIX_LDFLAGS=
|
|
||||||
export NIX_GLIBC_FLAGS_SET=1
|
|
||||||
|
|
||||||
|
|
||||||
postUnpack() {
|
postUnpack() {
|
||||||
cd $sourceRoot
|
cd $sourceRoot
|
||||||
unpackFile $linuxthreadsSrc
|
unpackFile $linuxthreadsSrc
|
||||||
@ -35,6 +28,8 @@ postInstall() {
|
|||||||
make localedata/install-locales
|
make localedata/install-locales
|
||||||
rm $out/etc/ld.so.cache
|
rm $out/etc/ld.so.cache
|
||||||
(cd $out/include && ln -s $kernelHeaders/include/* .) || exit 1
|
(cd $out/include && ln -s $kernelHeaders/include/* .) || exit 1
|
||||||
|
# `glibcbug' causes a retained dependency on the C compiler.
|
||||||
|
rm $out/bin/glibcbug
|
||||||
}
|
}
|
||||||
|
|
||||||
postInstall=postInstall
|
postInstall=postInstall
|
||||||
|
@ -108,14 +108,14 @@ diff -rc make-3.80-orig/make.h make-3.80/make.h
|
|||||||
+ extern int logNestingStderr;
|
+ extern int logNestingStderr;
|
||||||
diff -rc make-3.80-orig/remake.c make-3.80/remake.c
|
diff -rc make-3.80-orig/remake.c make-3.80/remake.c
|
||||||
*** make-3.80-orig/remake.c 2002-08-08 02:11:19.000000000 +0200
|
*** make-3.80-orig/remake.c 2002-08-08 02:11:19.000000000 +0200
|
||||||
--- make-3.80/remake.c 2004-04-02 17:43:00.000000000 +0200
|
--- make-3.80/remake.c 2004-04-04 23:10:19.000000000 +0200
|
||||||
***************
|
***************
|
||||||
*** 1049,1055 ****
|
*** 1049,1055 ****
|
||||||
--- 1049,1059 ----
|
--- 1049,1059 ----
|
||||||
/* The normal case: start some commands. */
|
/* The normal case: start some commands. */
|
||||||
if (!touch_flag || file->cmds->any_recurse)
|
if (!touch_flag || file->cmds->any_recurse)
|
||||||
{
|
{
|
||||||
+ fprintf(stderr, "\e[pbuilding %s", file->name);
|
+ fprintf(stderr, "\e[pbuilding %s\n", file->name);
|
||||||
+ logNestingStderr++;
|
+ logNestingStderr++;
|
||||||
execute_file_commands (file);
|
execute_file_commands (file);
|
||||||
+ fprintf(stderr, "\e[q");
|
+ fprintf(stderr, "\e[q");
|
||||||
|
79
pkgs/test/rpath/builder.sh
Normal file
79
pkgs/test/rpath/builder.sh
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
export NIX_DEBUG=1
|
||||||
|
|
||||||
|
. $stdenv/setup
|
||||||
|
|
||||||
|
mkdir $out
|
||||||
|
mkdir $out/bin
|
||||||
|
|
||||||
|
|
||||||
|
# 1: link statically against glibc.
|
||||||
|
res=$out/bin/hello1
|
||||||
|
gcc -static $src/hello1.c -o $res
|
||||||
|
|
||||||
|
case $(ldd $res) in
|
||||||
|
*"not a dynamic executable"*)
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "$res not statically linked!"
|
||||||
|
exit 1
|
||||||
|
esac
|
||||||
|
|
||||||
|
|
||||||
|
# 2: link dynamically against glibc.
|
||||||
|
res=$out/bin/hello2
|
||||||
|
gcc $src/hello1.c -o $res
|
||||||
|
|
||||||
|
case $(ldd $res) in
|
||||||
|
*/store/*glibc*/lib/libc.so*/store/*glibc*/lib/ld-linux.so*)
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "$res not dynamically linked / bad rpath!"
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
|
||||||
|
# 3: link C++ dynamically against glibc / libstdc++.
|
||||||
|
res=$out/bin/hello3
|
||||||
|
g++ $src/hello2.cc -o $res
|
||||||
|
|
||||||
|
case $(ldd $res) in
|
||||||
|
*/store/*gcc*/lib/*libstdc++*/store/*glibc*/lib/libm*/store/*gcc*/lib/libgcc_s*/store/*glibc*/lib/libc.so*/store/*glibc*/lib/ld-linux.so*)
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "$res not dynamically linked / bad rpath!"
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
|
||||||
|
# 4: build dynamic library locally, link against it, copy it.
|
||||||
|
res=$out/bin/hello4
|
||||||
|
mkdir bla
|
||||||
|
gcc -shared $src/text.c -o bla/libtext.so
|
||||||
|
gcc $src/hello3.c -o $res -L$(pwd)/bla -ltext
|
||||||
|
mkdir $out/lib
|
||||||
|
|
||||||
|
case $(ldd $res) in
|
||||||
|
*/tmp*)
|
||||||
|
echo "$res depends on file in /tmp!"
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
cp bla/libtext.so $out/lib
|
||||||
|
|
||||||
|
case $(ldd $res) in
|
||||||
|
*/store/*glibc*/lib/libc.so*/store/*glibc*/lib/ld-linux.so*)
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo "$res not dynamically linked / bad rpath!"
|
||||||
|
exit 1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
|
||||||
|
# Run the programs we just made.
|
||||||
|
for i in $out/bin/*; do
|
||||||
|
$i
|
||||||
|
done
|
18
pkgs/test/rpath/default.nix
Normal file
18
pkgs/test/rpath/default.nix
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
let {
|
||||||
|
system = "i686-linux";
|
||||||
|
|
||||||
|
stdenvs = (import ../../system/stdenvs.nix) {
|
||||||
|
inherit system;
|
||||||
|
allPackages = import ../../system/all-packages-generic.nix;
|
||||||
|
};
|
||||||
|
|
||||||
|
stdenv = stdenvs.stdenvLinuxBoot2;
|
||||||
|
|
||||||
|
test = stdenv.mkDerivation {
|
||||||
|
name = "rpath-test";
|
||||||
|
builder = ./builder.sh;
|
||||||
|
src = ./src;
|
||||||
|
};
|
||||||
|
|
||||||
|
body = test;
|
||||||
|
}
|
7
pkgs/test/rpath/src/hello1.c
Normal file
7
pkgs/test/rpath/src/hello1.c
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
int main(int argc, char * * argv)
|
||||||
|
{
|
||||||
|
printf("Hello World!\n");
|
||||||
|
return 0;
|
||||||
|
}
|
7
pkgs/test/rpath/src/hello2.cc
Normal file
7
pkgs/test/rpath/src/hello2.cc
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
int main(int argc, char * * argv)
|
||||||
|
{
|
||||||
|
std::cout << "Hello World!\n";
|
||||||
|
return 0;
|
||||||
|
}
|
9
pkgs/test/rpath/src/hello3.c
Normal file
9
pkgs/test/rpath/src/hello3.c
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
char * text();
|
||||||
|
|
||||||
|
int main(int argc, char * * argv)
|
||||||
|
{
|
||||||
|
printf(text());
|
||||||
|
return 0;
|
||||||
|
}
|
4
pkgs/test/rpath/src/text.c
Normal file
4
pkgs/test/rpath/src/text.c
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
char * text()
|
||||||
|
{
|
||||||
|
return "Hello World!\n";
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user