if (type == SSH2_MSG_NEWKEYS) { if (kex==NULL || mac==NULL || enc==NULL || comp==NULL) fatal("packet_read_poll2: no KEX"); if (mac->md != NULL) mac->enabled = 1; DBG(debug("cipher_init receive_context")); cipher_init(&receive_context, enc->cipher, enc->key, enc->cipher->key_len, enc->iv, enc->cipher->block_size); clear_enc_keys(enc, kex->we_need); if (comp->type != 0 && comp->enabled == 0) { comp->enabled = 1; if (! packet_compression) packet_start_compression(6); } }
if (type == SSH2_MSG_NEWKEYS) set_newkeys(MODE_IN);
packet_read_poll2(int *payload_len_ptr){	static u_int32_t seqnr = 0;	static u_int packet_length = 0;	u_int padlen, need;	u_char buf[8], *macbuf;	u_char *ucp;	char *cp;	int type;	int maclen, block_size;	Enc *enc   = NULL;	Mac *mac   = NULL;	Comp *comp = NULL;	if (kex != NULL) {		enc  = &kex->enc[MODE_IN];		mac  = &kex->mac[MODE_IN];		comp = &kex->comp[MODE_IN];	}	maclen = mac && mac->enabled ? mac->mac_len : 0;	block_size = enc ? enc->cipher->block_size : 8;	if (packet_length == 0) {		/*		 * check if input size is less than the cipher block size,		 * decrypt first block and extract length of incoming packet		 */		if (buffer_len(&input) < block_size)			return SSH_MSG_NONE;		buffer_clear(&incoming_packet);		buffer_append_space(&incoming_packet, &cp, block_size);		packet_decrypt(&receive_context, cp, buffer_ptr(&input),		    block_size);		ucp = (u_char *) buffer_ptr(&incoming_packet);		packet_length = GET_32BIT(ucp);		if (packet_length < 1 + 4 || packet_length > 256 * 1024) {			buffer_dump(&incoming_packet);			packet_disconnect("Bad packet length %d.", packet_length);		}		DBG(debug("input: packet len %d", packet_length+4));		buffer_consume(&input, block_size);	}	/* we have a partial packet of block_size bytes */	need = 4 + packet_length - block_size;	DBG(debug("partial packet %d, need %d, maclen %d", block_size,	    need, maclen));	if (need % block_size != 0)		fatal("padding error: need %d block %d mod %d",		    need, block_size, need % block_size);	/*	 * check if the entire packet has been received and	 * decrypt into incoming_packet	 */	if (buffer_len(&input) < need + maclen)		return SSH_MSG_NONE;#ifdef PACKET_DEBUG	fprintf(stderr, "read_poll enc/full: ");	buffer_dump(&input);#endif	buffer_append_space(&incoming_packet, &cp, need);	packet_decrypt(&receive_context, cp, buffer_ptr(&input), need);	buffer_consume(&input, need);	/*	 * compute MAC over seqnr and packet,	 * increment sequence number for incoming packet	 */	if (mac && mac->enabled) {		macbuf = mac_compute(mac, seqnr,		    (u_char *) buffer_ptr(&incoming_packet),		    buffer_len(&incoming_packet));		if (memcmp(macbuf, buffer_ptr(&input), mac->mac_len) != 0)			packet_disconnect("Corrupted MAC on input.");		DBG(debug("MAC #%d ok", seqnr));		buffer_consume(&input, mac->mac_len);	}	if (++seqnr == 0)		log("incoming seqnr wraps around");	/* get padlen */	cp = buffer_ptr(&incoming_packet) + 4;	padlen = *cp & 0xff;	DBG(debug("input: padlen %d", padlen));	if (padlen < 4)		packet_disconnect("Corrupted padlen %d on input.", padlen);	/* skip packet size + padlen, discard padding */	buffer_consume(&incoming_packet, 4 + 1);	buffer_consume_end(&incoming_packet, padlen);	DBG(debug("input: len before de-compress %d", buffer_len(&incoming_packet)));	if (comp && comp->enabled) {		buffer_clear(&compression_buffer);		buffer_uncompress(&incoming_packet, &compression_buffer);		buffer_clear(&incoming_packet);		buffer_append(&incoming_packet, buffer_ptr(&compression_buffer),		    buffer_len(&compression_buffer));		DBG(debug("input: len after de-compress %d", buffer_len(&incoming_packet)));	}	/*	 * get packet type, implies consume.	 * return length of payload (without type field)	 */	buffer_get(&incoming_packet, (char *)&buf[0], 1);	*payload_len_ptr = buffer_len(&incoming_packet);	/* reset for next packet */	packet_length = 0;	/* extract packet type */	type = (u_char)buf[0];	if (type == SSH2_MSG_NEWKEYS) {		if (kex==NULL || mac==NULL || enc==NULL || comp==NULL)			fatal("packet_read_poll2: no KEX");		if (mac->md != NULL)			mac->enabled = 1;		DBG(debug("cipher_init receive_context"));		cipher_init(&receive_context, enc->cipher,		    enc->key, enc->cipher->key_len,		    enc->iv, enc->cipher->block_size);		clear_enc_keys(enc, kex->we_need);		if (comp->type != 0 && comp->enabled == 0) {			comp->enabled = 1;			if (! packet_compression)				packet_start_compression(6);		}	}#ifdef PACKET_DEBUG	fprintf(stderr, "read/plain[%d]:\r\n", type);	buffer_dump(&incoming_packet);#endif	return (u_char)type;}