Bug#622817: perl: CVE-2011-1487: taint laundering in lc, uc

Niko Tyni ntyni at debian.org
Sat Apr 16 07:20:00 UTC 2011


On Fri, Apr 15, 2011 at 11:41:02PM +0300, Niko Tyni wrote:
> On Thu, Apr 14, 2011 at 09:45:55PM +0100, Dominic Hargreaves wrote:
> > Package: perl
> > Version: 5.10.1-19
> > Severity: grave
> > Tags: security
> > Justification: user security hole
> > 
> > CVE description:
> > 
> > The (1) lc, (2) lcfirst, (3) uc, and (4) ucfirst functions in Perl
> > 5.10.x, 5.11.x, and 5.12.x through 5.12.3, and 5.13.x through 5.13.11,
> > do not apply the taint attribute to the return value upon processing
> > tainted input, which might allow context-dependent attackers to bypass
> > the taint protection mechanism via a crafted string. 

> Security team, I assume this is going to be fixed through a DSA?

> It should be trivial to port this to squeeze and lenny. I'll try to
> prepare the debdiffs on Sunday, but if somebody else wants to do that,
> feel free.

I'm attaching the proposed debdiffs. I've verified that they fix
the issue and pass the test suite.

 perl -Te 'use Scalar::Util qw(tainted); $t=$0; $u=lc lcfirst uc ucfirst $t; printf("%d,%d\n",tainted($t),tainted($u))'

gives 1,0 without the fix and 1,1 with the fix.

> Please note that the sid fix can't currently be uploaded on its own
> because of a db4.7 related problem (just filed as #622916).

I'm waiting to see how this turns out. Not sure if we should wait
with the stable and oldstable updates until the fix is in unstable.
Not much risk for regressions AFAICS.

Security team, please let me know if I can upload these or if they
should go via spu instead
-- 
Niko Tyni   ntyni at debian.org
-------------- next part --------------
diff -u perl-5.10.0/patches-applied perl-5.10.0/patches-applied
--- perl-5.10.0/patches-applied
+++ perl-5.10.0/patches-applied
@@ -42,6 +42,7 @@
 debian/patches/41_map_memleak.diff
 debian/patches/42_cgi_cve_2010_4411
 debian/patches/43_safe_update_cve_2010_1168
+debian/patches/44_casing_taint_cve_2011_1487
 debian/patches/50_debian_use_gdbm
 debian/patches/51_debian_ld_run_path
 debian/patches/52_debian_extutils_hacks
diff -u perl-5.10.0/debian/changelog perl-5.10.0/debian/changelog
--- perl-5.10.0/debian/changelog
+++ perl-5.10.0/debian/changelog
@@ -1,3 +1,10 @@
+perl (5.10.0-19lenny4) oldstable-security; urgency=low
+
+  * [SECURITY] CVE-2011-1487: taint laundering in lc, uc, et al.
+    (Closes: #622817)
+
+ -- Niko Tyni <ntyni at debian.org>  Sat, 16 Apr 2011 09:05:09 +0300
+
 perl (5.10.0-19lenny3) stable; urgency=low
 
   * [SECURITY] CVE-2010-2761 CVE-2010-4410 CVE-2010-4411:
only in patch2:
unchanged:
--- perl-5.10.0.orig/pp.c
+++ perl-5.10.0/pp.c
@@ -3610,6 +3610,8 @@
 	    SvCUR_set(dest, need - 1);
 	}
     }
+    if (dest != source && SvTAINTED(source))
+        SvTAINT(dest);
     SvSETMAGIC(dest);
     RETURN;
 }
@@ -3660,7 +3662,8 @@
 	SvUPGRADE(dest, SVt_PV);
 	d = (U8*)SvGROW(dest, min);
 	(void)SvPOK_only(dest);
-
+	if (dest != source && SvTAINTED(source))
+	    SvTAINT(dest);
 	SETs(dest);
     }
 
@@ -3829,6 +3832,8 @@
 	    SvCUR_set(dest, d - (U8*)SvPVX_const(dest));
 	}
     }
+    if (dest != source && SvTAINTED(source))
+        SvTAINT(dest);
     SvSETMAGIC(dest);
     RETURN;
 }
only in patch2:
unchanged:
--- perl-5.10.0.orig/debian/patches/44_casing_taint_cve_2011_1487
+++ perl-5.10.0/debian/patches/44_casing_taint_cve_2011_1487
@@ -0,0 +1,81 @@
+From: Niko Tyni <ntyni at debian.org>
+Bug-Debian: http://bugs.debian.org/622817
+Bug: http://rt.perl.org/rt3/Public/Bug/Display.html?id=87336
+Origin: upstream, http://perl5.git.perl.org/perl.git/commitdiff/539689e74a3bcb04d29e4cd9396de91a81045b99
+Subject: fix unwanted taint laundering in lc(), uc() et al.
+
+Upstream patch ported to 5.12 by Marcela Ma?l??ov? <mmaslano at redhat.com>
+
+Tests modified by Niko Tyni <ntyni at debian.org> to actually fail without
+the patch.
+
+
+---
+ pp.c         |    7 ++++++-
+ t/op/taint.t |   15 ++++++++++++++-
+ 2 files changed, 20 insertions(+), 2 deletions(-)
+
+index 6d69589..b2c4f21 100644
+--- a/pp.c
++++ b/pp.c
+@@ -3610,6 +3610,8 @@ PP(pp_ucfirst)
+ 	    SvCUR_set(dest, need - 1);
+ 	}
+     }
++    if (dest != source && SvTAINTED(source))
++        SvTAINT(dest);
+     SvSETMAGIC(dest);
+     RETURN;
+ }
+@@ -3660,7 +3662,8 @@ PP(pp_uc)
+ 	SvUPGRADE(dest, SVt_PV);
+ 	d = (U8*)SvGROW(dest, min);
+ 	(void)SvPOK_only(dest);
+-
++	if (dest != source && SvTAINTED(source))
++	    SvTAINT(dest);
+ 	SETs(dest);
+     }
+ 
+@@ -3829,6 +3832,8 @@ PP(pp_lc)
+ 	    SvCUR_set(dest, d - (U8*)SvPVX_const(dest));
+ 	}
+     }
++    if (dest != source && SvTAINTED(source))
++        SvTAINT(dest);
+     SvSETMAGIC(dest);
+     RETURN;
+ }
+diff --git a/t/op/taint.t b/t/op/taint.t
+index b2688cf..dceadfe 100755
+--- a/t/op/taint.t
++++ b/t/op/taint.t
+@@ -17,7 +17,7 @@ use Config;
+ use File::Spec::Functions;
+ 
+ BEGIN { require './test.pl'; }
+-plan tests => 267;
++plan tests => 271;
+ 
+ $| = 1;
+ 
+@@ -1254,6 +1254,19 @@ foreach my $ord (78, 163, 256) {
+     ok(!tainted($1), "\\S match with chr $ord");
+ }
+ 
++{
++    # [perl #87336] lc/uc(first) failing to taint the returned string
++    my $source = "foo$TAINT";
++    my $dest = lc $source;
++    test tainted $dest, "lc(tainted) taints its return value";
++    $dest = lcfirst $source;
++    test tainted $dest, "lcfirst(tainted) taints its return value";
++    $dest = uc $source;
++    test tainted $dest, "uc(tainted) taints its return value";
++    $dest = ucfirst $source;
++    test tainted $dest, "ucfirst(tainted) taints its return value";
++}
++
+ # This may bomb out with the alarm signal so keep it last
+ SKIP: {
+     skip "No alarm()"  unless $Config{d_alarm};
only in patch2:
unchanged:
--- perl-5.10.0.orig/t/op/taint.t
+++ perl-5.10.0/t/op/taint.t
@@ -17,7 +17,7 @@
 use File::Spec::Functions;
 
 BEGIN { require './test.pl'; }
-plan tests => 267;
+plan tests => 271;
 
 $| = 1;
 
@@ -1254,6 +1254,19 @@
     ok(!tainted($1), "\\S match with chr $ord");
 }
 
+{
+    # [perl #87336] lc/uc(first) failing to taint the returned string
+    my $source = "foo$TAINT";
+    my $dest = lc $source;
+    test tainted $dest, "lc(tainted) taints its return value";
+    $dest = lcfirst $source;
+    test tainted $dest, "lcfirst(tainted) taints its return value";
+    $dest = uc $source;
+    test tainted $dest, "uc(tainted) taints its return value";
+    $dest = ucfirst $source;
+    test tainted $dest, "ucfirst(tainted) taints its return value";
+}
+
 # This may bomb out with the alarm signal so keep it last
 SKIP: {
     skip "No alarm()"  unless $Config{d_alarm};
-------------- next part --------------
diff -Nru perl-5.10.1/debian/changelog perl-5.10.1/debian/changelog
--- perl-5.10.1/debian/changelog	2011-01-07 13:57:45.000000000 +0200
+++ perl-5.10.1/debian/changelog	2011-04-16 09:02:11.000000000 +0300
@@ -1,3 +1,10 @@
+perl (5.10.1-17squeeze1) stable-security; urgency=low
+
+  * [SECURITY] CVE-2011-1487: taint laundering in lc, uc, et al.
+    (Closes: #622817)
+
+ -- Niko Tyni <ntyni at debian.org>  Sat, 16 Apr 2011 09:02:05 +0300
+
 perl (5.10.1-17) unstable; urgency=medium
 
   * [SECURITY] CVE-2010-2761 CVE-2010-4410 CVE-2010-4411:
diff -Nru perl-5.10.1/debian/control perl-5.10.1/debian/control
--- perl-5.10.1/debian/control	2011-01-07 09:33:52.000000000 +0200
+++ perl-5.10.1/debian/control	2011-04-16 09:00:59.000000000 +0300
@@ -2,13 +2,13 @@
 Section: perl
 Priority: standard
 Maintainer: Niko Tyni <ntyni at debian.org>
-Uploaders: Eugene V. Lyubimkin <jackyf at debian.org>
+Uploaders: Dominic Hargreaves <dom at earth.li>
 Standards-Version: 3.8.4
 Build-Depends: file, cpio (>= 2.6-5), libdb4.7-dev, libgdbm-dev, netbase [!hurd-i386],
  gcc (>= 4:4.2), procps | hurd, zlib1g-dev | libz-dev, libbz2-dev
 Build-Conflicts: libterm-readline-gnu-perl (<< 1.17)
-Vcs-Git: git://git.debian.org/git/perl/perl.git
-Vcs-Browser: http://git.debian.org/?p=perl/perl.git
+Vcs-Git: git://git.debian.org/git/perl/perl-squeeze.git
+Vcs-Browser: http://git.debian.org/?p=perl/perl-squeeze.git
 
 Package: perl-base
 Essential: yes
diff -Nru perl-5.10.1/debian/patches/fixes/assorted_docs.diff perl-5.10.1/debian/patches/fixes/assorted_docs.diff
--- perl-5.10.1/debian/patches/fixes/assorted_docs.diff	2011-01-07 13:58:01.000000000 +0200
+++ perl-5.10.1/debian/patches/fixes/assorted_docs.diff	2011-04-16 09:02:30.000000000 +0300
@@ -9,7 +9,7 @@
  1 files changed, 1 insertions(+), 1 deletions(-)
 
 diff --git a/lib/Math/BigInt/CalcEmu.pm b/lib/Math/BigInt/CalcEmu.pm
-index 79efac6..5810f5db 100644
+index 79efac6..5810f5d 100644
 --- a/lib/Math/BigInt/CalcEmu.pm
 +++ b/lib/Math/BigInt/CalcEmu.pm
 @@ -295,7 +295,7 @@ Math::BigInt::CalcEmu - Emulate low-level math with BigInt code
diff -Nru perl-5.10.1/debian/patches/fixes/casing-taint-cve-2011-1487.diff perl-5.10.1/debian/patches/fixes/casing-taint-cve-2011-1487.diff
--- perl-5.10.1/debian/patches/fixes/casing-taint-cve-2011-1487.diff	1970-01-01 02:00:00.000000000 +0200
+++ perl-5.10.1/debian/patches/fixes/casing-taint-cve-2011-1487.diff	2011-04-16 09:02:34.000000000 +0300
@@ -0,0 +1,84 @@
+From: Niko Tyni <ntyni at debian.org>
+Bug-Debian: http://bugs.debian.org/622817
+Bug: http://rt.perl.org/rt3/Public/Bug/Display.html?id=87336
+Origin: upstream, http://perl5.git.perl.org/perl.git/commitdiff/539689e74a3bcb04d29e4cd9396de91a81045b99
+Subject: fix unwanted taint laundering in lc(), uc() et al.
+
+Upstream patch ported to 5.12 by Marcela Ma?l??ov? <mmaslano at redhat.com>
+
+Tests modified by Niko Tyni <ntyni at debian.org> to actually fail without
+the patch.
+
+
+---
+ pp.c         |    7 ++++++-
+ t/op/taint.t |   15 ++++++++++++++-
+ 2 files changed, 20 insertions(+), 2 deletions(-)
+
+diff --git a/pp.c b/pp.c
+index 1c8620c..40e512a 100644
+--- a/pp.c
++++ b/pp.c
+@@ -3616,6 +3616,8 @@ PP(pp_ucfirst)
+ 	    SvCUR_set(dest, need - 1);
+ 	}
+     }
++    if (dest != source && SvTAINTED(source))
++        SvTAINT(dest);
+     SvSETMAGIC(dest);
+     RETURN;
+ }
+@@ -3666,7 +3668,8 @@ PP(pp_uc)
+ 	SvUPGRADE(dest, SVt_PV);
+ 	d = (U8*)SvGROW(dest, min);
+ 	(void)SvPOK_only(dest);
+-
++	if (dest != source && SvTAINTED(source))
++	    SvTAINT(dest);
+ 	SETs(dest);
+     }
+ 
+@@ -3835,6 +3838,8 @@ PP(pp_lc)
+ 	    SvCUR_set(dest, d - (U8*)SvPVX_const(dest));
+ 	}
+     }
++    if (dest != source && SvTAINTED(source))
++        SvTAINT(dest);
+     SvSETMAGIC(dest);
+     RETURN;
+ }
+diff --git a/t/op/taint.t b/t/op/taint.t
+index 6511fa5..80ac57b 100755
+--- a/t/op/taint.t
++++ b/t/op/taint.t
+@@ -17,7 +17,7 @@ use Config;
+ use File::Spec::Functions;
+ 
+ BEGIN { require './test.pl'; }
+-plan tests => 302;
++plan tests => 306;
+ 
+ $| = 1;
+ 
+@@ -1327,6 +1327,19 @@ foreach my $ord (78, 163, 256) {
+ }
+ 
+ 
++{
++    # [perl #87336] lc/uc(first) failing to taint the returned string
++    my $source = "foo$TAINT";
++    my $dest = lc $source;
++    test tainted $dest, "lc(tainted) taints its return value";
++    $dest = lcfirst $source;
++    test tainted $dest, "lcfirst(tainted) taints its return value";
++    $dest = uc $source;
++    test tainted $dest, "uc(tainted) taints its return value";
++    $dest = ucfirst $source;
++    test tainted $dest, "ucfirst(tainted) taints its return value";
++}
++
+ # This may bomb out with the alarm signal so keep it last
+ SKIP: {
+     skip "No alarm()"  unless $Config{d_alarm};
+-- 
+tg: (3801a1e..) fixes/casing-taint-cve-2011-1487 (depends on: upstream)
diff -Nru perl-5.10.1/debian/patches/patchlevel perl-5.10.1/debian/patches/patchlevel
--- perl-5.10.1/debian/patches/patchlevel	2011-01-07 13:58:05.000000000 +0200
+++ perl-5.10.1/debian/patches/patchlevel	2011-04-16 09:02:34.000000000 +0300
@@ -1,4 +1,4 @@
-Subject: List packaged patches for 5.10.1-17 in patchlevel.h
+Subject: List packaged patches for 5.10.1-17squeeze1 in patchlevel.h
 Origin: vendor
 Bug-Debian: http://bugs.debian.org/567489
 
@@ -8,7 +8,7 @@
 
 --- perl/patchlevel.bak
 +++ perl/patchlevel.h
-@@ -133,0 +134,51 @@
+@@ -133,0 +134,52 @@
 +	,"DEBPKG:debian/arm_thread_stress_timeout - http://bugs.debian.org/501970 Raise the timeout of ext/threads/shared/t/stress.t to accommodate slower build hosts"
 +	,"DEBPKG:debian/cpan_config_path - Set location of CPAN::Config to /etc/perl as /usr may not be writable."
 +	,"DEBPKG:debian/cpan_definstalldirs - Provide a sensible INSTALLDIRS default for modules installed from CPAN."
@@ -59,4 +59,5 @@
 +	,"DEBPKG:fixes/lc-numeric-sprintf - http://bugs.debian.org/601549 [perl #78632] [b3fd614] Fix sprintf not to ignore LC_NUMERIC with constants"
 +	,"DEBPKG:fixes/concat-stack-corruption - http://bugs.debian.org/596105 [perl #78674] [e3393f5] Fix stack pointer corruption in pp_concat() with 'use encoding'"
 +	,"DEBPKG:fixes/cgi-multiline-header - http://bugs.debian.org/606995 [CVE-2010-2761 CVE-2010-4410 CVE-2010-4411] CGI.pm MIME boundary and multiline header vulnerabilities"
-+	,"DEBPKG:patchlevel - http://bugs.debian.org/567489 List packaged patches for 5.10.1-17 in patchlevel.h"
++	,"DEBPKG:fixes/casing-taint-cve-2011-1487 - http://bugs.debian.org/622817 [perl #87336] fix unwanted taint laundering in lc(), uc() et al."
++	,"DEBPKG:patchlevel - http://bugs.debian.org/567489 List packaged patches for 5.10.1-17squeeze1 in patchlevel.h"
diff -Nru perl-5.10.1/debian/patches/series perl-5.10.1/debian/patches/series
--- perl-5.10.1/debian/patches/series	2011-01-07 13:58:05.000000000 +0200
+++ perl-5.10.1/debian/patches/series	2011-04-16 09:02:34.000000000 +0300
@@ -48,4 +48,5 @@
 fixes/lc-numeric-sprintf.diff -p1
 fixes/concat-stack-corruption.diff -p1
 fixes/cgi-multiline-header.diff -p1
+fixes/casing-taint-cve-2011-1487.diff -p1
 patchlevel -p1


More information about the Perl-maintainers mailing list