1e1051a39Sopenharmony_ci#!perl -T 2e1051a39Sopenharmony_ci# Tests for taint-mode features 3e1051a39Sopenharmony_ci 4e1051a39Sopenharmony_ciuse strict; 5e1051a39Sopenharmony_ciuse warnings; 6e1051a39Sopenharmony_ciuse lib 'blib/lib'; 7e1051a39Sopenharmony_ciuse Test::More tests => 21; 8e1051a39Sopenharmony_ciuse File::Temp; 9e1051a39Sopenharmony_ci 10e1051a39Sopenharmony_ciuse_ok 'Text::Template' or exit 1; 11e1051a39Sopenharmony_ci 12e1051a39Sopenharmony_ciif ($^O eq 'MSWin32') { 13e1051a39Sopenharmony_ci # File::Temp (for all versions up to at least 0.2308) is currently bugged under MSWin32/taint mode [as of 2018-09] 14e1051a39Sopenharmony_ci # ... fails unless "/tmp" on the current windows drive is a writable directory OR either $ENV{TMP} or $ENV{TEMP} are untainted and point to a writable directory 15e1051a39Sopenharmony_ci # ref: [File-Temp: Fails under -T, Windows 7, Strawberry Perl 5.12.1](https://rt.cpan.org/Public/Bug/Display.html?id=60340) 16e1051a39Sopenharmony_ci ($ENV{TEMP}) = $ENV{TEMP} =~ m/^.*$/gmsx; # untaint $ENV{TEMP} 17e1051a39Sopenharmony_ci ($ENV{TMP}) = $ENV{TMP} =~ m/^.*$/gmsx; # untaint $ENV{TMP} 18e1051a39Sopenharmony_ci} 19e1051a39Sopenharmony_ci 20e1051a39Sopenharmony_cimy $tmpfile = File::Temp->new; 21e1051a39Sopenharmony_cimy $file = $tmpfile->filename; 22e1051a39Sopenharmony_ci 23e1051a39Sopenharmony_ci# makes its arguments tainted 24e1051a39Sopenharmony_cisub taint { 25e1051a39Sopenharmony_ci for (@_) { 26e1051a39Sopenharmony_ci $_ .= substr($0, 0, 0); # LOD 27e1051a39Sopenharmony_ci } 28e1051a39Sopenharmony_ci} 29e1051a39Sopenharmony_ci 30e1051a39Sopenharmony_cimy $template = 'The value of $n is {$n}.'; 31e1051a39Sopenharmony_ci 32e1051a39Sopenharmony_ciopen my $fh, '>', $file or die "Couldn't write temporary file $file: $!"; 33e1051a39Sopenharmony_ciprint $fh $template, "\n"; 34e1051a39Sopenharmony_ciclose $fh or die "Couldn't finish temporary file $file: $!"; 35e1051a39Sopenharmony_ci 36e1051a39Sopenharmony_cisub should_fail { 37e1051a39Sopenharmony_ci my $obj = Text::Template->new(@_); 38e1051a39Sopenharmony_ci eval { $obj->fill_in() }; 39e1051a39Sopenharmony_ci if ($@) { 40e1051a39Sopenharmony_ci pass $@; 41e1051a39Sopenharmony_ci } 42e1051a39Sopenharmony_ci else { 43e1051a39Sopenharmony_ci fail q[didn't fail]; 44e1051a39Sopenharmony_ci } 45e1051a39Sopenharmony_ci} 46e1051a39Sopenharmony_ci 47e1051a39Sopenharmony_cisub should_work { 48e1051a39Sopenharmony_ci my $obj = Text::Template->new(@_); 49e1051a39Sopenharmony_ci eval { $obj->fill_in() }; 50e1051a39Sopenharmony_ci if ($@) { 51e1051a39Sopenharmony_ci fail $@; 52e1051a39Sopenharmony_ci } 53e1051a39Sopenharmony_ci else { 54e1051a39Sopenharmony_ci pass; 55e1051a39Sopenharmony_ci } 56e1051a39Sopenharmony_ci} 57e1051a39Sopenharmony_ci 58e1051a39Sopenharmony_cisub should_be_tainted { 59e1051a39Sopenharmony_ci ok !Text::Template::_is_clean($_[0]); 60e1051a39Sopenharmony_ci} 61e1051a39Sopenharmony_ci 62e1051a39Sopenharmony_cisub should_be_clean { 63e1051a39Sopenharmony_ci ok Text::Template::_is_clean($_[0]); 64e1051a39Sopenharmony_ci} 65e1051a39Sopenharmony_ci 66e1051a39Sopenharmony_ci# Tainted filename should die with and without UNTAINT option 67e1051a39Sopenharmony_ci# untainted filename should die without UNTAINT option 68e1051a39Sopenharmony_ci# filehandle should die without UNTAINT option 69e1051a39Sopenharmony_ci# string and array with tainted data should die either way 70e1051a39Sopenharmony_ci 71e1051a39Sopenharmony_ci# (2)-(7) 72e1051a39Sopenharmony_cimy $tfile = $file; 73e1051a39Sopenharmony_citaint($tfile); 74e1051a39Sopenharmony_cishould_be_tainted($tfile); 75e1051a39Sopenharmony_cishould_be_clean($file); 76e1051a39Sopenharmony_cishould_fail TYPE => 'file', SOURCE => $tfile; 77e1051a39Sopenharmony_cishould_fail TYPE => 'file', SOURCE => $tfile, UNTAINT => 1; 78e1051a39Sopenharmony_cishould_fail TYPE => 'file', SOURCE => $file; 79e1051a39Sopenharmony_cishould_work TYPE => 'file', SOURCE => $file, UNTAINT => 1; 80e1051a39Sopenharmony_ci 81e1051a39Sopenharmony_ci# (8-9) 82e1051a39Sopenharmony_ciopen $fh, '<', $file or die "Couldn't open $file for reading: $!; aborting"; 83e1051a39Sopenharmony_cishould_fail TYPE => 'filehandle', SOURCE => $fh; 84e1051a39Sopenharmony_ciclose $fh; 85e1051a39Sopenharmony_ci 86e1051a39Sopenharmony_ciopen $fh, '<', $file or die "Couldn't open $file for reading: $!; aborting"; 87e1051a39Sopenharmony_cishould_work TYPE => 'filehandle', SOURCE => $fh, UNTAINT => 1; 88e1051a39Sopenharmony_ciclose $fh; 89e1051a39Sopenharmony_ci 90e1051a39Sopenharmony_ci# (10-15) 91e1051a39Sopenharmony_cimy $ttemplate = $template; 92e1051a39Sopenharmony_citaint($ttemplate); 93e1051a39Sopenharmony_cishould_be_tainted($ttemplate); 94e1051a39Sopenharmony_cishould_be_clean($template); 95e1051a39Sopenharmony_cishould_fail TYPE => 'string', SOURCE => $ttemplate; 96e1051a39Sopenharmony_cishould_fail TYPE => 'string', SOURCE => $ttemplate, UNTAINT => 1; 97e1051a39Sopenharmony_cishould_work TYPE => 'string', SOURCE => $template; 98e1051a39Sopenharmony_cishould_work TYPE => 'string', SOURCE => $template, UNTAINT => 1; 99e1051a39Sopenharmony_ci 100e1051a39Sopenharmony_ci# (16-19) 101e1051a39Sopenharmony_cimy $array = [$template]; 102e1051a39Sopenharmony_cimy $tarray = [$ttemplate]; 103e1051a39Sopenharmony_cishould_fail TYPE => 'array', SOURCE => $tarray; 104e1051a39Sopenharmony_cishould_fail TYPE => 'array', SOURCE => $tarray, UNTAINT => 1; 105e1051a39Sopenharmony_cishould_work TYPE => 'array', SOURCE => $array; 106e1051a39Sopenharmony_cishould_work TYPE => 'array', SOURCE => $array, UNTAINT => 1; 107e1051a39Sopenharmony_ci 108e1051a39Sopenharmony_ci# (20-21) Test _unconditionally_untaint utility function 109e1051a39Sopenharmony_ciText::Template::_unconditionally_untaint($ttemplate); 110e1051a39Sopenharmony_cishould_be_clean($ttemplate); 111e1051a39Sopenharmony_ciText::Template::_unconditionally_untaint($tfile); 112e1051a39Sopenharmony_cishould_be_clean($tfile); 113