Mercurial > dropbear
comparison packet.c @ 906:4696755c4cac
A few fixes for cases where compression increases payload sizes, and
be more precise about maximum channel sizes
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Sat, 22 Feb 2014 18:02:09 +0800 |
parents | 220f55d540ae |
children | b8208506322e |
comparison
equal
deleted
inserted
replaced
905:f98618496f82 | 906:4696755c4cac |
---|---|
39 static void make_mac(unsigned int seqno, const struct key_context_directional * key_state, | 39 static void make_mac(unsigned int seqno, const struct key_context_directional * key_state, |
40 buffer * clear_buf, unsigned int clear_len, | 40 buffer * clear_buf, unsigned int clear_len, |
41 unsigned char *output_mac); | 41 unsigned char *output_mac); |
42 static int checkmac(); | 42 static int checkmac(); |
43 | 43 |
44 #define ZLIB_COMPRESS_INCR 100 | 44 /* For exact details see http://www.zlib.net/zlib_tech.html |
45 * 5 bytes per 16kB block, plus 6 bytes for the stream. | |
46 * We might allocate 5 unnecessary bytes here if it's an | |
47 * exact multiple. */ | |
48 #define ZLIB_COMPRESS_EXPANSION (((RECV_MAX_PAYLOAD_LEN/16384)+1)*5 + 6) | |
45 #define ZLIB_DECOMPRESS_INCR 1024 | 49 #define ZLIB_DECOMPRESS_INCR 1024 |
46 #ifndef DISABLE_ZLIB | 50 #ifndef DISABLE_ZLIB |
47 static buffer* buf_decompress(buffer* buf, unsigned int len); | 51 static buffer* buf_decompress(buffer* buf, unsigned int len); |
48 static void buf_compress(buffer * dest, buffer * src, unsigned int len); | 52 static void buf_compress(buffer * dest, buffer * src, unsigned int len); |
49 #endif | 53 #endif |
331 padlen = buf_getbyte(ses.readbuf); | 335 padlen = buf_getbyte(ses.readbuf); |
332 | 336 |
333 /* payload length */ | 337 /* payload length */ |
334 /* - 4 - 1 is for LEN and PADLEN values */ | 338 /* - 4 - 1 is for LEN and PADLEN values */ |
335 len = ses.readbuf->len - padlen - 4 - 1 - macsize; | 339 len = ses.readbuf->len - padlen - 4 - 1 - macsize; |
336 if ((len > RECV_MAX_PAYLOAD_LEN) || (len < 1)) { | 340 if ((len > RECV_MAX_PAYLOAD_LEN+ZLIB_COMPRESS_EXPANSION) || (len < 1)) { |
337 dropbear_exit("Bad packet size %d", len); | 341 dropbear_exit("Bad packet size %d", len); |
338 } | 342 } |
339 | 343 |
340 buf_setpos(ses.readbuf, PACKET_PAYLOAD_OFF); | 344 buf_setpos(ses.readbuf, PACKET_PAYLOAD_OFF); |
341 | 345 |
420 } | 424 } |
421 | 425 |
422 if (zstream->avail_out == 0) { | 426 if (zstream->avail_out == 0) { |
423 int new_size = 0; | 427 int new_size = 0; |
424 if (ret->size >= RECV_MAX_PAYLOAD_LEN) { | 428 if (ret->size >= RECV_MAX_PAYLOAD_LEN) { |
429 /* Already been increased as large as it can go, | |
430 * yet didn't finish up the decompression */ | |
425 dropbear_exit("bad packet, oversized decompressed"); | 431 dropbear_exit("bad packet, oversized decompressed"); |
426 } | 432 } |
427 new_size = MIN(RECV_MAX_PAYLOAD_LEN, ret->size + ZLIB_DECOMPRESS_INCR); | 433 new_size = MIN(RECV_MAX_PAYLOAD_LEN, ret->size + ZLIB_DECOMPRESS_INCR); |
428 buf_resize(ret, new_size); | 434 buf_resize(ret, new_size); |
429 } | 435 } |
524 + MAX(MIN_PACKET_LEN, blocksize) + 3 | 530 + MAX(MIN_PACKET_LEN, blocksize) + 3 |
525 /* add space for the MAC at the end */ | 531 /* add space for the MAC at the end */ |
526 + mac_size | 532 + mac_size |
527 #ifndef DISABLE_ZLIB | 533 #ifndef DISABLE_ZLIB |
528 /* some extra in case 'compression' makes it larger */ | 534 /* some extra in case 'compression' makes it larger */ |
529 + ZLIB_COMPRESS_INCR | 535 + ZLIB_COMPRESS_EXPANSION |
530 #endif | 536 #endif |
531 /* and an extra cleartext (stripped before transmission) byte for the | 537 /* and an extra cleartext (stripped before transmission) byte for the |
532 * packet type */ | 538 * packet type */ |
533 + 1; | 539 + 1; |
534 | 540 |
537 buf_setpos(writebuf, PACKET_PAYLOAD_OFF); | 543 buf_setpos(writebuf, PACKET_PAYLOAD_OFF); |
538 | 544 |
539 #ifndef DISABLE_ZLIB | 545 #ifndef DISABLE_ZLIB |
540 /* compression */ | 546 /* compression */ |
541 if (is_compress_trans()) { | 547 if (is_compress_trans()) { |
542 int compress_delta; | |
543 buf_compress(writebuf, ses.writepayload, ses.writepayload->len); | 548 buf_compress(writebuf, ses.writepayload, ses.writepayload->len); |
544 compress_delta = (writebuf->len - PACKET_PAYLOAD_OFF) - ses.writepayload->len; | |
545 | |
546 /* Handle the case where 'compress' increased the size. */ | |
547 if (compress_delta > ZLIB_COMPRESS_INCR) { | |
548 buf_resize(writebuf, writebuf->size + compress_delta); | |
549 } | |
550 } else | 549 } else |
551 #endif | 550 #endif |
552 { | 551 { |
553 memcpy(buf_getwriteptr(writebuf, ses.writepayload->len), | 552 memcpy(buf_getwriteptr(writebuf, ses.writepayload->len), |
554 buf_getptr(ses.writepayload, ses.writepayload->len), | 553 buf_getptr(ses.writepayload, ses.writepayload->len), |
692 dropbear_assert(ses.keys->trans.zstream->avail_out == 0); | 691 dropbear_assert(ses.keys->trans.zstream->avail_out == 0); |
693 | 692 |
694 /* the buffer has been filled, we must extend. This only happens in | 693 /* the buffer has been filled, we must extend. This only happens in |
695 * unusual circumstances where the data grows in size after deflate(), | 694 * unusual circumstances where the data grows in size after deflate(), |
696 * but it is possible */ | 695 * but it is possible */ |
697 buf_resize(dest, dest->size + ZLIB_COMPRESS_INCR); | 696 buf_resize(dest, dest->size + ZLIB_COMPRESS_EXPANSION); |
698 | 697 |
699 } | 698 } |
700 TRACE2(("leave buf_compress")) | 699 TRACE2(("leave buf_compress")) |
701 } | 700 } |
702 #endif | 701 #endif |