Subject: PoPToP PPTP server remotely exploitable buffer overflow Versions older than 1.1.4-b3 and 1.1.3-20030409 affected. This seems to be exploitable only with Linux. PPTP? ----- PPTP-over-IPSEC is commonly used to create VPNs. Windows plays quite nicely with it. problem ------- PPTP packet header contain 16bit length which specifies the full size of the packet: bytes_this = read(clientFd, packet + bytes_ttl, 2 - bytes_ttl); // ... bytes_ttl += bytes_this; // ... length = htons(*(u_int16_t *) packet); if (length > PPTP_MAX_CTRL_PCKT_SIZE) { // abort } Looks good so far, except: bytes_this = read(clientFd, packet + bytes_ttl, length - bytes_ttl); If given length was 0 or 1, the "length - bytes_ttl" result is -1 or -2, which means that it reads unlimited amount of data from client into "packet", which is a buffer located in stack. The exploitability only depends on if libc allows the size parameter to be larger than SSIZE_MAX bytes. GLIBC does, Solaris and *BSD don't. tips of the day --------------- Don't do arithmetic in parameters specifying buffer size. Block PPTP port for non-IPSEC connections, if you don't already. patch ----- This is the same as in latest versions: --- ctrlpacket.c.old 1999-12-23 23:43:33.000000000 +0200 +++ ctrlpacket.c 2003-04-09 18:58:21.000000000 +0300 @@ -254,8 +254,8 @@ } /* OK, we have (at least) the first 2 bytes, and there is data waiting */ length = htons(*(u_int16_t *) packet); - if (length > PPTP_MAX_CTRL_PCKT_SIZE) { - syslog(LOG_ERR, "CTRL: Control packet > PPTP_MAX_CTRL_PCKT_SIZE (length = %d)", length); + if (length <= 10 || length > PPTP_MAX_CTRL_PCKT_SIZE) { + syslog(LOG_ERR, "CTRL: 11 < Control packet (length=%d) < ", length); /* we loose sync (unless we malloc something big, which isn't a good * idea - potential DoS) so we must close connection (draft states that * if you loose sync you must close the control connection immediately)