diff options
author | Father Chrysostomos <sprout@cpan.org> | 2013-06-08 23:01:07 -0700 |
---|---|---|
committer | Father Chrysostomos <sprout@cpan.org> | 2013-06-08 23:25:13 -0700 |
commit | 82730d4c29900a581a5c4f6cd8c0cdef16c6e687 (patch) | |
tree | 99e30b878e7256fa5942d595f176d15b9665af38 | |
parent | 483ad8291bb83bb55f59f0ff324af70346c4945a (diff) | |
download | perl-82730d4c29900a581a5c4f6cd8c0cdef16c6e687.tar.gz |
[perl #89940] File::Spec->tmpdir and env changes
If the environment changes, File::Spec->tmpdir should respect that and
recalculate the temp directory.
The only objection raised in the ticket was that File::Spec is already
accused of being too slow, so removing the cache would not be a good
idea. So I put in a check to see whether the relevant environment
variables have changed since the last call to tmpdir.
-rw-r--r-- | dist/Cwd/lib/File/Spec/Cygwin.pm | 11 | ||||
-rw-r--r-- | dist/Cwd/lib/File/Spec/Mac.pm | 6 | ||||
-rw-r--r-- | dist/Cwd/lib/File/Spec/OS2.pm | 8 | ||||
-rw-r--r-- | dist/Cwd/lib/File/Spec/Unix.pm | 22 | ||||
-rw-r--r-- | dist/Cwd/lib/File/Spec/VMS.pm | 9 | ||||
-rw-r--r-- | dist/Cwd/lib/File/Spec/Win32.pm | 3 | ||||
-rw-r--r-- | dist/Cwd/t/tmpdir.t | 19 |
7 files changed, 59 insertions, 19 deletions
diff --git a/dist/Cwd/lib/File/Spec/Cygwin.pm b/dist/Cwd/lib/File/Spec/Cygwin.pm index b27f7b15f1..4eb0347cc4 100644 --- a/dist/Cwd/lib/File/Spec/Cygwin.pm +++ b/dist/Cwd/lib/File/Spec/Cygwin.pm @@ -97,10 +97,15 @@ variables are tainted, they are not used. =cut -my $tmpdir; sub tmpdir { - return $tmpdir if defined $tmpdir; - $tmpdir = $_[0]->_tmpdir( $ENV{TMPDIR}, "/tmp", $ENV{'TMP'}, $ENV{'TEMP'}, 'C:/temp' ); + my $cached = $_[0]->_cached_tmpdir(qw 'TMPDIR TMP TEMP'); + return $cached if defined $cached; + $_[0]->_cache_tmpdir( + $_[0]->_tmpdir( + $ENV{TMPDIR}, "/tmp", $ENV{'TMP'}, $ENV{'TEMP'}, 'C:/temp' + ), + qw 'TMPDIR TMP TEMP' + ); } =item case_tolerant diff --git a/dist/Cwd/lib/File/Spec/Mac.pm b/dist/Cwd/lib/File/Spec/Mac.pm index 7f42171bc9..aa6a7bf19c 100644 --- a/dist/Cwd/lib/File/Spec/Mac.pm +++ b/dist/Cwd/lib/File/Spec/Mac.pm @@ -374,10 +374,10 @@ directory on your startup volume. =cut -my $tmpdir; sub tmpdir { - return $tmpdir if defined $tmpdir; - $tmpdir = $_[0]->_tmpdir( $ENV{TMPDIR} ); + my $cached = $_[0]->_cached_tmpdir('TMPDIR'); + return $cached if defined $cached; + $_[0]->_cache_tmpdir($_[0]->_tmpdir( $ENV{TMPDIR} ), 'TMPDIR'); } =item updir diff --git a/dist/Cwd/lib/File/Spec/OS2.pm b/dist/Cwd/lib/File/Spec/OS2.pm index 7f60d68927..f9c6d44453 100644 --- a/dist/Cwd/lib/File/Spec/OS2.pm +++ b/dist/Cwd/lib/File/Spec/OS2.pm @@ -35,11 +35,13 @@ sub _cwd { return Cwd::sys_cwd(); } -my $tmpdir; sub tmpdir { - return $tmpdir if defined $tmpdir; + my $cached = $_[0]->_cached_tmpdir(qw 'TMPDIR TEMP TMP'); + return $cached if defined $cached; my @d = @ENV{qw(TMPDIR TEMP TMP)}; # function call could autovivivy - $tmpdir = $_[0]->_tmpdir( @d, '/tmp', '/' ); + $_[0]->_cache_tmpdir( + $_[0]->_tmpdir( @d, '/tmp', '/' ), qw 'TMPDIR TEMP TMP' + ); } sub catdir { diff --git a/dist/Cwd/lib/File/Spec/Unix.pm b/dist/Cwd/lib/File/Spec/Unix.pm index a1a91b4260..0eb68b9444 100644 --- a/dist/Cwd/lib/File/Spec/Unix.pm +++ b/dist/Cwd/lib/File/Spec/Unix.pm @@ -140,9 +140,22 @@ is tainted, it is not used. =cut -my $tmpdir; +my ($tmpdir, %tmpenv); +# Cache and return the calculated tmpdir, recording which env vars +# determined it. +sub _cache_tmpdir { + @tmpenv{@_[2..$#_]} = @ENV{@_[2..$#_]}; + return $tmpdir = $_[1]; +} +# Retrieve the cached tmpdir, checking first whether relevant env vars have +# changed and invalidated the cache. +sub _cached_tmpdir { + shift; + local $^W; + return if grep $ENV{$_} ne $tmpenv{$_}, @_; + return $tmpdir; +} sub _tmpdir { - return $tmpdir if defined $tmpdir; my $self = shift; my @dirlist = @_; { @@ -166,8 +179,9 @@ sub _tmpdir { } sub tmpdir { - return $tmpdir if defined $tmpdir; - $tmpdir = $_[0]->_tmpdir( $ENV{TMPDIR}, "/tmp" ); + my $cached = $_[0]->_cached_tmpdir('TMPDIR'); + return $cached if defined $cached; + $_[0]->_cache_tmpdir($_[0]->_tmpdir( $ENV{TMPDIR}, "/tmp" ), 'TMPDIR'); } =item updir diff --git a/dist/Cwd/lib/File/Spec/VMS.pm b/dist/Cwd/lib/File/Spec/VMS.pm index ce0dab763e..16f4789c68 100644 --- a/dist/Cwd/lib/File/Spec/VMS.pm +++ b/dist/Cwd/lib/File/Spec/VMS.pm @@ -276,16 +276,17 @@ is tainted, it is not used. =cut -my $tmpdir; sub tmpdir { my $self = shift @_; + my $tmpdir = $self->_cached_tmpdir('TMPDIR'); return $tmpdir if defined $tmpdir; if ($self->_unix_rpt) { $tmpdir = $self->_tmpdir('/tmp', '/sys$scratch', $ENV{TMPDIR}); - return $tmpdir; } - - $tmpdir = $self->_tmpdir( 'sys$scratch:', $ENV{TMPDIR} ); + else { + $tmpdir = $self->_tmpdir( 'sys$scratch:', $ENV{TMPDIR} ); + } + $self->_cache_tmpdir($tmpdir, 'TMPDIR'); } =item updir (override) diff --git a/dist/Cwd/lib/File/Spec/Win32.pm b/dist/Cwd/lib/File/Spec/Win32.pm index ae74a26593..b606011bce 100644 --- a/dist/Cwd/lib/File/Spec/Win32.pm +++ b/dist/Cwd/lib/File/Spec/Win32.pm @@ -67,8 +67,8 @@ variables are tainted, they are not used. =cut -my $tmpdir; sub tmpdir { + my $tmpdir = $_[0]->_cached_tmpdir(qw(TMPDIR TEMP TMP)); return $tmpdir if defined $tmpdir; $tmpdir = $_[0]->_tmpdir( map( $ENV{$_}, qw(TMPDIR TEMP TMP) ), 'SYS:/temp', @@ -76,6 +76,7 @@ sub tmpdir { 'C:/temp', '/tmp', '/' ); + $_[0]->_cache_tmpdir($tmpdir, qw(TMPDIR TEMP TMP)); } =item case_tolerant diff --git a/dist/Cwd/t/tmpdir.t b/dist/Cwd/t/tmpdir.t index 6f7f318180..7c13da1fe3 100644 --- a/dist/Cwd/t/tmpdir.t +++ b/dist/Cwd/t/tmpdir.t @@ -1,5 +1,5 @@ use strict; -use Test::More tests => 5; +use Test::More tests => 7; # Grab all of the plain routines from File::Spec use File::Spec; @@ -29,3 +29,20 @@ SKIP: { File::Spec::Win32->tmpdir; is(scalar keys %ENV, $num_keys, "Win32->tmpdir() shouldn't change the contents of %ENV"); + +# Changing tmpdir dynamically +for ('File::Spec', "File::Spec::Win32") { + SKIP: { + skip('sys$scratch: takes precedence over env on vms', 1) + if $^O eq 'VMS'; + local $ENV{TMPDIR} = $_->catfile($_->curdir, 'lib'); + -d $ENV{TMPDIR} && -w _ + or skip "Can't create usable TMPDIR env var", 1; + my $tmpdir1 = $_->tmpdir; + $ENV{TMPDIR} = $_->catfile($_->curdir, 't'); + -d $ENV{TMPDIR} && -w _ + or skip "Can't create usable TMPDIR env var", 1; + my $tmpdir2 = $_->tmpdir; + isn't $tmpdir2, $tmpdir1, "$_->tmpdir works with changing env"; + } +} |