Skip to content

Commit 306d5cd

Browse files
committed
perlPackages: Add cross-compilation support.
This involved: * Installing miniperl as $dev/bin/perl * Setting miniperl to take INC from lib/perl5/{site_perl/,}cross_perl/${version} as well as lib/perl5/{site_perl/,}/${version}/${runtimeArch}, in that order. miniperl taking from runtimeArch is not really correct, but it works in some pure-perl cases (e.g. Config.pm) and can be overridden with the cross_perl variant. * Installing perl-cross's stubs into $dev/lib/perl5/cross_perl/${version} * Patching MakeMaker.pm to gracefully degrade (very slightly) if B.pm can't be loaded, which it can't in cross-compilation. * Passing the right build-time and runtime perls to Makefile.PL
1 parent 8e65205 commit 306d5cd

6 files changed

Lines changed: 81 additions & 7 deletions

File tree

doc/languages-frameworks/perl.xml

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -177,5 +177,18 @@ you need it.</para>
177177

178178
</section>
179179

180+
<section xml:id="ssec-perl-cross-compilation"><title>Cross-compiling modules</title>
181+
182+
<para>Nixpkgs has experimental support for cross-compiling Perl
183+
modules. In many cases, it will just work out of the box, even for
184+
modules with native extensions. Sometimes, however, the Makefile.PL
185+
for a module may (indirectly) import a native module. In that case,
186+
you will need to make a stub for that module that will satisfy the
187+
Makefile.PL and install it into
188+
<filename>lib/perl5/site_perl/cross_perl/${perl.version}</filename>.
189+
</para>
190+
191+
</section>
192+
180193
</section>
181194

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
diff -Naur a/cpan/ExtUtils-MakeMaker/lib/ExtUtils/MakeMaker.pm b/cpan/ExtUtils-MakeMaker/lib/ExtUtils/MakeMaker.pm
2+
--- a/cpan/ExtUtils-MakeMaker/lib/ExtUtils/MakeMaker.pm 2017-06-30 17:03:20.000000000 -0400
3+
+++ b/cpan/ExtUtils-MakeMaker/lib/ExtUtils/MakeMaker.pm 2018-02-28 10:06:37.031237946 -0500
4+
@@ -1267,7 +1267,12 @@
5+
my $value = shift;
6+
return $value if $UNDER_CORE;
7+
my $tvalue = '';
8+
- require B;
9+
+ eval {
10+
+ require B;
11+
+ };
12+
+ if ($@) {
13+
+ return $tvalue;
14+
+ }
15+
my $sv = B::svref_2object(\$value);
16+
my $magic = ref($sv) eq 'B::PVMG' ? $sv->MAGIC : undef;
17+
while ( $magic ) {

pkgs/development/interpreters/perl/default.nix

Lines changed: 35 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
{ lib, stdenv, fetchurlBoot, buildPackages, enableThreading ? stdenv ? glibc, fetchpatch }:
1+
{ lib, stdenv, fetchurlBoot, buildPackages
2+
, enableThreading ? stdenv ? glibc, fetchpatch, makeWrapper
3+
}:
24

35
with lib;
46

@@ -29,7 +31,8 @@ let
2931
};
3032

3133
# TODO: Add a "dev" output containing the header files.
32-
outputs = [ "out" "man" "devdoc" ];
34+
outputs = [ "out" "man" "devdoc" ] ++
35+
stdenv.lib.optional crossCompiling "dev";
3336
setOutputFlags = false;
3437

3538
patches =
@@ -45,7 +48,8 @@ let
4548
})
4649
++ optional stdenv.isSunOS ./ld-shared.patch
4750
++ optional stdenv.isDarwin ./cpp-precomp.patch
48-
++ optional (stdenv.isDarwin && versionAtLeast version "5.24") ./sw_vers.patch;
51+
++ optional (stdenv.isDarwin && versionAtLeast version "5.24") ./sw_vers.patch
52+
++ optional crossCompiling ./MakeMaker-cross.patch;
4953

5054
postPatch = ''
5155
pwd="$(type -P pwd)"
@@ -117,6 +121,28 @@ let
117121
if stdenv.cc.cc or null != null then stdenv.cc.cc else "/no-such-path"
118122
}" /no-such-path \
119123
--replace "$man" /no-such-path
124+
'' + stdenv.lib.optionalString crossCompiling
125+
''
126+
mkdir -p $dev/lib/perl5/cross_perl/${version}
127+
for dir in cnf/{stub,cpan}; do
128+
cp -r $dir/* $dev/lib/perl5/cross_perl/${version}
129+
done
130+
131+
mkdir -p $dev/bin
132+
install -m755 miniperl $dev/bin/perl
133+
134+
export runtimeArch="$(ls $out/lib/perl5/site_perl/${version})"
135+
# wrapProgram should use a runtime-native SHELL by default, but
136+
# it actually uses a buildtime-native one. If we ever fix that,
137+
# we'll need to fix this to use a buildtime-native one.
138+
#
139+
# Adding the arch-specific directory is morally incorrect, as
140+
# miniperl can't load the native modules there. However, it can
141+
# (and sometimes needs to) load and run some of the pure perl
142+
# code there, so we add it anyway. When needed, stubs can be put
143+
# into $dev/lib/perl5/cross_perl/${version}.
144+
wrapProgram $dev/bin/perl --prefix PERL5LIB : \
145+
"$dev/lib/perl5/cross_perl/${version}:$out/lib/perl5/${version}:$out/lib/perl5/${version}/$runtimeArch"
120146
''; # */
121147

122148
meta = {
@@ -139,7 +165,7 @@ let
139165
sha256 = "1gh8w9m5if2s0lrx2x8f8grp74d1l6d46m8jglpjm5a1kf55j810";
140166
};
141167

142-
depsBuildBuild = [ buildPackages.stdenv.cc ];
168+
depsBuildBuild = [ buildPackages.stdenv.cc makeWrapper ];
143169

144170
postUnpack = ''
145171
unpackFile ${perl-cross-src}
@@ -150,6 +176,11 @@ let
150176
'';
151177

152178
configurePlatforms = [ "build" "host" "target" ];
179+
180+
inherit version;
181+
182+
# TODO merge setup hooks
183+
setupHook = ./setup-hook-cross.sh;
153184
});
154185
in rec {
155186
perl = perl524;
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
addPerlLibPath () {
2+
addToSearchPath PERL5LIB $1/lib/perl5/site_perl/@version@
3+
addToSearchPath PERL5LIB $1/lib/perl5/site_perl/cross_perl/@version@
4+
# Adding the arch-specific directory is morally incorrect, as
5+
# miniperl can't load the native modules there. However, it can
6+
# (and sometimes needs to) load and run some of the pure perl
7+
# code there, so we add it anyway. When needed, stubs can be put
8+
# into $1/lib/perl5/site_perl/cross_perl/@version@
9+
addToSearchPath PERL5LIB $1/lib/perl5/site_perl/@version@/@runtimeArch@
10+
}
11+
12+
addEnvHooks "$targetOffset" addPerlLibPath

pkgs/development/perl-modules/generic/builder.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ preConfigure() {
2222
fi
2323
done
2424

25-
perl Makefile.PL PREFIX=$out INSTALLDIRS=site $makeMakerFlags
25+
perl Makefile.PL PREFIX=$out INSTALLDIRS=site $makeMakerFlags PERL=$(type -P perl) FULLPERL=$perl/bin/perl
2626
}
2727

2828

pkgs/development/perl-modules/generic/default.nix

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
perl:
22

3-
{ buildInputs ? [], name, ... } @ attrs:
3+
{ nativeBuildInputs ? [], name, ... } @ attrs:
44

55
perl.stdenv.mkDerivation (
66
{
@@ -27,6 +27,7 @@ perl.stdenv.mkDerivation (
2727
{
2828
name = "perl-" + name;
2929
builder = ./builder.sh;
30-
buildInputs = buildInputs ++ [ perl ];
30+
nativeBuildInputs = nativeBuildInputs ++ [ (perl.dev or perl) ];
31+
inherit perl;
3132
}
3233
)

0 commit comments

Comments
 (0)