Hello,
I have found some NULL dereferencing bugs and buffer overflows in
lynx. They cause crashes under various circumstances. Despite being
buffer overflows, I see no security impact at all. The bugs affect
at least the versions 2.8.6dev.13 and 2.8.5. All patches are made
against 2.8.6dev.13.
1) NULL dereferencing crash with unexpected data from Gopher server
I have attached a fake Gopher server, lynx-gopher-crash.pl, that
illustrates this issue. Run it, connect to it with lynx (lynx
gopher://fake.server), select the Search menu item, press s, search
for something.. notice how lynx crashes.
The attached patch lynx.gophercrash.patch corrects this bug.
2) Buffer overflow when handling overly long prefix/suffix strings
in lynx.cfg
You can test this issue by applying the lynxcfg.prefixsuffix.patch
file to lynx.cfg and then using lynx to connect to a host with no
dots (lynx a).. notice how lynx crashes.
The attached patch lynx.prefixsuffixcrash.patch corrects this bug.
3) Buffer overflow when lex() parses data from files
I have attached the lynx.lexoverflow.patch file for this issue.
// Ulf Harnhammar
#!/usr/bin/perl --
# lynx-gopher-crash
# by Ulf Harnhammar in 2005
# I hereby place this program in the public domain.
use strict;
use IO::Socket;
$main::port = 70;
$main::timeout = 5;
# *** SUBROUTINES ***
sub mysend($$)
{
my $file = shift;
my $str = shift;
print $file "$str\n";
print "SENT: $str\n";
} # sub mysend
sub myreceive($)
{
my $file = shift;
my $inp;
eval
{
local $SIG{ALRM} = sub { die "alarm\n" };
alarm $main::timeout;
$inp = <$file>;
alarm 0;
};
if ($@ eq "alarm\n") { $inp = ''; print "TIMED OUT\n"; }
$inp =~ tr/\015\012\000//d;
print "RECEIVED: $inp\n";
$inp;
} # sub myreceive
# *** MAIN PROGRAM ***
{
die "usage: $0 my_own_hostname\n" unless @ARGV == 1;
my $server = IO::Socket::INET->new( Proto => 'tcp',
LocalPort => $main::port,
Listen => SOMAXCONN,
Reuse => 1);
die "can't set up server!\n" unless $server;
while (my $client = $server->accept())
{
$client->autoflush(1);
print 'connection from '.$client->peerhost."\n";
my $str = myreceive($client);
if ($str eq '')
{ mysend($client, "2Search\tsearch\t$ARGV[0]\t$main::port"); }
else
{ mysend($client, '-a'); }
close $client;
print "closed\n\n\n";
} # while client=server->accept()
}
--- WWW/Library/Implementation/HTGopher.c.old 2005-01-03 00:35:21.000000000
+0100
+++ WWW/Library/Implementation/HTGopher.c 2005-09-24 20:39:17.046628248
+0200
@@ -455,7 +455,7 @@ static void parse_cso(const char *arg,
int ich;
char line[BIG];
char *p = line;
- char *second_colon, last_char = '\0';
+ char *first_colon, *second_colon, last_char = '\0';
const char *title;
START(HTML_HEAD);
@@ -524,7 +524,11 @@ static void parse_cso(const char *arg,
/*
* Find the second_colon.
*/
- second_colon = strchr(strchr(p, ':') + 1, ':');
+ second_colon = NULL;
+ first_colon = strchr(p, ':');
+ if (first_colon != NULL) {
+ second_colon = strchr(first_colon + 1, ':');
+ }
if (second_colon != NULL) { /* error check */
--- lynx.cfg.old 2004-12-30 13:11:59.000000000 +0100
+++ lynx.cfg 2005-09-25 00:43:49.853694800 +0200
@@ -626,8 +626,8 @@
# and use "http://" as the default (e.g., gopher.wfbr.edu or gopher.wfbr.
# will be made gopher://gopher.wfbr.edu).
#
-#URL_DOMAIN_PREFIXES:www.
-#URL_DOMAIN_SUFFIXES:.com,.edu,.net,.org
+URL_DOMAIN_PREFIXES:UUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUU.
+URL_DOMAIN_SUFFIXES:.com,.edu,.net,.UUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUU,.org
.h2 FORMS_OPTIONS
--- src/LYUtils.c.old 2005-06-03 00:36:59.000000000 +0200
+++ src/LYUtils.c 2005-09-25 00:53:39.621036536 +0200
@@ -4368,6 +4368,7 @@ BOOLEAN LYExpandHostForURL(char **Alloca
char DomainPrefix[80];
const char *StartP, *EndP;
char DomainSuffix[80];
+ unsigned int fixcount;
const char *StartS, *EndS;
char *Str = NULL, *StrColon = NULL, *MsgStr = NULL;
char *Host = NULL, *HostColon = NULL, *host = NULL;
@@ -4521,7 +4522,10 @@ BOOLEAN LYExpandHostForURL(char **Alloca
while (*EndP && !WHITE(*EndP) && *EndP != ',') {
EndP++; /* Find separator */
}
- LYstrncpy(DomainPrefix, StartP, (EndP - StartP));
+ fixcount = EndP - StartP;
+ if (fixcount > 79)
+ fixcount = 79;
+ LYstrncpy(DomainPrefix, StartP, fixcount);
/*
* Test each prefix with each suffix. - FM
@@ -4541,7 +4545,10 @@ BOOLEAN LYExpandHostForURL(char **Alloca
while (*EndS && !WHITE(*EndS) && *EndS != ',') {
EndS++; /* Find separator */
}
- LYstrncpy(DomainSuffix, StartS, (EndS - StartS));
+ fixcount = EndS - StartS;
+ if (fixcount > 79)
+ fixcount = 79;
+ LYstrncpy(DomainSuffix, StartS, fixcount);
/*
* Create domain names and do DNS tests. - FM
@@ -4597,7 +4604,10 @@ BOOLEAN LYExpandHostForURL(char **Alloca
while (*EndS && !WHITE(*EndS) && *EndS != ',') {
EndS++; /* Find separator */
}
- LYstrncpy(DomainSuffix, StartS, (EndS - StartS));
+ fixcount = EndS - StartS;
+ if (fixcount > 79)
+ fixcount = 79;
+ LYstrncpy(DomainSuffix, StartS, fixcount);
}
} while ((GotHost == FALSE) && (*DomainSuffix != '\0'));
@@ -4613,7 +4623,10 @@ BOOLEAN LYExpandHostForURL(char **Alloca
while (*EndP && !WHITE(*EndP) && *EndP != ',') {
EndP++; /* Find separator */
}
- LYstrncpy(DomainPrefix, StartP, (EndP - StartP));
+ fixcount = EndP - StartP;
+ if (fixcount > 79)
+ fixcount = 79;
+ LYstrncpy(DomainPrefix, StartP, fixcount);
}
} while ((GotHost == FALSE) && (*DomainPrefix != '\0'));
--- WWW/Library/Implementation/HTLex.c.old 2004-11-07 18:43:13.000000000
+0100
+++ WWW/Library/Implementation/HTLex.c 2005-09-25 01:19:13.153904104 +0200
@@ -97,7 +97,8 @@ LexItem lex(FILE *fp)
}
break;
default:
- HTlex_buffer[lex_cnt++] = (char) ch;
+ if (lex_cnt < 39)
+ HTlex_buffer[lex_cnt++] = (char) ch;
HTlex_buffer[lex_cnt] = '\0';
if ('*' == ch)
lex_template = YES;
_______________________________________________
Lynx-dev mailing list
[email protected]
http://lists.nongnu.org/mailman/listinfo/lynx-dev