From eed1de6d29d29dabb8ded36c1ecd5603a0c2ae58 Mon Sep 17 00:00:00 2001 From: Oliver Date: Tue, 7 Feb 2012 19:41:49 +0100 Subject: [PATCH] [sys net destiny] - TCP_HC: changed retransmit of payload to MOSTLY_COMPRESSED_HEADER --- projects/tlayer/main.c | 2 +- sys/net/destiny/destiny.h | 2 +- sys/net/destiny/socket.c | 40 ++++++++---- sys/net/destiny/socket.h | 2 +- sys/net/destiny/tcp.c | 7 ++- sys/net/destiny/tcp.h | 2 +- sys/net/destiny/tcp_hc.c | 125 +++++++++++++++++++++++++++++++++++--- sys/net/destiny/tcp_hc.h | 2 +- 8 files changed, 155 insertions(+), 27 deletions(-) diff --git a/projects/tlayer/main.c b/projects/tlayer/main.c index a08598d68f..f2432dd0b7 100644 --- a/projects/tlayer/main.c +++ b/projects/tlayer/main.c @@ -94,7 +94,7 @@ void tcp_ch(void) read_bytes = recv(SocketFD, buff_msg, MAX_TCP_BUFFER, 0); if (read_bytes > 0) { - printf("--- Message: %s ---\n", buff_msg); +// printf("--- Message: %s ---\n", buff_msg); } } diff --git a/sys/net/destiny/destiny.h b/sys/net/destiny/destiny.h index 3b42e105e5..7a793e488c 100644 --- a/sys/net/destiny/destiny.h +++ b/sys/net/destiny/destiny.h @@ -8,7 +8,7 @@ #ifndef DESTINY_H_ #define DESTINY_H_ -//#define TCP_HC +#define TCP_HC void init_transport_layer(void); diff --git a/sys/net/destiny/socket.c b/sys/net/destiny/socket.c index 505431aa47..4030caf70f 100644 --- a/sys/net/destiny/socket.c +++ b/sys/net/destiny/socket.c @@ -17,8 +17,8 @@ #include "sys/net/net_help/net_help.h" #include "sys/net/net_help/msg_help.h" -msg_t socket_msg_queue[IP_PKT_RECV_BUF_SIZE]; -msg_t send_msg_queue[SEND_MSG_BUF_SIZE]; +//msg_t socket_msg_queue[IP_PKT_RECV_BUF_SIZE]; +//msg_t send_msg_queue[SEND_MSG_BUF_SIZE]; void printf_tcp_context(tcp_hc_context_t *current_tcp_context) { @@ -391,6 +391,11 @@ int send_tcp(socket_internal_t *current_socket, tcp_hdr_t *current_tcp_packet, i uint16_t compressed_size; compressed_size = compress_tcp_packet(current_socket, (uint8_t *) current_tcp_packet, temp_ipv6_header, flags, payload_length); + if (compressed_size == 0) + { + // Error in compressing tcp packet header + return -1; + } sixlowpan_send(¤t_tcp_socket->foreign_address.sin6_addr, (uint8_t*)(current_tcp_packet), compressed_size, IPPROTO_TCP); return 1; @@ -531,7 +536,7 @@ int32_t send(int s, void *msg, uint64_t len, int flags) uint8_t send_buffer[BUFFER_SIZE]; ipv6_hdr_t *temp_ipv6_header = ((ipv6_hdr_t*)(&send_buffer)); tcp_hdr_t *current_tcp_packet = ((tcp_hdr_t*)(&send_buffer[IPV6_HDR_LEN])); - msg_init_queue(send_msg_queue, SEND_MSG_BUF_SIZE); +// msg_init_queue(send_msg_queue, SEND_MSG_BUF_SIZE); // Check if socket exists and is TCP socket if (!isTCPSocket(s)) @@ -553,6 +558,13 @@ int32_t send(int s, void *msg, uint64_t len, int flags) current_tcp_socket->tcp_control.no_of_retry = 0; +#ifdef TCP_HC + current_tcp_socket->tcp_control.tcp_context.hc_type = COMPRESSED_HEADER; + // Remember TCP Context for possible TCP_RETRY + tcp_hc_context_t saved_tcp_context; + memcpy(&saved_tcp_context, ¤t_tcp_socket->tcp_control.tcp_context, sizeof(tcp_hc_context_t)-1); +#endif + while (1) { // Add packet data @@ -570,13 +582,17 @@ int32_t send(int s, void *msg, uint64_t len, int flags) current_tcp_socket->tcp_control.send_nxt += sent_bytes; current_tcp_socket->tcp_control.send_wnd -= sent_bytes; + if (send_tcp(current_int_tcp_socket, current_tcp_packet, temp_ipv6_header, 0, sent_bytes) != 1) + { + // Error while sending tcp data + current_tcp_socket->tcp_control.send_nxt -= sent_bytes; + current_tcp_socket->tcp_control.send_wnd += sent_bytes; #ifdef TCP_HC - // Remember TCP Context for possible TCP_RETRY - tcp_hc_context_t saved_tcp_context; - memcpy(&saved_tcp_context, ¤t_tcp_socket->tcp_control.tcp_context, sizeof(tcp_hc_context_t)); + memcpy(¤t_tcp_socket->tcp_control.tcp_context, &saved_tcp_context, sizeof(tcp_hc_context_t)); + current_tcp_socket->tcp_control.tcp_context.hc_type = COMPRESSED_HEADER; #endif - - send_tcp(current_int_tcp_socket, current_tcp_packet, temp_ipv6_header, 0, sent_bytes); + return -1; + } // Remember current time current_tcp_socket->tcp_control.last_packet_time = vtimer_now(); @@ -593,6 +609,9 @@ int32_t send(int s, void *msg, uint64_t len, int flags) current_tcp_socket->tcp_control.send_nxt = tcp_header->ack_nr; current_tcp_socket->tcp_control.send_wnd = tcp_header->window; // Got ACK for every sent byte +#ifdef TCP_HC + current_tcp_socket->tcp_control.tcp_context.hc_type = COMPRESSED_HEADER; +#endif return sent_bytes; } else @@ -617,6 +636,7 @@ int32_t send(int s, void *msg, uint64_t len, int flags) current_tcp_socket->tcp_control.send_wnd += sent_bytes; #ifdef TCP_HC memcpy(¤t_tcp_socket->tcp_control.tcp_context, &saved_tcp_context, sizeof(tcp_hc_context_t)); + current_tcp_socket->tcp_control.tcp_context.hc_type = COMPRESSED_HEADER; #endif return -1; break; @@ -656,8 +676,7 @@ int recv(int s, void *buf, uint64_t len, int flags) uint8_t read_bytes; msg_t m_recv, m_send; socket_internal_t *current_int_tcp_socket; - socket_t *current_tcp_socket; - msg_init_queue(socket_msg_queue, IP_PKT_RECV_BUF_SIZE); +// msg_init_queue(socket_msg_queue, IP_PKT_RECV_BUF_SIZE); // Check if socket exists if (!isTCPSocket(s)) { @@ -666,7 +685,6 @@ int recv(int s, void *buf, uint64_t len, int flags) } current_int_tcp_socket = getSocket(s); - current_tcp_socket = ¤t_int_tcp_socket->socket_values; // Setting Thread PID current_int_tcp_socket->recv_pid = thread_getpid(); diff --git a/sys/net/destiny/socket.h b/sys/net/destiny/socket.h index 69ecd14d56..19ac0d96b6 100644 --- a/sys/net/destiny/socket.h +++ b/sys/net/destiny/socket.h @@ -14,7 +14,7 @@ #include "in.h" #include "sys/net/sixlowpan/sixlowip.h" -//#define TCP_HC +#define TCP_HC /* * Types diff --git a/sys/net/destiny/tcp.c b/sys/net/destiny/tcp.c index 72411c800b..51ed68bab1 100644 --- a/sys/net/destiny/tcp.c +++ b/sys/net/destiny/tcp.c @@ -226,6 +226,9 @@ void handle_tcp_no_flags_packet(ipv6_hdr_t *ipv6_header, tcp_hdr_t *tcp_header, if (tcp_payload_len > 0) { +#ifdef TCP_HC + current_tcp_socket->tcp_control.tcp_context.hc_type = COMPRESSED_HEADER; +#endif if (check_tcp_consistency(current_tcp_socket, tcp_header) == PACKET_OK) { read_bytes = handle_payload(ipv6_header, tcp_header, tcp_socket, payload); @@ -342,8 +345,8 @@ void tcp_packet_handler (void) else { printf("Wrong checksum (%x) or no corresponding socket found!\n", chksum); -// printArrayRange(((uint8_t *)ipv6_header), IPV6_HDR_LEN+ipv6_header->length, "Incoming"); -// print_tcp_status(INC_PACKET, ipv6_header, tcp_header, &tcp_socket->socket_values); + printArrayRange(((uint8_t *)ipv6_header), IPV6_HDR_LEN+ipv6_header->length, "Incoming"); + print_tcp_status(INC_PACKET, ipv6_header, tcp_header, &tcp_socket->socket_values); } msg_reply(&m_recv_ip, &m_send_ip); diff --git a/sys/net/destiny/tcp.h b/sys/net/destiny/tcp.h index 569c3afe21..f1c1472172 100644 --- a/sys/net/destiny/tcp.h +++ b/sys/net/destiny/tcp.h @@ -8,7 +8,7 @@ #ifndef TCP_H_ #define TCP_H_ -//#define TCP_HC +#define TCP_HC #define TCP_HDR_LEN 20 diff --git a/sys/net/destiny/tcp_hc.c b/sys/net/destiny/tcp_hc.c index 9f016ed9d5..4662321bc1 100644 --- a/sys/net/destiny/tcp_hc.c +++ b/sys/net/destiny/tcp_hc.c @@ -59,11 +59,8 @@ uint16_t compress_tcp_packet(socket_internal_t *current_socket, uint8_t *current tcp_hdr_t full_tcp_header; uint16_t packet_size = 0; + // Connection establisment phase, use FULL_HEADER TCP if (tcp_cb->state != ESTABLISHED) -// if ((tcp_cb->state != ESTABLISHED) || -// ((tcp_cb->state == ESTABLISHED) && -// IS_TCP_ACK(((tcp_hdr_t*)current_tcp_packet)->reserved_flags) && -// (tcp_cb->tcp_context.ack_snd == ((tcp_hdr_t*)current_tcp_packet)->ack_nr))) { // draft-aayadi-6lowpan-tcphc-01: 5.1 Full header TCP segment. Establishing Connection @@ -88,7 +85,8 @@ uint16_t compress_tcp_packet(socket_internal_t *current_socket, uint8_t *current return packet_size; } - else + // Check for header compression type: COMPRESSED_HEADER + else if (tcp_context->hc_type == COMPRESSED_HEADER) { // draft-aayadi-6lowpan-tcphc-01: 5.1 Compressed header TCP segment. @@ -109,8 +107,8 @@ uint16_t compress_tcp_packet(socket_internal_t *current_socket, uint8_t *current // 5.2. LOWPAN_TCPHC Format - // First 3 bits of TCP_HC_Header are not exactly specified. In this implementation they are always (1|1|0) - // CID is always 16 bits in this implementation (1) + // First 3 bits of TCP_HC_Header are not exactly specified. In this implementation they are (1|1|0) + // for compressed headers and the CID is always 16 bits (1) // (1|1|0|1) = D tcp_hc_header |= 0xD000; @@ -278,6 +276,102 @@ uint16_t compress_tcp_packet(socket_internal_t *current_socket, uint8_t *current // print_tcp_status(OUT_PACKET, temp_ipv6_header, &full_tcp_header, current_tcp_socket); return packet_size; } + // Check for header compression type: MOSTLY_COMPRESSED_HEADER + else if (tcp_context->hc_type == MOSTLY_COMPRESSED_HEADER) + { + // draft-aayadi-6lowpan-tcphc-01: 5.1 Compressed header TCP segment. + + // Temporary variable for TCP_HC_Header Bytes + uint16_t tcp_hc_header = 0x0000; + + // Save TCP_Header to refresh TCP Context values after compressing the packet + memcpy(&full_tcp_header, current_tcp_packet, TCP_HDR_LEN); + + // Temporary variable for storing TCP header beginning + uint8_t *tcp_packet_begin = current_tcp_packet; + + // Position for first TCP header value, TCP_HC_Header and Context ID + current_tcp_packet += 4; + + // Packet size value + packet_size += 4; + + // 5.2. LOWPAN_TCPHC Format + + // First 3 bits of TCP_HC_Header are not exactly specified. In this implementation they are (1|0|0) + // for mostly compressed headers and the CID is always 16 bits (1) + // (1|0|0|1) = 9 + tcp_hc_header |= 0x9000; + + /*----------------------------------*/ + /*| Sequence number handling |*/ + /*----------------------------------*/ + // Sending uncompressed sequence number + // Seq = (1|1) + tcp_hc_header |= 0x0C00; + + // Copy all bits of sequence number into buffer + uint32_t cur_seq_no = HTONL(full_tcp_header.seq_nr); + memcpy(current_tcp_packet, &cur_seq_no, 4); + current_tcp_packet += 4; + packet_size += 4; + + /*----------------------------------*/ + /*| Acknowledgment number handling |*/ + /*----------------------------------*/ + // Ack = (1|1) + tcp_hc_header |= 0x0300; + + // Copy all bits of acknowledgment number into buffer + uint32_t cur_ack_nr = HTONL(full_tcp_header.ack_nr); + memcpy(current_tcp_packet, &cur_ack_nr, 4); + current_tcp_packet += 4; + packet_size += 4; + + /*----------------------------------*/ + /*| Window handling |*/ + /*----------------------------------*/ + // Wnd = (1|1) + tcp_hc_header |= 0x00C0; + + // Copy all bits of window size into buffer + uint16_t cur_window = HTONS(full_tcp_header.window); + memcpy(current_tcp_packet, &cur_window, 2); + current_tcp_packet += 2; + packet_size += 2; + + // FIN flag + if (IS_TCP_FIN(full_tcp_header.reserved_flags)) + { + // F = (1) + tcp_hc_header |= 0x0008; + } + + // Copy checksum into buffer + uint16_t cur_chk_sum = HTONS(full_tcp_header.checksum); + memcpy(current_tcp_packet, &cur_chk_sum, 2); + current_tcp_packet += 2; + packet_size += 2; + + // Copy TCP_HC Bytes into buffer + uint16_t cur_tcp_hc_header = HTONS(tcp_hc_header); + memcpy(tcp_packet_begin, &cur_tcp_hc_header, 2); + + // Copy TCP_HC Context ID into buffer + uint16_t cur_context_id = HTONS(tcp_context->context_id); + memcpy(tcp_packet_begin+2, &cur_context_id, 2); + + // Move payload to end of tcp header + memmove(current_tcp_packet, tcp_packet_begin+TCP_HDR_LEN, payload_length); + + // Adding TCP payload length to TCP_HC header length + packet_size += payload_length; + + update_tcp_hc_context(false, current_socket, &full_tcp_header); +// print_tcp_status(OUT_PACKET, temp_ipv6_header, &full_tcp_header, current_tcp_socket); + return packet_size; + } + return 0; } socket_internal_t *decompress_tcp_packet(ipv6_hdr_t *temp_ipv6_header) @@ -322,10 +416,20 @@ socket_internal_t *decompress_tcp_packet(ipv6_hdr_t *temp_ipv6_header) memcpy(¤t_context, (packet_buffer+2), 2); current_context = NTOHS(current_context); - // Copy TCP_HC header into local variable + // Copy TCP_HC header into local variable (1,0,0,1|SEQ,SEQ,0)(1,0,0,1|0,0,0,0) memcpy(&tcp_hc_header, packet_buffer, 2); tcp_hc_header = NTOHS(tcp_hc_header); + uint8_t header_type = UNDEFINED; + if (BITSET(tcp_hc_header, 15) && !BITSET(tcp_hc_header, 14) && !BITSET(tcp_hc_header, 13)) + { + header_type = MOSTLY_COMPRESSED_HEADER; + } + else if (BITSET(tcp_hc_header, 15) && BITSET(tcp_hc_header, 14) && !BITSET(tcp_hc_header, 13)) + { + header_type = COMPRESSED_HEADER; + } + // Setting pointer to first tcp_hc field packet_buffer += 4; packet_size += 4; @@ -414,7 +518,10 @@ socket_internal_t *decompress_tcp_packet(ipv6_hdr_t *temp_ipv6_header) full_tcp_header.ack_nr = NTOHL(full_tcp_header.ack_nr); packet_buffer += 4; packet_size += 4; - SET_TCP_ACK(full_tcp_header.reserved_flags); + if (header_type == COMPRESSED_HEADER) + { + SET_TCP_ACK(full_tcp_header.reserved_flags); + } } /*----------------------------------*/ diff --git a/sys/net/destiny/tcp_hc.h b/sys/net/destiny/tcp_hc.h index 52f7fb2003..33eabe8d84 100644 --- a/sys/net/destiny/tcp_hc.h +++ b/sys/net/destiny/tcp_hc.h @@ -8,7 +8,7 @@ #ifndef TCP_HC_H_ #define TCP_HC_H_ -//#define TCP_HC +#define TCP_HC #include "tcp.h" #include "sys/net/sixlowpan/sixlowip.h"