Subject: | Executables build by pp fail with "Error in tempfile()..." |
PAR: 0.69 (built from sources)
Perl: v5.8.0 built for i386-linux-thread-multi
OS: Linux 2.4.21 (Debian sid)
Build an executable from foo.pl which consists of two lines:
use XML::XPath;
print "hello world\n";
$ pp -o foo foo.pl
$ ./foo
Error in tempfile() using /tmp/par_priv.759.tmp/XXXXXXXXXX.so: Parent directory (/tmp/par_priv.759.tmp/) is not a directory at /usr/share/perl5/PAR/Heavy.pm line 79
The problem is that the temp directory /tmp/par_priv.759.tmp for
the unpacked shared libraries hasn't been created. I tracked this
down to the following:
myldr/main.c starts with (line 73)
char *stmpdir = par_mktmpdir( argv );
The first time around, par_mktmpdir generates the name for the
temp directory, e.g. /tmp/par_priv.759.tmp, and puts into
the environment variable PAR_TEMP. It also prepends this
directory to LD_LIBRARY_PATH, then exec's itself with argv unchanged
(so that the new LD_LIBRARY_PATH takes effect). So again
char *stmpdir = par_mktmpdir( argv );
This time par_mktmpdir finds PAR_TEMP already in the environment
(using getenv) and just returns its value. I checked stmpdir
at this point, it's as expected.
Later on (starting with line 169) myldr/main.c uses stmpdir
in
i = PerlDir_mkdir(stmpdir, 0755);
This fails, because stmpdir suddenly points to an empty string!
I preceded the line with
stmpdir = getenv("PAR_TEMP");
and then stmpdir has the correct value. I checked the pointer
itself returned on line 63 and by the latter getenv() and they
are different. Apparently the environment gets relocated
between line 63 and 169 (and the old copy gets zeroed out).
So my temporary fix is:
--- PAR-0.69/myldr/main.c 2003-05-31 14:27:59.000000000 +0200
+++ libpar-perl-0.69-hacked/myldr/main.c 2003-06-15 17:54:32.000000000 +0
200
@@ -70,7 +70,8 @@
char *subsubdir;
#ifdef PAR_MKTMPDIR
- char *stmpdir = par_mktmpdir( argv );
+ char *stmpdir;
+ par_mktmpdir( argv );
#endif
#if (defined(USE_5005THREADS) || defined(USE_ITHREADS)) && defined(HAS_PTHREAD_
ATFORK)
@@ -166,6 +167,7 @@
#ifdef PAR_MKTMPDIR
/* create temporary PAR directory */
+ stmpdir = getenv("PAR_TEMP");
if ( stmpdir != NULL ) {
i = PerlDir_mkdir(stmpdir, 0755);
if ( (i != 0) && (i != EEXIST) && (i != -1) ) {
BTW, the problem would have been detected earlier, because
PerlDir_mkdir fails for stmpdir = "", but
returns i = -1 so that the following error message
"creation of private temporary subdirectory %s failed - aborting with %i."
doesn't get triggered.
Cheeers, Roderich