diff options
author | Father Chrysostomos <sprout@cpan.org> | 2016-09-03 13:30:22 -0700 |
---|---|---|
committer | Father Chrysostomos <sprout@cpan.org> | 2016-09-03 18:51:41 -0700 |
commit | ba0a4150f6f1604df236035adf6df18bd43de88e (patch) | |
tree | 04c01c3acb428079b256a36f99efb832403e68d7 /util.c | |
parent | fac2c98c83b1d3b5039146aa7b14e3ed41f65cc4 (diff) | |
download | perl-ba0a4150f6f1604df236035adf6df18bd43de88e.tar.gz |
Fix checks for tainted dir in $ENV{PATH}
$ cat > foo
#!/usr/bin/perl
print "What?!\n"
^D
$ chmod +x foo
$ ./perl -Ilib -Te '$ENV{PATH}="."; exec "foo"'
Insecure directory in $ENV{PATH} while running with -T switch at -e line 1.
That is what I expect to see. But:
$ ./perl -Ilib -Te '$ENV{PATH}="/\\:."; exec "foo"'
What?!
Perl is allowing the \ to escape the :, but the \ is not treated as an
escape by the system, allowing a relative path in PATH to be consid-
ered safe.
Diffstat (limited to 'util.c')
-rw-r--r-- | util.c | 25 |
1 files changed, 22 insertions, 3 deletions
@@ -524,15 +524,17 @@ Free_t Perl_mfree (Malloc_t where) /* copy a string up to some (non-backslashed) delimiter, if any */ -char * -Perl_delimcpy(char *to, const char *toend, const char *from, const char *fromend, int delim, I32 *retlen) +static char * +S_delimcpy(char *to, const char *toend, const char *from, + const char *fromend, int delim, I32 *retlen, + const bool allow_escape) { I32 tolen; PERL_ARGS_ASSERT_DELIMCPY; for (tolen = 0; from < fromend; from++, tolen++) { - if (*from == '\\') { + if (allow_escape && *from == '\\') { if (from[1] != delim) { if (to < toend) *to++ = *from; @@ -551,6 +553,23 @@ Perl_delimcpy(char *to, const char *toend, const char *from, const char *fromend return (char *)from; } +char * +Perl_delimcpy(char *to, const char *toend, const char *from, const char *fromend, int delim, I32 *retlen) +{ + PERL_ARGS_ASSERT_DELIMCPY; + + return S_delimcpy(to, toend, from, fromend, delim, retlen, 1); +} + +char * +Perl_delimcpy_no_escape(char *to, const char *toend, const char *from, + const char *fromend, int delim, I32 *retlen) +{ + PERL_ARGS_ASSERT_DELIMCPY_NO_ESCAPE; + + return S_delimcpy(to, toend, from, fromend, delim, retlen, 0); +} + /* =head1 Miscellaneous Functions |