1
0
mirror of https://github.com/nmap/nmap.git synced 2025-12-25 17:09:02 +00:00

Fix TCP option checking, which could be fooled by unknown kind into failing validation. See #1204

This commit is contained in:
dmiller
2018-05-01 03:39:49 +00:00
parent 45229e0fbd
commit c314e81cc6

View File

@@ -1360,25 +1360,31 @@ static bool validateTCPhdr(u8 *tcpc, unsigned len) {
tcpc += sizeof(struct tcp_hdr);
optlen = hdrlen - sizeof(struct tcp_hdr);
#define OPTLEN_IS(expected) do { \
if (optlen < (expected) || *++tcpc != (expected)) \
return false; \
optlen -= (expected); \
tcpc += (expected) - 1; \
} while(0);
while (optlen > 0) {
switch (*tcpc) {
case 0: // EOL
/* Options processing is over. */
return true;
case 1: // NOP
/* 1 byte, no length. All other options have a length. */
optlen--;
tcpc++;
break;
case 2: /* MSS */
if (optlen < 4)
return false;
optlen -= 4;
tcpc += 4;
OPTLEN_IS(4);
break;
case 3: /* Window Scale */
if (optlen < 3)
return false;
optlen -= 3;
tcpc += 3;
OPTLEN_IS(3);
break;
case 4: /* SACK Permitted */
if (optlen < 2)
return false;
optlen -= 2;
tcpc += 2;
OPTLEN_IS(2);
break;
case 5: /* SACK */
if (optlen < *++tcpc)
@@ -1389,23 +1395,19 @@ static bool validateTCPhdr(u8 *tcpc, unsigned len) {
tcpc += (*tcpc - 1);
break;
case 8: /* Timestamp */
if (optlen < 10)
return false;
optlen -= 10;
tcpc += 10;
OPTLEN_IS(10);
break;
case 14: /* Alternate checksum */
/* Sometimes used for hardware checksum offloading
* ftp://ftp.ucsd.edu/pub/csl/fastnet/faq.txt
*/
if (optlen < 3)
return false;
optlen -= 3;
tcpc += 3;
OPTLEN_IS(3);
break;
default:
optlen--;
tcpc++;
if (optlen < 2 || optlen < *++tcpc)
return false;
optlen -= *tcpc;
tcpc += (*tcpc - 1);
break;
}
}