From 6e89e545b3302689c367505c5bc7d0ceea2a1c9f Mon Sep 17 00:00:00 2001 From: adamdunkels Date: Thu, 24 Jan 2008 23:08:58 +0000 Subject: [PATCH] Added optional transmission of ICMP destimation unreachable in response to incoming UDP packets with an destination port that is not open. This is needed for correct operation of traceroute --- core/net/uip.c | 35 ++++++++++++++++++++++++++++++++++- core/net/uip.h | 3 ++- 2 files changed, 36 insertions(+), 2 deletions(-) diff --git a/core/net/uip.c b/core/net/uip.c index 2dcfa1e21..b843da5a7 100644 --- a/core/net/uip.c +++ b/core/net/uip.c @@ -41,7 +41,7 @@ * * This file is part of the uIP TCP/IP stack. * - * $Id: uip.c,v 1.9 2007/11/28 12:53:07 adamdunkels Exp $ + * $Id: uip.c,v 1.10 2008/01/24 23:08:58 adamdunkels Exp $ * */ @@ -196,6 +196,9 @@ static u16_t tmp16; #define ICMP_ECHO_REPLY 0 #define ICMP_ECHO 8 +#define ICMP_DEST_UNREACHABLE 3 +#define ICMP_PORT_UNREACHABLE 3 + #define ICMP6_ECHO_REPLY 129 #define ICMP6_ECHO 128 #define ICMP6_NEIGHBOR_SOLICITATION 135 @@ -1104,7 +1107,37 @@ uip_process(u8_t flag) } } UIP_LOG("udp: no matching connection found"); +#if UIP_CONF_ICMP_DEST_UNREACH && !UIP_CONF_IPV6 + /* Copy fields from packet header into payload of this ICMP packet. */ + memcpy(&(ICMPBUF->payload[0]), ICMPBUF, UIP_IPH_LEN + 8); + + /* Set the ICMP type and code. */ + ICMPBUF->type = ICMP_DEST_UNREACHABLE; + ICMPBUF->icode = ICMP_PORT_UNREACHABLE; + + /* Calculate the ICMP checksum. */ + ICMPBUF->icmpchksum = 0; + ICMPBUF->icmpchksum = ~uip_chksum((u16_t *)&(ICMPBUF->type), 36); + + /* Set the IP destination address to be the source address of the + original packet. */ + uip_ipaddr_copy(&BUF->destipaddr, &BUF->srcipaddr); + + /* Set our IP address as the source address. */ + uip_ipaddr_copy(&BUF->srcipaddr, &uip_hostaddr); + + /* The size of the ICMP destination unreachable packet is 36 + the + size of the IP header (20) = 56. */ + uip_len = 36 + UIP_IPH_LEN; + ICMPBUF->len[0] = 0; + ICMPBUF->len[1] = (u8_t)uip_len; + ICMPBUF->ttl = UIP_TTL; + ICMPBUF->proto = UIP_PROTO_ICMP; + + goto ip_send_nolen; +#else /* UIP_CONF_ICMP_DEST_UNREACH */ goto drop; +#endif /* UIP_CONF_ICMP_DEST_UNREACH */ udp_found: uip_conn = NULL; diff --git a/core/net/uip.h b/core/net/uip.h index 477817dad..e5688b570 100644 --- a/core/net/uip.h +++ b/core/net/uip.h @@ -46,7 +46,7 @@ * * This file is part of the uIP TCP/IP stack. * - * $Id: uip.h,v 1.13 2007/11/28 12:52:12 adamdunkels Exp $ + * $Id: uip.h,v 1.14 2008/01/24 23:08:58 adamdunkels Exp $ * */ @@ -1497,6 +1497,7 @@ struct uip_icmpip_hdr { u16_t icmpchksum; #if !UIP_CONF_IPV6 u16_t id, seqno; + u8_t payload[1]; #else /* !UIP_CONF_IPV6 */ u8_t flags, reserved1, reserved2, reserved3; u8_t icmp6data[16];