CC: | jkeenan [...] cpan.org |
Subject: | [RT #38387] Net::Cmd does not handle CR and LF correctly |
The bug report below was originally submitted to the Perl 5 bug tracker in January 2006. It never received a response. libnet is included in the Perl 5 core distribution, but until Aug 12 2013 the place to which bugs were to be reported was undefined. Since Perl 5's Porting/Maintainers.pl now lists "UPSTREAM => 'cpan'", I am transferring this bug report to this queue on rt.cpan.org. --jkeenan
This is a bug report for perl from alexander_bluhm@genua.de,
generated with the help of perlbug 1.35 running under perl v5.8.6.
-----------------------------------------------------------------
[Please enter your report here]
Hi,
The escaping of CR and LF in Net::Cmd->dataend is somewhat broken.
A sequence "a\r" is escaped as "a\015\015\012.\015\012".
There is even a test for this behavior. But it does not conform
to RFC 2821 Section 2.3.7:
In addition, the appearance of "bare" "CR" or "LF" characters in text
(i.e., either without the other) has a long history of causing
problems in mail implementations and applications that use the mail
system as a tool. SMTP client implementations MUST NOT transmit
these characters except when they are intended as line terminators
and then MUST, as indicated above, transmit them only as a <CRLF>
sequence.
So sending the sequence "\015\015" is illegal because the first
"\015" is not followed by a "\012".
I have made a patch for that bug. I have also added a lot of other
test cases to the t/datasend.t test. I wrote these tests, after
we had encountered real world SMTP problems with different versions
of Net::Cmd.
I am using Net::Cmd Version 2.26 from the libnet-1.19 package in
the Perl 5.8.6 core.
Alexander
--- ./Net/Cmd.pm.orig Wed Jun 30 15:56:11 2004
+++ ./Net/Cmd.pm Tue Jan 31 21:52:14 2006
@@ -512,6 +512,9 @@
if (!defined $ch) {
return 1;
}
+ elsif ($ch eq "\015") {
+ $tosend = "\012";
+ }
elsif ($ch ne "\012") {
$tosend = "\015\012";
}
--- ./t/datasend.t.orig Wed Jun 30 15:56:10 2004
+++ ./t/datasend.t Tue Jan 31 22:56:21 2006
@@ -30,7 +33,7 @@
(my $libnet_t = __FILE__) =~ s/datasend.t/libnet_t.pl/;
require $libnet_t or die;
-print "1..51\n";
+print "1..212\n";
sub check {
my $expect = pop;
@@ -46,8 +49,6 @@
);
}
-my $cmd;
-
check(
# nothing
@@ -63,7 +64,7 @@
check(
"a\r",
- "a\015\015\012.\015\012",
+ "a\015\012.\015\012",
);
check(
@@ -144,3 +145,67 @@
"a\015\012..\015\012.\015\012",
);
+# Send data with \r\n on block break.
+my @rn = (
+ [ "single line" ],
+ [ "two\nlines" ],
+ [ "endnl\n" ],
+ [ "endcr\r" ],
+ [ "blockendnl", "\n" ],
+ [ "\n", "blockstartnl" ],
+ [ "\nbothnl\n" ],
+ [ "\n", "blockbothnl", "\n" ],
+ [ "separate", "lines" ],
+ [ "separate\n", "newlines\n" ],
+ [ "only\rcr" ],
+ [ "end\rcr\r" ],
+ [ "after", "\nbreak", "\r\ncr" ],
+ [ "before\n", "break\r\n", "cr" ],
+ [ "both\n", "\nbreak\r", "\ncr" ],
+ [ "break\r", "\ncr\nnewline" ],
+ [ "a\r\n\r\n", "b\r\n\r", "\nc\r\n", "\r\nd\r", "\n\r\ne", "\r\n\r\nf" ],
+ [ "\r\r\nx\r", "\r\ny", "\r\r\nz\r\r" ],
+ [ "foo\r", "\nbar\n", "Hello\nworld\r" ],
+ [ "newlines\n\n" ],
+ [ "tripple\r", "\n\n\n" ],
+);
+
+# Send data with 0. on block break.
+my @zd = (
+ [ "foo\n.\nbar" ],
+ [ "foo", "\n.\nbar" ],
+ [ "foo\n", ".\nbar" ],
+ [ "foo\n.", "\nbar" ],
+ [ "foo\n.\n", "bar" ],
+
+ [ "foo\n." ],
+ [ "foo", "\n." ],
+ [ "foo\n", "." ],
+
+ [ ".\nbar" ],
+ [ ".", "\nbar" ],
+ [ ".\n", "bar" ],
+
+ [ "foo0.\nbar" ],
+ [ "foo", "0.\nbar" ],
+ [ "foo0", ".\nbar" ],
+ [ "foo0.", "\nbar" ],
+ [ "foo0.\n", "bar" ],
+
+ [ "foo0\n." ],
+ [ "foo", "0\n." ],
+ [ "foo0", "\n." ],
+ [ "foo0\n", "." ],
+);
+
+foreach (@rn, @zd) {
+ my @data = @$_;
+ my $expect = join("", @data);
+ $expect .= "\n" if $expect !~ /\n$/;
+ $expect =~ s/\r?\n/\r\n/gs;
+ $expect =~ s/(?:^|(?<=\r\n))\.\r\n/..\r\n/gs;
+ $expect .= ".\r\n";
+ $expect =~ tr/\r/\015/;
+ $expect =~ tr/\n/\012/;
+ check(@data, $expect);
+}
[Please do not change anything below this line]
-----------------------------------------------------------------
---
Flags:
category=library
severity=medium
---
Site configuration information for perl v5.8.6:
Configured by root at Thu Jan 1 0:00:00 UTC 1970.
Summary of my perl5 (revision 5 version 8 subversion 6) configuration:
Platform:
osname=openbsd, osvers=3.9, archname=i386-openbsd
uname='openbsd'
config_args='-dsE -Dopenbsd_distribution=defined'
hint=recommended, useposix=true, d_sigaction=define
usethreads=undef use5005threads=undef useithreads=undef usemultiplicity=undef
useperlio=define d_sfio=undef uselargefiles=define usesocks=undef
use64bitint=undef use64bitall=undef uselongdouble=undef
usemymalloc=n, bincompat5005=undef
Compiler:
cc='cc', ccflags ='-fno-strict-aliasing -fno-delete-null-pointer-checks -pipe -I/usr/local/include',
optimize='-O2',
cppflags='-fno-strict-aliasing -fno-delete-null-pointer-checks -pipe -I/usr/local/include'
ccversion='', gccversion='3.3.5 (propolice)', gccosandvers='openbsd3.9'
intsize=4, longsize=4, ptrsize=4, doublesize=8, byteorder=1234
d_longlong=define, longlongsize=8, d_longdbl=define, longdblsize=12
ivtype='long', ivsize=4, nvtype='double', nvsize=8, Off_t='off_t', lseeksize=8
alignbytes=4, prototype=define
Linker and Libraries:
ld='cc', ldflags ='-Wl,-E '
libpth=/usr/lib
libs=-lm -lutil -lc
perllibs=-lm -lutil -lc
libc=/usr/lib/libc.so.39.0, so=so, useshrplib=true, libperl=libperl.so.10.0
gnulibc_version=''
Dynamic Linking:
dlsrc=dl_dlopen.xs, dlext=so, d_dlsymun=undef, ccdlflags='-Wl,-R/usr/libdata/perl5/i386-openbsd/5.8.6/CORE'
cccdlflags='-DPIC -fPIC ', lddlflags='-shared -fPIC '
Locally applied patches:
SUIDPERLIO1 - fix PERLIO_DEBUG buffer overflow (CAN-2005-0156)
SPRINTF0 - fixes for sprintf formatting issues - CVE-2005-3962
---
@INC for perl v5.8.6:
/usr/libdata/perl5/i386-openbsd/5.8.6
/usr/local/libdata/perl5/i386-openbsd/5.8.6
/usr/libdata/perl5
/usr/local/libdata/perl5
/usr/local/libdata/perl5/site_perl/i386-openbsd
/usr/libdata/perl5/site_perl/i386-openbsd
/usr/local/libdata/perl5/site_perl
/usr/libdata/perl5/site_perl
/usr/local/lib/perl5/site_perl
.
---
Environment for perl v5.8.6:
HOME=/home/bluhm
LANG (unset)
LANGUAGE (unset)
LD_LIBRARY_PATH (unset)
LOGDIR (unset)
PATH=/usr/bin:/bin:/usr/sbin:/sbin:/usr/X11R6/bin:/usr/local/bin:/home/bluhm/bin
PERL_BADLANG (unset)
SHELL=/bin/ksh