Openwall GNU/*/Linux - a small security-enhanced Linux distro for servers
[<prev] [next>] [thread-next>] [day] [month] [year] [list]
Date: Sat, 16 May 2015 12:58:12 +0200
From: Hanno Böck <hanno@...eck.de>
To: oss-security@...ts.openwall.com
Subject: about this openssh heap overflow

Hi,

Quick background story: I started a while ago to develop a solution to
use american fuzzy lop with networking input. I did so by creating a
library to be preloaded with LD_PRELOAD that would intercept some
functions to simulate a network connection and pass data from a file.

This is trickier than it sounds and doesn't really work yet, but I
managed to use this to fuzz the ssh client handshake. In combination
with address sanitizer this turned up a read heap overflow. I reported
this to openssh's damien miller. He considered it not security relevant
and committed the fix to the public repo:
https://anongit.mindrot.org/openssh.git/commit/?id=77199d6ec8986d470487e66f8ea8f4cf43d2e20c

With that it was public, but nobody noticed. Until today someone
proposed a very similar approach to network fuzzing on the afl mailing
list and I answered that I was working on this and briefly mentioned
the ssh overflow:
https://groups.google.com/d/msg/afl-users/gahT13i4zG4/I2jdwpyG3W4J

Now this is making rounds on twitter, so I thought I'd publish all
details. I just pasted below what I reported to openssh.

As this is only a read overflow it likely is not exploitable in any
way, but itsec history has shown that often enough when people think
something is not exploitable they were wrong.

If this makes you nervous apply the patch linked above (which will just
remove the length argument from the function) or this shorter patch
which will just fix the wrong function cal:

--- openssh-6.8p1/compat.c	2015-03-17 06:49:20.000000000 +0100
+++ openssh-6.8p1-fix/compat.c	2015-05-03 17:51:32.251293388 +0200
@@ -229,7 +229,7 @@
 	buffer_init(&b);
 	tmp = orig_prop = xstrdup(proposal);
 	while ((cp = strsep(&tmp, ",")) != NULL) {
-		if (match_pattern_list(cp, filter, strlen(cp), 0) != 1) {
+		if (match_pattern_list(cp, filter, strlen(filter), 0) != 1) {
 			if (buffer_len(&b) > 0)
 				buffer_append(&b, ",", 1);
 			buffer_append(&b, cp, strlen(cp));



-------------------------------

I think I found a bug in ssh, maybe security relevant.

It's surprisingly easy to reproduce:
* Compile latest openssh 6.8p1 with address sanitizer (./configure
  CFLAGS="-fsanitize=address" LDFLAGS="-fsanitize=address"; make)
* Run this netcat-command:
echo "SSH-2.0-OpenSSH_6.5"|nc -l -p 22
* ssh to it: ./ssh 127.0.0.1

I'm not entirely sure when and why this is triggered, doesn't work
against a real ssh server (I assume something with the version number
and not answering after the inital banner to the client)

However, here is why it causes an invalid memory access:
In combat.c there is this call for the function match_pattern_list in
line 232:
		if (match_pattern_list(cp, filter, strlen(cp), 0) != 1)
{

The function definition (match.c, line 120):
match_pattern_list(const char *string, const char *pattern, u_int len,

Looking at the function (match.c, line 141/142) we have this:
		for (subi = 0;
		    i < len && subi < sizeof(sub) - 1 && pattern[i] !=
',';

		    subi++, i++)

It will iterate over pattern with length len. pattern is the second
parameter passed. But in the function call len is given as the length
of the first parameter. So they don't match and this will cause a
buffer overflow if cp is longer than filter.

So the function call really should be:
		if (match_pattern_list(cp, filter, strlen(filter), 0) !=
1) {

Right? (Not 100% sure if I got everything what's happening here...)
See attached patch. Will also attach an address sanitizer stack trace
(for reasons unknown to me this stack trace only appears if I compile
openssh with afl + asan, not with asan alone)


-- 
Hanno Böck
http://hboeck.de/

mail/jabber: hanno@...eck.de
GPG: BBB51E42

Content of type "application/pgp-signature" skipped

Powered by blists - more mailing lists

Your e-mail address:

Please check out the Open Source Software Security Wiki, which is counterpart to this mailing list.

Powered by Openwall GNU/*/Linux - Powered by OpenVZ