63 #if LWIP_IPV4 && LWIP_ICMP 73 #ifdef LWIP_HOOK_FILENAME 74 #include LWIP_HOOK_FILENAME 80 #ifndef LWIP_ICMP_ECHO_CHECK_INPUT_PBUF_LEN 81 #define LWIP_ICMP_ECHO_CHECK_INPUT_PBUF_LEN 1 85 #define ICMP_DEST_UNREACH_DATASIZE 8 87 static void icmp_send_response(
struct pbuf *p, u8_t type, u8_t code);
99 icmp_input(
struct pbuf *p,
struct netif *inp)
106 const struct ip_hdr *iphdr_in;
108 const ip4_addr_t* src;
110 ICMP_STATS_INC(icmp.recv);
111 MIB2_STATS_INC(mib2.icmpinmsgs);
113 iphdr_in = ip4_current_header();
114 hlen = IPH_HL(iphdr_in) * 4;
115 if (hlen < IP_HLEN) {
119 if (p->
len <
sizeof(u16_t)*2) {
126 code = *(((u8_t *)p->
payload)+1);
132 MIB2_STATS_INC(mib2.icmpinechoreps);
135 MIB2_STATS_INC(mib2.icmpinechos);
136 src = ip4_current_dest_addr();
138 if (ip4_addr_ismulticast(ip4_current_dest_addr())) {
139 #if LWIP_MULTICAST_PING 141 src = netif_ip4_addr(inp);
149 #if LWIP_BROADCAST_PING 151 src = netif_ip4_addr(inp);
162 #if CHECKSUM_CHECK_ICMP 163 IF__NETIF_CHECKSUM_ENABLED(inp, NETIF_CHECKSUM_CHECK_ICMP) {
167 ICMP_STATS_INC(icmp.chkerr);
168 MIB2_STATS_INC(mib2.icmpinerrors);
173 #if LWIP_ICMP_ECHO_CHECK_INPUT_PBUF_LEN 191 MEMCPY(r->
payload, iphdr_in, hlen);
194 LWIP_ASSERT(
"icmp_input: moving r->payload to icmp header failed\n", 0);
211 LWIP_ASSERT(
"icmp_input: restoring original p->payload failed\n", 0);
225 ip4_addr_copy(iphdr->src, *src);
226 ip4_addr_copy(iphdr->dest, *ip4_current_src_addr());
227 ICMPH_TYPE_SET(iecho, ICMP_ER);
228 #if CHECKSUM_GEN_ICMP 229 IF__NETIF_CHECKSUM_ENABLED(inp, NETIF_CHECKSUM_GEN_ICMP) {
231 if (iecho->chksum > PP_HTONS(0xffffU - (ICMP_ECHO << 8))) {
232 iecho->chksum += PP_HTONS(ICMP_ECHO << 8) + 1;
234 iecho->chksum += PP_HTONS(ICMP_ECHO << 8);
237 #if LWIP_CHECKSUM_CTRL_PER_NETIF 248 IPH_CHKSUM_SET(iphdr, 0);
250 IF__NETIF_CHECKSUM_ENABLED(inp, NETIF_CHECKSUM_GEN_IP) {
251 IPH_CHKSUM_SET(iphdr, inet_chksum(iphdr, hlen));
255 ICMP_STATS_INC(icmp.xmit);
257 MIB2_STATS_INC(mib2.icmpoutmsgs);
259 MIB2_STATS_INC(mib2.icmpoutechoreps);
262 ret = ip4_output_if(p, src, LWIP_IP_HDRINCL,
270 if (type == ICMP_DUR) {
271 MIB2_STATS_INC(mib2.icmpindestunreachs);
272 }
else if (type == ICMP_TE) {
273 MIB2_STATS_INC(mib2.icmpintimeexcds);
274 }
else if (type == ICMP_PP) {
275 MIB2_STATS_INC(mib2.icmpinparmprobs);
276 }
else if (type == ICMP_SQ) {
277 MIB2_STATS_INC(mib2.icmpinsrcquenchs);
278 }
else if (type == ICMP_RD) {
279 MIB2_STATS_INC(mib2.icmpinredirects);
280 }
else if (type == ICMP_TS) {
281 MIB2_STATS_INC(mib2.icmpintimestamps);
282 }
else if (type == ICMP_TSR) {
283 MIB2_STATS_INC(mib2.icmpintimestampreps);
284 }
else if (type == ICMP_AM) {
285 MIB2_STATS_INC(mib2.icmpinaddrmasks);
286 }
else if (type == ICMP_AMR) {
287 MIB2_STATS_INC(mib2.icmpinaddrmaskreps);
290 (s16_t)type, (s16_t)code));
291 ICMP_STATS_INC(icmp.proterr);
292 ICMP_STATS_INC(icmp.drop);
298 ICMP_STATS_INC(icmp.lenerr);
299 MIB2_STATS_INC(mib2.icmpinerrors);
301 #if LWIP_ICMP_ECHO_CHECK_INPUT_PBUF_LEN || !LWIP_MULTICAST_PING || !LWIP_BROADCAST_PING 304 ICMP_STATS_INC(icmp.err);
305 MIB2_STATS_INC(mib2.icmpinerrors);
322 MIB2_STATS_INC(mib2.icmpoutdestunreachs);
323 icmp_send_response(p, ICMP_DUR, t);
326 #if IP_FORWARD || IP_REASSEMBLY 337 MIB2_STATS_INC(mib2.icmpouttimeexcds);
338 icmp_send_response(p, ICMP_TE, t);
352 icmp_send_response(
struct pbuf *p, u8_t type, u8_t code)
358 ip4_addr_t iphdr_src;
362 MIB2_STATS_INC(mib2.icmpoutmsgs);
369 MIB2_STATS_INC(mib2.icmpouterrors);
372 LWIP_ASSERT(
"check that first pbuf can hold icmp message",
373 (q->
len >= (
sizeof(
struct icmp_echo_hdr) + IP_HLEN + ICMP_DEST_UNREACH_DATASIZE)));
377 ip4_addr_debug_print_val(
ICMP_DEBUG, iphdr->src);
379 ip4_addr_debug_print_val(
ICMP_DEBUG, iphdr->dest);
383 icmphdr->type = type;
384 icmphdr->code = code;
390 IP_HLEN + ICMP_DEST_UNREACH_DATASIZE);
392 ip4_addr_copy(iphdr_src, iphdr->src);
393 #ifdef LWIP_HOOK_IP4_ROUTE_SRC 395 ip4_addr_t iphdr_dst;
396 ip4_addr_copy(iphdr_dst, iphdr->dest);
397 netif = ip4_route_src(&iphdr_src, &iphdr_dst);
400 netif = ip4_route(&iphdr_src);
405 #if CHECKSUM_GEN_ICMP 406 IF__NETIF_CHECKSUM_ENABLED(netif, NETIF_CHECKSUM_GEN_ICMP) {
407 icmphdr->chksum = inet_chksum(icmphdr, q->
len);
410 ICMP_STATS_INC(icmp.xmit);
411 ip4_output_if(q, NULL, &iphdr_src,
ICMP_TTL, 0, IP_PROTO_ICMP, netif);
u8_t pbuf_header(struct pbuf *p, s16_t header_size_increment)
#define ip_current_netif()
err_t pbuf_copy(struct pbuf *p_to, const struct pbuf *p_from)
#define LWIP_DBG_LEVEL_SERIOUS
u16_t inet_chksum_pbuf(struct pbuf *p)
#define LWIP_DEBUGF(debug, message)
struct pbuf * pbuf_alloc(pbuf_layer layer, u16_t length, pbuf_type type)
u8_t pbuf_free(struct pbuf *p)
#define PBUF_LINK_ENCAPSULATION_HLEN