| 1 | |
| 2 | |
| 3 | * NET3: Implementation of the ICMP protocol layer.
|
| 4 | *
|
| 5 | * Alan Cox, <[email protected]>
|
| 6 | *
|
| 7 | * Some of the function names and the icmp unreach table for this
|
| 8 | * module were derived from [icmp.c 1.0.11 06/02/93] by
|
| 9 | * Ross Biro, Fred N. van Kempen, Mark Evans, Alan Cox, Gerhard Koerting.
|
| 10 | * Other than that this module is a complete rewrite.
|
| 11 | *
|
| 12 | * Fixes:
|
| 13 | * Clemens Fruhwirth : introduce global icmp rate limiting
|
| 14 | * with icmp type masking ability instead
|
| 15 | * of broken per type icmp timeouts.
|
| 16 | * Mike Shaver : RFC1122 checks.
|
| 17 | * Alan Cox : Multicast ping reply as self.
|
| 18 | * Alan Cox : Fix atomicity lockup in ip_build_xmit
|
| 19 | * call.
|
| 20 | * Alan Cox : Added 216,128 byte paths to the MTU
|
| 21 | * code.
|
| 22 | * Martin Mares : RFC1812 checks.
|
| 23 | * Martin Mares : Can be configured to follow redirects
|
| 24 | * if acting as a router _without_ a
|
| 25 | * routing protocol (RFC 1812).
|
| 26 | * Martin Mares : Echo requests may be configured to
|
| 27 | * be ignored (RFC 1812).
|
| 28 | * Martin Mares : Limitation of ICMP error message
|
| 29 | * transmit rate (RFC 1812).
|
| 30 | * Martin Mares : TOS and Precedence set correctly
|
| 31 | * (RFC 1812).
|
| 32 | * Martin Mares : Now copying as much data from the
|
| 33 | * original packet as we can without
|
| 34 | * exceeding 576 bytes (RFC 1812).
|
| 35 | * Willy Konynenberg : Transparent proxying support.
|
| 36 | * Keith Owens : RFC1191 correction for 4.2BSD based
|
| 37 | * path MTU bug.
|
| 38 | * Thomas Quinot : ICMP Dest Unreach codes up to 15 are
|
| 39 | * valid (RFC 1812).
|
| 40 | * Andi Kleen : Check all packet lengths properly
|
| 41 | * and moved all kfree_skb() up to
|
| 42 | * icmp_rcv.
|
| 43 | * Andi Kleen : Move the rate limit bookkeeping
|
| 44 | * into the dest entry and use a token
|
| 45 | * bucket filter (thanks to ANK). Make
|
| 46 | * the rates sysctl configurable.
|
| 47 | * Yu Tianli : Fixed two ugly bugs in icmp_send
|
| 48 | * - IP option length was accounted wrongly
|
| 49 | * - ICMP header length was not accounted
|
| 50 | * at all.
|
| 51 | * Tristan Greaves : Added sysctl option to ignore bogus
|
| 52 | * broadcast responses from broken routers.
|
| 53 | *
|
| 54 | * To Fix:
|
| 55 | *
|
| 56 | * - Should use skb_pull() instead of all the manual checking.
|
| 57 | * This would also greatly simply some upper layer error handlers. --AK
|
| 58 |
|
| 59 |
|
| 60 | #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
|
| 61 |
|
| 62 | #include <linux/module.h>
|
| 63 | #include <linux/types.h>
|
| 64 | #include <linux/jiffies.h>
|
| 65 | #include <linux/kernel.h>
|
| 66 | #include <linux/fcntl.h>
|
| 67 | #include <linux/nospec.h>
|
| 68 | #include <linux/socket.h>
|
| 69 | #include <linux/in.h>
|
| 70 | #include <linux/inet.h>
|
| 71 | #include <linux/inetdevice.h>
|
| 72 | #include <linux/netdevice.h>
|
| 73 | #include <linux/string.h>
|
| 74 | #include <linux/netfilter_ipv4.h>
|
| 75 | #include <linux/slab.h>
|
| 76 | #include <net/flow.h>
|
| 77 | #include <net/snmp.h>
|
| 78 | #include <net/ip.h>
|
| 79 | #include <net/route.h>
|
| 80 | #include <net/protocol.h>
|
| 81 | #include <net/icmp.h>
|
| 82 | #include <net/tcp.h>
|
| 83 | #include <net/udp.h>
|
| 84 | #include <net/raw.h>
|
| 85 | #include <net/ping.h>
|
| 86 | #include <linux/skbuff.h>
|
| 87 | #include <net/sock.h>
|
| 88 | #include <linux/errno.h>
|
| 89 | #include <linux/timer.h>
|
| 90 | #include <linux/init.h>
|
| 91 | #include <linux/uaccess.h>
|
| 92 | #include <net/checksum.h>
|
| 93 | #include <net/xfrm.h>
|
| 94 | #include <net/inet_common.h>
|
| 95 | #include <net/ip_fib.h>
|
| 96 | #include <net/l3mdev.h>
|
| 97 | #include <net/addrconf.h>
|
| 98 | #include <net/inet_dscp.h>
|
| 99 | #define CREATE_TRACE_POINTS
|
| 100 | #include <trace/events/icmp.h>
|
| 101 |
|
| 102 | |
| 103 | * Build xmit assembly blocks
|
| 104 |
|
| 105 |
|
| 106 | struct icmp_bxm {
|
| 107 | struct sk_buff *skb;
|
| 108 | int offset;
|
| 109 | int data_len;
|
| 110 |
|
| 111 | struct {
|
| 112 | struct icmphdr icmph;
|
| 113 | __be32 times[3];
|
| 114 | } data;
|
| 115 | int head_len;
|
| 116 |
|
| 117 |
|
| 118 | struct ip_options_rcu replyopts;
|
| 119 | };
|
| 120 |
|
| 121 |
|
| 122 |
|
| 123 |
|
| 124 | const struct icmp_err icmp_err_convert[] = {
|
| 125 | {
|
| 126 | .errno = ENETUNREACH,
|
| 127 | .fatal = 0,
|
| 128 | },
|
| 129 | {
|
| 130 | .errno = EHOSTUNREACH,
|
| 131 | .fatal = 0,
|
| 132 | },
|
| 133 | {
|
| 134 | .errno = ENOPROTOOPT ,
|
| 135 | .fatal = 1,
|
| 136 | },
|
| 137 | {
|
| 138 | .errno = ECONNREFUSED,
|
| 139 | .fatal = 1,
|
| 140 | },
|
| 141 | {
|
| 142 | .errno = EMSGSIZE,
|
| 143 | .fatal = 0,
|
| 144 | },
|
| 145 | {
|
| 146 | .errno = EOPNOTSUPP,
|
| 147 | .fatal = 0,
|
| 148 | },
|
| 149 | {
|
| 150 | .errno = ENETUNREACH,
|
| 151 | .fatal = 1,
|
| 152 | },
|
| 153 | {
|
| 154 | .errno = EHOSTDOWN,
|
| 155 | .fatal = 1,
|
| 156 | },
|
| 157 | {
|
| 158 | .errno = ENONET,
|
| 159 | .fatal = 1,
|
| 160 | },
|
| 161 | {
|
| 162 | .errno = ENETUNREACH,
|
| 163 | .fatal = 1,
|
| 164 | },
|
| 165 | {
|
| 166 | .errno = EHOSTUNREACH,
|
| 167 | .fatal = 1,
|
| 168 | },
|
| 169 | {
|
| 170 | .errno = ENETUNREACH,
|
| 171 | .fatal = 0,
|
| 172 | },
|
| 173 | {
|
| 174 | .errno = EHOSTUNREACH,
|
| 175 | .fatal = 0,
|
| 176 | },
|
| 177 | {
|
| 178 | .errno = EHOSTUNREACH,
|
| 179 | .fatal = 1,
|
| 180 | },
|
| 181 | {
|
| 182 | .errno = EHOSTUNREACH,
|
| 183 | .fatal = 1,
|
| 184 | },
|
| 185 | {
|
| 186 | .errno = EHOSTUNREACH,
|
| 187 | .fatal = 1,
|
| 188 | },
|
| 189 | };
|
| 190 | EXPORT_SYMBOL(icmp_err_convert);
|
| 191 |
|
| 192 | |
| 193 | * ICMP control array. This specifies what to do with each ICMP.
|
| 194 |
|
| 195 |
|
| 196 | struct icmp_control {
|
| 197 | enum skb_drop_reason (*handler)(struct sk_buff *skb);
|
| 198 | short error;
|
| 199 | };
|
| 200 |
|
| 201 | static const struct icmp_control icmp_pointers[NR_ICMP_TYPES+1];
|
| 202 |
|
| 203 | static DEFINE_PER_CPU(struct sock *, ipv4_icmp_sk);
|
| 204 |
|
| 205 |
|
| 206 | static inline struct sock *icmp_xmit_lock(struct net *net)
|
| 207 | {
|
| 208 | struct sock *sk;
|
| 209 |
|
| 210 | sk = this_cpu_read(ipv4_icmp_sk);
|
| 211 |
|
| 212 | if (unlikely(!spin_trylock(&sk->sk_lock.slock))) {
|
| 213 | |
| 214 | * dst_link_failure() for an outgoing ICMP packet.
|
| 215 |
|
| 216 | return NULL;
|
| 217 | }
|
| 218 | sock_net_set(sk, net);
|
| 219 | return sk;
|
| 220 | }
|
| 221 |
|
| 222 | static inline void icmp_xmit_unlock(struct sock *sk)
|
| 223 | {
|
| 224 | sock_net_set(sk, &init_net);
|
| 225 | spin_unlock(&sk->sk_lock.slock);
|
| 226 | }
|
| 227 |
|
| 228 | |
| 229 | * icmp_global_allow - Are we allowed to send one more ICMP message ?
|
| 230 | * @net: network namespace
|
| 231 | *
|
| 232 | * Uses a token bucket to limit our ICMP messages to ~sysctl_icmp_msgs_per_sec.
|
| 233 | * Returns false if we reached the limit and can not send another packet.
|
| 234 | * Works in tandem with icmp_global_consume().
|
| 235 |
|
| 236 | bool icmp_global_allow(struct net *net)
|
| 237 | {
|
| 238 | u32 delta, now, oldstamp;
|
| 239 | int incr, new, old;
|
| 240 |
|
| 241 | |
| 242 | * Then later icmp_global_consume() could consume more credits,
|
| 243 | * this is an acceptable race.
|
| 244 |
|
| 245 | if (atomic_read(&net->ipv4.icmp_global_credit) > 0)
|
| 246 | return true;
|
| 247 |
|
| 248 | now = jiffies;
|
| 249 | oldstamp = READ_ONCE(net->ipv4.icmp_global_stamp);
|
| 250 | delta = min_t(u32, now - oldstamp, HZ);
|
| 251 | if (delta < HZ / 50)
|
| 252 | return false;
|
| 253 |
|
| 254 | incr = READ_ONCE(net->ipv4.sysctl_icmp_msgs_per_sec);
|
| 255 | incr = div_u64((u64)incr * delta, HZ);
|
| 256 | if (!incr)
|
| 257 | return false;
|
| 258 |
|
| 259 | if (cmpxchg(&net->ipv4.icmp_global_stamp, oldstamp, now) == oldstamp) {
|
| 260 | old = atomic_read(&net->ipv4.icmp_global_credit);
|
| 261 | do {
|
| 262 | new = min(old + incr, READ_ONCE(net->ipv4.sysctl_icmp_msgs_burst));
|
| 263 | } while (!atomic_try_cmpxchg(&net->ipv4.icmp_global_credit, &old, new));
|
| 264 | }
|
| 265 | return true;
|
| 266 | }
|
| 267 |
|
| 268 | void icmp_global_consume(struct net *net)
|
| 269 | {
|
| 270 | int credits = get_random_u32_below(3);
|
| 271 |
|
| 272 |
|
| 273 | if (credits)
|
| 274 | atomic_sub(credits, &net->ipv4.icmp_global_credit);
|
| 275 | }
|
| 276 |
|
| 277 | static bool icmpv4_mask_allow(struct net *net, int type, int code)
|
| 278 | {
|
| 279 | if (type > NR_ICMP_TYPES)
|
| 280 | return true;
|
| 281 |
|
| 282 |
|
| 283 | if (type == ICMP_DEST_UNREACH && code == ICMP_FRAG_NEEDED)
|
| 284 | return true;
|
| 285 |
|
| 286 |
|
| 287 | if (!((1 << type) & READ_ONCE(net->ipv4.sysctl_icmp_ratemask)))
|
| 288 | return true;
|
| 289 |
|
| 290 | return false;
|
| 291 | }
|
| 292 |
|
| 293 | static bool icmpv4_global_allow(struct net *net, int type, int code,
|
| 294 | bool *apply_ratelimit)
|
| 295 | {
|
| 296 | if (icmpv4_mask_allow(net, type, code))
|
| 297 | return true;
|
| 298 |
|
| 299 | if (icmp_global_allow(net)) {
|
| 300 | *apply_ratelimit = true;
|
| 301 | return true;
|
| 302 | }
|
| 303 | __ICMP_INC_STATS(net, ICMP_MIB_RATELIMITGLOBAL);
|
| 304 | return false;
|
| 305 | }
|
| 306 |
|
| 307 | |
| 308 | * Send an ICMP frame.
|
| 309 |
|
| 310 |
|
| 311 | static bool icmpv4_xrlim_allow(struct net *net, struct rtable *rt,
|
| 312 | struct flowi4 *fl4, int type, int code,
|
| 313 | bool apply_ratelimit)
|
| 314 | {
|
| 315 | struct dst_entry *dst = &rt->dst;
|
| 316 | struct inet_peer *peer;
|
| 317 | struct net_device *dev;
|
| 318 | int peer_timeout;
|
| 319 | bool rc = true;
|
| 320 |
|
| 321 | if (!apply_ratelimit)
|
| 322 | return true;
|
| 323 |
|
| 324 | peer_timeout = READ_ONCE(net->ipv4.sysctl_icmp_ratelimit);
|
| 325 | if (!peer_timeout)
|
| 326 | goto out;
|
| 327 |
|
| 328 |
|
| 329 | rcu_read_lock();
|
| 330 | dev = dst_dev_rcu(dst);
|
| 331 | if (dev && (dev->flags & IFF_LOOPBACK))
|
| 332 | goto out_unlock;
|
| 333 |
|
| 334 | peer = inet_getpeer_v4(net->ipv4.peers, fl4->daddr,
|
| 335 | l3mdev_master_ifindex_rcu(dev));
|
| 336 | rc = inet_peer_xrlim_allow(peer, peer_timeout);
|
| 337 |
|
| 338 | out_unlock:
|
| 339 | rcu_read_unlock();
|
| 340 | out:
|
| 341 | if (!rc)
|
| 342 | __ICMP_INC_STATS(net, ICMP_MIB_RATELIMITHOST);
|
| 343 | else
|
| 344 | icmp_global_consume(net);
|
| 345 | return rc;
|
| 346 | }
|
| 347 |
|
| 348 | |
| 349 | * Maintain the counters used in the SNMP statistics for outgoing ICMP
|
| 350 |
|
| 351 | void icmp_out_count(struct net *net, unsigned char type)
|
| 352 | {
|
| 353 | ICMPMSGOUT_INC_STATS(net, type);
|
| 354 | ICMP_INC_STATS(net, ICMP_MIB_OUTMSGS);
|
| 355 | }
|
| 356 |
|
| 357 | |
| 358 | * Checksum each fragment, and on the first include the headers and final
|
| 359 | * checksum.
|
| 360 |
|
| 361 | static int icmp_glue_bits(void *from, char *to, int offset, int len, int odd,
|
| 362 | struct sk_buff *skb)
|
| 363 | {
|
| 364 | DEFINE_RAW_FLEX(struct icmp_bxm, icmp_param, replyopts.opt.__data,
|
| 365 | IP_OPTIONS_DATA_FIXED_SIZE);
|
| 366 | __wsum csum;
|
| 367 |
|
| 368 | icmp_param = from;
|
| 369 |
|
| 370 | csum = skb_copy_and_csum_bits(icmp_param->skb,
|
| 371 | icmp_param->offset + offset,
|
| 372 | to, len);
|
| 373 |
|
| 374 | skb->csum = csum_block_add(skb->csum, csum, odd);
|
| 375 | if (icmp_param->data.icmph.type <= NR_ICMP_TYPES &&
|
| 376 | icmp_pointers[array_index_nospec(icmp_param->data.icmph.type,
|
| 377 | NR_ICMP_TYPES + 1)].error)
|
| 378 | nf_ct_attach(skb, icmp_param->skb);
|
| 379 | return 0;
|
| 380 | }
|
| 381 |
|
| 382 | static void icmp_push_reply(struct sock *sk,
|
| 383 | struct icmp_bxm *icmp_param,
|
| 384 | struct flowi4 *fl4,
|
| 385 | struct ipcm_cookie *ipc, struct rtable **rt)
|
| 386 | {
|
| 387 | struct sk_buff *skb;
|
| 388 |
|
| 389 | if (ip_append_data(sk, fl4, icmp_glue_bits, icmp_param,
|
| 390 | icmp_param->data_len+icmp_param->head_len,
|
| 391 | icmp_param->head_len,
|
| 392 | ipc, rt, MSG_DONTWAIT) < 0) {
|
| 393 | __ICMP_INC_STATS(sock_net(sk), ICMP_MIB_OUTERRORS);
|
| 394 | ip_flush_pending_frames(sk);
|
| 395 | } else if ((skb = skb_peek(&sk->sk_write_queue)) != NULL) {
|
| 396 | struct icmphdr *icmph = icmp_hdr(skb);
|
| 397 | __wsum csum;
|
| 398 | struct sk_buff *skb1;
|
| 399 |
|
| 400 | csum = csum_partial_copy_nocheck((void *)&icmp_param->data,
|
| 401 | (char *)icmph,
|
| 402 | icmp_param->head_len);
|
| 403 | skb_queue_walk(&sk->sk_write_queue, skb1) {
|
| 404 | csum = csum_add(csum, skb1->csum);
|
| 405 | }
|
| 406 | icmph->checksum = csum_fold(csum);
|
| 407 | skb->ip_summed = CHECKSUM_NONE;
|
| 408 | ip_push_pending_frames(sk, fl4);
|
| 409 | }
|
| 410 | }
|
| 411 |
|
| 412 | |
| 413 | * Driving logic for building and sending ICMP messages.
|
| 414 |
|
| 415 |
|
| 416 | static void icmp_reply(struct icmp_bxm *icmp_param, struct sk_buff *skb)
|
| 417 | {
|
| 418 | struct rtable *rt = skb_rtable(skb);
|
| 419 | struct net *net = dev_net_rcu(rt->dst.dev);
|
| 420 | bool apply_ratelimit = false;
|
| 421 | struct ipcm_cookie ipc;
|
| 422 | struct flowi4 fl4;
|
| 423 | struct sock *sk;
|
| 424 | __be32 daddr, saddr;
|
| 425 | u32 mark = IP4_REPLY_MARK(net, skb->mark);
|
| 426 | int type = icmp_param->data.icmph.type;
|
| 427 | int code = icmp_param->data.icmph.code;
|
| 428 |
|
| 429 | if (ip_options_echo(net, &icmp_param->replyopts.opt, skb))
|
| 430 | return;
|
| 431 |
|
| 432 |
|
| 433 | local_bh_disable();
|
| 434 |
|
| 435 |
|
| 436 | if (!icmpv4_global_allow(net, type, code, &apply_ratelimit))
|
| 437 | goto out_bh_enable;
|
| 438 |
|
| 439 | sk = icmp_xmit_lock(net);
|
| 440 | if (!sk)
|
| 441 | goto out_bh_enable;
|
| 442 |
|
| 443 | icmp_param->data.icmph.checksum = 0;
|
| 444 |
|
| 445 | ipcm_init(&ipc);
|
| 446 | ipc.tos = ip_hdr(skb)->tos;
|
| 447 | ipc.sockc.mark = mark;
|
| 448 | daddr = ipc.addr = ip_hdr(skb)->saddr;
|
| 449 | saddr = fib_compute_spec_dst(skb);
|
| 450 |
|
| 451 | if (icmp_param->replyopts.opt.optlen) {
|
| 452 | ipc.opt = &icmp_param->replyopts;
|
| 453 | if (ipc.opt->opt.srr)
|
| 454 | daddr = icmp_param->replyopts.opt.faddr;
|
| 455 | }
|
| 456 | memset(&fl4, 0, sizeof(fl4));
|
| 457 | fl4.daddr = daddr;
|
| 458 | fl4.saddr = saddr;
|
| 459 | fl4.flowi4_mark = mark;
|
| 460 | fl4.flowi4_uid = sock_net_uid(net, NULL);
|
| 461 | fl4.flowi4_dscp = ip4h_dscp(ip_hdr(skb));
|
| 462 | fl4.flowi4_proto = IPPROTO_ICMP;
|
| 463 | fl4.flowi4_oif = l3mdev_master_ifindex(skb->dev);
|
| 464 | security_skb_classify_flow(skb, flowi4_to_flowi_common(&fl4));
|
| 465 | rt = ip_route_output_key(net, &fl4);
|
| 466 | if (IS_ERR(rt))
|
| 467 | goto out_unlock;
|
| 468 | if (icmpv4_xrlim_allow(net, rt, &fl4, type, code, apply_ratelimit))
|
| 469 | icmp_push_reply(sk, icmp_param, &fl4, &ipc, &rt);
|
| 470 | ip_rt_put(rt);
|
| 471 | out_unlock:
|
| 472 | icmp_xmit_unlock(sk);
|
| 473 | out_bh_enable:
|
| 474 | local_bh_enable();
|
| 475 | }
|
| 476 |
|
| 477 | |
| 478 | * The device used for looking up which routing table to use for sending an ICMP
|
| 479 | * error is preferably the source whenever it is set, which should ensure the
|
| 480 | * icmp error can be sent to the source host, else lookup using the routing
|
| 481 | * table of the destination device, else use the main routing table (index 0).
|
| 482 |
|
| 483 | static struct net_device *icmp_get_route_lookup_dev(struct sk_buff *skb)
|
| 484 | {
|
| 485 | struct net_device *dev = skb->dev;
|
| 486 | const struct dst_entry *dst;
|
| 487 |
|
| 488 | if (dev)
|
| 489 | return dev;
|
| 490 | dst = skb_dst(skb);
|
| 491 | return dst ? dst_dev(dst) : NULL;
|
| 492 | }
|
| 493 |
|
| 494 | static struct rtable *icmp_route_lookup(struct net *net, struct flowi4 *fl4,
|
| 495 | struct sk_buff *skb_in,
|
| 496 | const struct iphdr *iph, __be32 saddr,
|
| 497 | dscp_t dscp, u32 mark, int type,
|
| 498 | int code, struct icmp_bxm *param)
|
| 499 | {
|
| 500 | struct net_device *route_lookup_dev;
|
| 501 | struct dst_entry *dst, *dst2;
|
| 502 | struct rtable *rt, *rt2;
|
| 503 | struct flowi4 fl4_dec;
|
| 504 | int err;
|
| 505 |
|
| 506 | memset(fl4, 0, sizeof(*fl4));
|
| 507 | fl4->daddr = (param->replyopts.opt.srr ?
|
| 508 | param->replyopts.opt.faddr : iph->saddr);
|
| 509 | fl4->saddr = saddr;
|
| 510 | fl4->flowi4_mark = mark;
|
| 511 | fl4->flowi4_uid = sock_net_uid(net, NULL);
|
| 512 | fl4->flowi4_dscp = dscp;
|
| 513 | fl4->flowi4_proto = IPPROTO_ICMP;
|
| 514 | fl4->fl4_icmp_type = type;
|
| 515 | fl4->fl4_icmp_code = code;
|
| 516 | route_lookup_dev = icmp_get_route_lookup_dev(skb_in);
|
| 517 | fl4->flowi4_oif = l3mdev_master_ifindex(route_lookup_dev);
|
| 518 |
|
| 519 | security_skb_classify_flow(skb_in, flowi4_to_flowi_common(fl4));
|
| 520 | rt = ip_route_output_key_hash(net, fl4, skb_in);
|
| 521 | if (IS_ERR(rt))
|
| 522 | return rt;
|
| 523 |
|
| 524 |
|
| 525 | rt2 = rt;
|
| 526 |
|
| 527 | dst = xfrm_lookup(net, &rt->dst,
|
| 528 | flowi4_to_flowi(fl4), NULL, 0);
|
| 529 | rt = dst_rtable(dst);
|
| 530 | if (!IS_ERR(dst)) {
|
| 531 | if (rt != rt2)
|
| 532 | return rt;
|
| 533 | if (inet_addr_type_dev_table(net, route_lookup_dev,
|
| 534 | fl4->daddr) == RTN_LOCAL)
|
| 535 | return rt;
|
| 536 | } else if (PTR_ERR(dst) == -EPERM) {
|
| 537 | rt = NULL;
|
| 538 | } else {
|
| 539 | return rt;
|
| 540 | }
|
| 541 | err = xfrm_decode_session_reverse(net, skb_in, flowi4_to_flowi(&fl4_dec), AF_INET);
|
| 542 | if (err)
|
| 543 | goto relookup_failed;
|
| 544 |
|
| 545 | if (inet_addr_type_dev_table(net, route_lookup_dev,
|
| 546 | fl4_dec.saddr) == RTN_LOCAL) {
|
| 547 | rt2 = __ip_route_output_key(net, &fl4_dec);
|
| 548 | if (IS_ERR(rt2))
|
| 549 | err = PTR_ERR(rt2);
|
| 550 | } else {
|
| 551 | struct flowi4 fl4_2 = fl4_dec;
|
| 552 | unsigned long orefdst;
|
| 553 |
|
| 554 | swap(fl4_2.daddr, fl4_2.saddr);
|
| 555 | switch (fl4_2.flowi4_proto) {
|
| 556 | case IPPROTO_TCP:
|
| 557 | case IPPROTO_UDP:
|
| 558 | case IPPROTO_SCTP:
|
| 559 | case IPPROTO_DCCP:
|
| 560 | swap(fl4_2.fl4_sport, fl4_2.fl4_dport);
|
| 561 | break;
|
| 562 | }
|
| 563 |
|
| 564 | fl4_2.flowi4_oif = l3mdev_master_ifindex(route_lookup_dev);
|
| 565 | fl4_2.flowi4_flags |= FLOWI_FLAG_ANYSRC;
|
| 566 |
|
| 567 | rt2 = __ip_route_output_key(net, &fl4_2);
|
| 568 | if (IS_ERR(rt2)) {
|
| 569 | err = PTR_ERR(rt2);
|
| 570 | goto relookup_failed;
|
| 571 | }
|
| 572 |
|
| 573 | orefdst = skb_dstref_steal(skb_in);
|
| 574 | err = ip_route_input(skb_in, fl4_dec.daddr, fl4_dec.saddr,
|
| 575 | dscp, rt2->dst.dev) ? -EINVAL : 0;
|
| 576 |
|
| 577 | dst_release(&rt2->dst);
|
| 578 | rt2 = skb_rtable(skb_in);
|
| 579 |
|
| 580 | skb_dstref_steal(skb_in);
|
| 581 | skb_dstref_restore(skb_in, orefdst);
|
| 582 |
|
| 583 | |
| 584 | * fl4_dec.daddr is not expected to be local here, but it can be
|
| 585 | * added to an interface concurrently, in which case
|
| 586 | * ip_route_input() returns a LOCAL route. It can also fail to
|
| 587 | * build a forwarding route towards fl4_dec.daddr, for example,
|
| 588 | * when forwarding is disabled, and return an UNREACHABLE route.
|
| 589 | * Both cases will result in a route with dst.output=ip_rt_bug,
|
| 590 | * which must not be used for output.
|
| 591 |
|
| 592 | if (!err && rt2 && rt2->rt_type == RTN_LOCAL)
|
| 593 | net_warn_ratelimited("detected local route for %pI4 during ICMP sending, src %pI4\n",
|
| 594 | &fl4_dec.daddr, &fl4_dec.saddr);
|
| 595 | if (!err && rt2 &&
|
| 596 | (rt2->rt_type == RTN_LOCAL || rt2->rt_type == RTN_UNREACHABLE)) {
|
| 597 | dst_release(&rt2->dst);
|
| 598 | err = -EINVAL;
|
| 599 | }
|
| 600 | }
|
| 601 |
|
| 602 | if (err)
|
| 603 | goto relookup_failed;
|
| 604 |
|
| 605 | dst2 = xfrm_lookup(net, &rt2->dst, flowi4_to_flowi(&fl4_dec), NULL,
|
| 606 | XFRM_LOOKUP_ICMP);
|
| 607 | rt2 = dst_rtable(dst2);
|
| 608 | if (!IS_ERR(dst2)) {
|
| 609 | dst_release(&rt->dst);
|
| 610 | rt = rt2;
|
| 611 | } else if (PTR_ERR(dst2) == -EPERM) {
|
| 612 | if (rt)
|
| 613 | dst_release(&rt->dst);
|
| 614 | return rt2;
|
| 615 | } else {
|
| 616 | err = PTR_ERR(dst2);
|
| 617 | goto relookup_failed;
|
| 618 | }
|
| 619 | return rt;
|
| 620 |
|
| 621 | relookup_failed:
|
| 622 | if (rt)
|
| 623 | return rt;
|
| 624 | return ERR_PTR(err);
|
| 625 | }
|
| 626 |
|
| 627 | struct icmp_ext_iio_addr4_subobj {
|
| 628 | __be16 afi;
|
| 629 | __be16 reserved;
|
| 630 | __be32 addr4;
|
| 631 | };
|
| 632 |
|
| 633 | static unsigned int icmp_ext_iio_len(void)
|
| 634 | {
|
| 635 | return sizeof(struct icmp_extobj_hdr) +
|
| 636 |
|
| 637 | sizeof(__be32) +
|
| 638 |
|
| 639 | sizeof(struct icmp_ext_iio_addr4_subobj) +
|
| 640 | |
| 641 | * bytes.
|
| 642 |
|
| 643 | ALIGN(sizeof(struct icmp_ext_iio_name_subobj), 4) +
|
| 644 |
|
| 645 | sizeof(__be32);
|
| 646 | }
|
| 647 |
|
| 648 | static unsigned int icmp_ext_max_len(u8 ext_objs)
|
| 649 | {
|
| 650 | unsigned int ext_max_len;
|
| 651 |
|
| 652 | ext_max_len = sizeof(struct icmp_ext_hdr);
|
| 653 |
|
| 654 | if (ext_objs & BIT(ICMP_ERR_EXT_IIO_IIF))
|
| 655 | ext_max_len += icmp_ext_iio_len();
|
| 656 |
|
| 657 | return ext_max_len;
|
| 658 | }
|
| 659 |
|
| 660 | static __be32 icmp_ext_iio_addr4_find(const struct net_device *dev)
|
| 661 | {
|
| 662 | struct in_device *in_dev;
|
| 663 | struct in_ifaddr *ifa;
|
| 664 |
|
| 665 | in_dev = __in_dev_get_rcu(dev);
|
| 666 | if (!in_dev)
|
| 667 | return 0;
|
| 668 |
|
| 669 | |
| 670 | * it makes sense to choose a global unicast address.
|
| 671 |
|
| 672 | in_dev_for_each_ifa_rcu(ifa, in_dev) {
|
| 673 | if (READ_ONCE(ifa->ifa_flags) & IFA_F_SECONDARY)
|
| 674 | continue;
|
| 675 | if (ifa->ifa_scope != RT_SCOPE_UNIVERSE ||
|
| 676 | ipv4_is_multicast(ifa->ifa_address))
|
| 677 | continue;
|
| 678 | return ifa->ifa_address;
|
| 679 | }
|
| 680 |
|
| 681 | return 0;
|
| 682 | }
|
| 683 |
|
| 684 | static void icmp_ext_iio_iif_append(struct net *net, struct sk_buff *skb,
|
| 685 | int iif)
|
| 686 | {
|
| 687 | struct icmp_ext_iio_name_subobj *name_subobj;
|
| 688 | struct icmp_extobj_hdr *objh;
|
| 689 | struct net_device *dev;
|
| 690 | __be32 data;
|
| 691 |
|
| 692 | if (!iif)
|
| 693 | return;
|
| 694 |
|
| 695 |
|
| 696 | objh = skb_put(skb, sizeof(*objh));
|
| 697 | objh->class_num = ICMP_EXT_OBJ_CLASS_IIO;
|
| 698 | objh->class_type = ICMP_EXT_CTYPE_IIO_ROLE(ICMP_EXT_CTYPE_IIO_ROLE_IIF);
|
| 699 |
|
| 700 | data = htonl(iif);
|
| 701 | skb_put_data(skb, &data, sizeof(__be32));
|
| 702 | objh->class_type |= ICMP_EXT_CTYPE_IIO_IFINDEX;
|
| 703 |
|
| 704 | rcu_read_lock();
|
| 705 |
|
| 706 | dev = dev_get_by_index_rcu(net, iif);
|
| 707 | if (!dev)
|
| 708 | goto out;
|
| 709 |
|
| 710 | data = icmp_ext_iio_addr4_find(dev);
|
| 711 | if (data) {
|
| 712 | struct icmp_ext_iio_addr4_subobj *addr4_subobj;
|
| 713 |
|
| 714 | addr4_subobj = skb_put_zero(skb, sizeof(*addr4_subobj));
|
| 715 | addr4_subobj->afi = htons(ICMP_AFI_IP);
|
| 716 | addr4_subobj->addr4 = data;
|
| 717 | objh->class_type |= ICMP_EXT_CTYPE_IIO_IPADDR;
|
| 718 | }
|
| 719 |
|
| 720 | name_subobj = skb_put_zero(skb, ALIGN(sizeof(*name_subobj), 4));
|
| 721 | name_subobj->len = ALIGN(sizeof(*name_subobj), 4);
|
| 722 | netdev_copy_name(dev, name_subobj->name);
|
| 723 | objh->class_type |= ICMP_EXT_CTYPE_IIO_NAME;
|
| 724 |
|
| 725 | data = htonl(READ_ONCE(dev->mtu));
|
| 726 | skb_put_data(skb, &data, sizeof(__be32));
|
| 727 | objh->class_type |= ICMP_EXT_CTYPE_IIO_MTU;
|
| 728 |
|
| 729 | out:
|
| 730 | rcu_read_unlock();
|
| 731 | objh->length = htons(skb_tail_pointer(skb) - (unsigned char *)objh);
|
| 732 | }
|
| 733 |
|
| 734 | static void icmp_ext_objs_append(struct net *net, struct sk_buff *skb,
|
| 735 | u8 ext_objs, int iif)
|
| 736 | {
|
| 737 | if (ext_objs & BIT(ICMP_ERR_EXT_IIO_IIF))
|
| 738 | icmp_ext_iio_iif_append(net, skb, iif);
|
| 739 | }
|
| 740 |
|
| 741 | static struct sk_buff *
|
| 742 | icmp_ext_append(struct net *net, struct sk_buff *skb_in, struct icmphdr *icmph,
|
| 743 | unsigned int room, int iif)
|
| 744 | {
|
| 745 | unsigned int payload_len, ext_max_len, ext_len;
|
| 746 | struct icmp_ext_hdr *ext_hdr;
|
| 747 | struct sk_buff *skb;
|
| 748 | u8 ext_objs;
|
| 749 | int nhoff;
|
| 750 |
|
| 751 | switch (icmph->type) {
|
| 752 | case ICMP_DEST_UNREACH:
|
| 753 | case ICMP_TIME_EXCEEDED:
|
| 754 | case ICMP_PARAMETERPROB:
|
| 755 | break;
|
| 756 | default:
|
| 757 | return NULL;
|
| 758 | }
|
| 759 |
|
| 760 | ext_objs = READ_ONCE(net->ipv4.sysctl_icmp_errors_extension_mask);
|
| 761 | if (!ext_objs)
|
| 762 | return NULL;
|
| 763 |
|
| 764 | ext_max_len = icmp_ext_max_len(ext_objs);
|
| 765 | if (ICMP_EXT_ORIG_DGRAM_MIN_LEN + ext_max_len > room)
|
| 766 | return NULL;
|
| 767 |
|
| 768 | skb = skb_clone(skb_in, GFP_ATOMIC);
|
| 769 | if (!skb)
|
| 770 | return NULL;
|
| 771 |
|
| 772 | nhoff = skb_network_offset(skb);
|
| 773 | payload_len = min(skb->len - nhoff, ICMP_EXT_ORIG_DGRAM_MIN_LEN);
|
| 774 |
|
| 775 | if (!pskb_network_may_pull(skb, payload_len))
|
| 776 | goto free_skb;
|
| 777 |
|
| 778 | if (pskb_trim(skb, nhoff + ICMP_EXT_ORIG_DGRAM_MIN_LEN) ||
|
| 779 | __skb_put_padto(skb, nhoff + ICMP_EXT_ORIG_DGRAM_MIN_LEN, false))
|
| 780 | goto free_skb;
|
| 781 |
|
| 782 | if (pskb_expand_head(skb, 0, ext_max_len, GFP_ATOMIC))
|
| 783 | goto free_skb;
|
| 784 |
|
| 785 | ext_hdr = skb_put_zero(skb, sizeof(*ext_hdr));
|
| 786 | ext_hdr->version = ICMP_EXT_VERSION_2;
|
| 787 |
|
| 788 | icmp_ext_objs_append(net, skb, ext_objs, iif);
|
| 789 |
|
| 790 |
|
| 791 | ext_len = skb_tail_pointer(skb) - (unsigned char *)ext_hdr;
|
| 792 | if (ext_len == sizeof(*ext_hdr))
|
| 793 | goto free_skb;
|
| 794 |
|
| 795 | ext_hdr->checksum = ip_compute_csum(ext_hdr, ext_len);
|
| 796 |
|
| 797 | icmph->un.reserved[1] = ICMP_EXT_ORIG_DGRAM_MIN_LEN / sizeof(u32);
|
| 798 |
|
| 799 | return skb;
|
| 800 |
|
| 801 | free_skb:
|
| 802 | consume_skb(skb);
|
| 803 | return NULL;
|
| 804 | }
|
| 805 |
|
| 806 | |
| 807 | * Send an ICMP message in response to a situation
|
| 808 | *
|
| 809 | * RFC 1122: 3.2.2 MUST send at least the IP header and 8 bytes of header.
|
| 810 | * MAY send more (we do).
|
| 811 | * MUST NOT change this header information.
|
| 812 | * MUST NOT reply to a multicast/broadcast IP address.
|
| 813 | * MUST NOT reply to a multicast/broadcast MAC address.
|
| 814 | * MUST reply to only the first fragment.
|
| 815 |
|
| 816 |
|
| 817 | void __icmp_send(struct sk_buff *skb_in, int type, int code, __be32 info,
|
| 818 | const struct inet_skb_parm *parm)
|
| 819 | {
|
| 820 | DEFINE_RAW_FLEX(struct icmp_bxm, icmp_param, replyopts.opt.__data,
|
| 821 | IP_OPTIONS_DATA_FIXED_SIZE);
|
| 822 | struct iphdr *iph;
|
| 823 | int room;
|
| 824 | struct rtable *rt = skb_rtable(skb_in);
|
| 825 | bool apply_ratelimit = false;
|
| 826 | struct sk_buff *ext_skb;
|
| 827 | struct ipcm_cookie ipc;
|
| 828 | struct flowi4 fl4;
|
| 829 | __be32 saddr;
|
| 830 | u8 tos;
|
| 831 | u32 mark;
|
| 832 | struct net *net;
|
| 833 | struct sock *sk;
|
| 834 |
|
| 835 | if (!rt)
|
| 836 | return;
|
| 837 |
|
| 838 | rcu_read_lock();
|
| 839 |
|
| 840 | if (rt->dst.dev)
|
| 841 | net = dev_net_rcu(rt->dst.dev);
|
| 842 | else if (skb_in->dev)
|
| 843 | net = dev_net_rcu(skb_in->dev);
|
| 844 | else
|
| 845 | goto out;
|
| 846 |
|
| 847 | |
| 848 | * Find the original header. It is expected to be valid, of course.
|
| 849 | * Check this, icmp_send is called from the most obscure devices
|
| 850 | * sometimes.
|
| 851 |
|
| 852 | iph = ip_hdr(skb_in);
|
| 853 |
|
| 854 | if ((u8 *)iph < skb_in->head ||
|
| 855 | (skb_network_header(skb_in) + sizeof(*iph)) >
|
| 856 | skb_tail_pointer(skb_in))
|
| 857 | goto out;
|
| 858 |
|
| 859 | |
| 860 | * No replies to physical multicast/broadcast
|
| 861 |
|
| 862 | if (skb_in->pkt_type != PACKET_HOST)
|
| 863 | goto out;
|
| 864 |
|
| 865 | |
| 866 | * Now check at the protocol level
|
| 867 |
|
| 868 | if (rt->rt_flags & (RTCF_BROADCAST | RTCF_MULTICAST))
|
| 869 | goto out;
|
| 870 |
|
| 871 | |
| 872 | * Only reply to fragment 0. We byte re-order the constant
|
| 873 | * mask for efficiency.
|
| 874 |
|
| 875 | if (iph->frag_off & htons(IP_OFFSET))
|
| 876 | goto out;
|
| 877 |
|
| 878 | |
| 879 | * If we send an ICMP error to an ICMP error a mess would result..
|
| 880 |
|
| 881 | if (icmp_pointers[type].error) {
|
| 882 | |
| 883 | * We are an error, check if we are replying to an
|
| 884 | * ICMP error
|
| 885 |
|
| 886 | if (iph->protocol == IPPROTO_ICMP) {
|
| 887 | u8 _inner_type, *itp;
|
| 888 |
|
| 889 | itp = skb_header_pointer(skb_in,
|
| 890 | skb_network_header(skb_in) +
|
| 891 | (iph->ihl << 2) +
|
| 892 | offsetof(struct icmphdr,
|
| 893 | type) -
|
| 894 | skb_in->data,
|
| 895 | sizeof(_inner_type),
|
| 896 | &_inner_type);
|
| 897 | if (!itp)
|
| 898 | goto out;
|
| 899 |
|
| 900 | |
| 901 | * Assume any unknown ICMP type is an error. This
|
| 902 | * isn't specified by the RFC, but think about it..
|
| 903 |
|
| 904 | if (*itp > NR_ICMP_TYPES ||
|
| 905 | icmp_pointers[*itp].error)
|
| 906 | goto out;
|
| 907 | }
|
| 908 | }
|
| 909 |
|
| 910 |
|
| 911 | local_bh_disable();
|
| 912 |
|
| 913 | |
| 914 | * incoming dev is loopback. If outgoing dev change to not be
|
| 915 | * loopback, then peer ratelimit still work (in icmpv4_xrlim_allow)
|
| 916 |
|
| 917 | if (!(skb_in->dev && (skb_in->dev->flags&IFF_LOOPBACK)) &&
|
| 918 | !icmpv4_global_allow(net, type, code, &apply_ratelimit))
|
| 919 | goto out_bh_enable;
|
| 920 |
|
| 921 | sk = icmp_xmit_lock(net);
|
| 922 | if (!sk)
|
| 923 | goto out_bh_enable;
|
| 924 |
|
| 925 | |
| 926 | * Construct source address and options.
|
| 927 |
|
| 928 |
|
| 929 | saddr = iph->daddr;
|
| 930 | if (!(rt->rt_flags & RTCF_LOCAL)) {
|
| 931 | struct net_device *dev = NULL;
|
| 932 |
|
| 933 | rcu_read_lock();
|
| 934 | if (rt_is_input_route(rt) &&
|
| 935 | READ_ONCE(net->ipv4.sysctl_icmp_errors_use_inbound_ifaddr))
|
| 936 | dev = dev_get_by_index_rcu(net, parm->iif ? parm->iif :
|
| 937 | inet_iif(skb_in));
|
| 938 |
|
| 939 | if (dev)
|
| 940 | saddr = inet_select_addr(dev, iph->saddr,
|
| 941 | RT_SCOPE_LINK);
|
| 942 | else
|
| 943 | saddr = 0;
|
| 944 | rcu_read_unlock();
|
| 945 | }
|
| 946 |
|
| 947 | tos = icmp_pointers[type].error ? (RT_TOS(iph->tos) |
|
| 948 | IPTOS_PREC_INTERNETCONTROL) :
|
| 949 | iph->tos;
|
| 950 | mark = IP4_REPLY_MARK(net, skb_in->mark);
|
| 951 |
|
| 952 | if (__ip_options_echo(net, &icmp_param->replyopts.opt, skb_in,
|
| 953 | &parm->opt))
|
| 954 | goto out_unlock;
|
| 955 |
|
| 956 |
|
| 957 | |
| 958 | * Prepare data for ICMP header.
|
| 959 |
|
| 960 |
|
| 961 | icmp_param->data.icmph.type = type;
|
| 962 | icmp_param->data.icmph.code = code;
|
| 963 | icmp_param->data.icmph.un.gateway = info;
|
| 964 | icmp_param->data.icmph.checksum = 0;
|
| 965 | icmp_param->skb = skb_in;
|
| 966 | icmp_param->offset = skb_network_offset(skb_in);
|
| 967 | ipcm_init(&ipc);
|
| 968 | ipc.tos = tos;
|
| 969 | ipc.addr = iph->saddr;
|
| 970 | ipc.opt = &icmp_param->replyopts;
|
| 971 | ipc.sockc.mark = mark;
|
| 972 |
|
| 973 | rt = icmp_route_lookup(net, &fl4, skb_in, iph, saddr,
|
| 974 | inet_dsfield_to_dscp(tos), mark, type, code,
|
| 975 | icmp_param);
|
| 976 | if (IS_ERR(rt))
|
| 977 | goto out_unlock;
|
| 978 |
|
| 979 | if (rt->rt_flags & (RTCF_BROADCAST | RTCF_MULTICAST))
|
| 980 | goto ende;
|
| 981 |
|
| 982 |
|
| 983 | if (!icmpv4_xrlim_allow(net, rt, &fl4, type, code, apply_ratelimit))
|
| 984 | goto ende;
|
| 985 |
|
| 986 |
|
| 987 |
|
| 988 | room = dst4_mtu(&rt->dst);
|
| 989 | if (room > 576)
|
| 990 | room = 576;
|
| 991 | room -= sizeof(struct iphdr) + icmp_param->replyopts.opt.optlen;
|
| 992 | room -= sizeof(struct icmphdr);
|
| 993 | |
| 994 | * IP network header for this message to make any sense.
|
| 995 |
|
| 996 | if (room <= (int)sizeof(struct iphdr))
|
| 997 | goto ende;
|
| 998 |
|
| 999 | ext_skb = icmp_ext_append(net, skb_in, &icmp_param->data.icmph, room,
|
| 1000 | parm->iif);
|
| 1001 | if (ext_skb)
|
| 1002 | icmp_param->skb = ext_skb;
|
| 1003 |
|
| 1004 | icmp_param->data_len = icmp_param->skb->len - icmp_param->offset;
|
| 1005 | if (icmp_param->data_len > room)
|
| 1006 | icmp_param->data_len = room;
|
| 1007 | icmp_param->head_len = sizeof(struct icmphdr);
|
| 1008 |
|
| 1009 | |
| 1010 | * dummy address instead of sending out a packet with a source address
|
| 1011 | * of 0.0.0.0
|
| 1012 |
|
| 1013 | if (!fl4.saddr)
|
| 1014 | fl4.saddr = htonl(INADDR_DUMMY);
|
| 1015 |
|
| 1016 | trace_icmp_send(skb_in, type, code);
|
| 1017 |
|
| 1018 | icmp_push_reply(sk, icmp_param, &fl4, &ipc, &rt);
|
| 1019 |
|
| 1020 | if (ext_skb)
|
| 1021 | consume_skb(ext_skb);
|
| 1022 | ende:
|
| 1023 | ip_rt_put(rt);
|
| 1024 | out_unlock:
|
| 1025 | icmp_xmit_unlock(sk);
|
| 1026 | out_bh_enable:
|
| 1027 | local_bh_enable();
|
| 1028 | out:
|
| 1029 | rcu_read_unlock();
|
| 1030 | }
|
| 1031 | EXPORT_SYMBOL(__icmp_send);
|
| 1032 |
|
| 1033 | #if IS_ENABLED(CONFIG_NF_NAT)
|
| 1034 | #include <net/netfilter/nf_conntrack.h>
|
| 1035 | void icmp_ndo_send(struct sk_buff *skb_in, int type, int code, __be32 info)
|
| 1036 | {
|
| 1037 | struct sk_buff *cloned_skb = NULL;
|
| 1038 | enum ip_conntrack_info ctinfo;
|
| 1039 | enum ip_conntrack_dir dir;
|
| 1040 | struct inet_skb_parm parm;
|
| 1041 | struct nf_conn *ct;
|
| 1042 | __be32 orig_ip;
|
| 1043 |
|
| 1044 | memset(&parm, 0, sizeof(parm));
|
| 1045 | ct = nf_ct_get(skb_in, &ctinfo);
|
| 1046 | if (!ct || !(READ_ONCE(ct->status) & IPS_NAT_MASK)) {
|
| 1047 | __icmp_send(skb_in, type, code, info, &parm);
|
| 1048 | return;
|
| 1049 | }
|
| 1050 |
|
| 1051 | if (skb_shared(skb_in))
|
| 1052 | skb_in = cloned_skb = skb_clone(skb_in, GFP_ATOMIC);
|
| 1053 |
|
| 1054 | if (unlikely(!skb_in || skb_network_header(skb_in) < skb_in->head ||
|
| 1055 | (skb_network_header(skb_in) + sizeof(struct iphdr)) >
|
| 1056 | skb_tail_pointer(skb_in) || skb_ensure_writable(skb_in,
|
| 1057 | skb_network_offset(skb_in) + sizeof(struct iphdr))))
|
| 1058 | goto out;
|
| 1059 |
|
| 1060 | orig_ip = ip_hdr(skb_in)->saddr;
|
| 1061 | dir = CTINFO2DIR(ctinfo);
|
| 1062 | ip_hdr(skb_in)->saddr = ct->tuplehash[dir].tuple.src.u3.ip;
|
| 1063 | __icmp_send(skb_in, type, code, info, &parm);
|
| 1064 | ip_hdr(skb_in)->saddr = orig_ip;
|
| 1065 | out:
|
| 1066 | consume_skb(cloned_skb);
|
| 1067 | }
|
| 1068 | EXPORT_SYMBOL(icmp_ndo_send);
|
| 1069 | #endif
|
| 1070 |
|
| 1071 | static void icmp_socket_deliver(struct sk_buff *skb, u32 info)
|
| 1072 | {
|
| 1073 | const struct iphdr *iph = (const struct iphdr *)skb->data;
|
| 1074 | const struct net_protocol *ipprot;
|
| 1075 | int protocol = iph->protocol;
|
| 1076 |
|
| 1077 | |
| 1078 | * avoid additional coding at protocol handlers.
|
| 1079 |
|
| 1080 | if (!pskb_may_pull(skb, iph->ihl * 4 + 8))
|
| 1081 | goto out;
|
| 1082 |
|
| 1083 |
|
| 1084 | if (protocol == IPPROTO_RAW)
|
| 1085 | goto out;
|
| 1086 |
|
| 1087 | raw_icmp_error(skb, protocol, info);
|
| 1088 |
|
| 1089 | ipprot = rcu_dereference(inet_protos[protocol]);
|
| 1090 | if (ipprot && ipprot->err_handler)
|
| 1091 | ipprot->err_handler(skb, info);
|
| 1092 | return;
|
| 1093 |
|
| 1094 | out:
|
| 1095 | __ICMP_INC_STATS(dev_net_rcu(skb->dev), ICMP_MIB_INERRORS);
|
| 1096 | }
|
| 1097 |
|
| 1098 | static bool icmp_tag_validation(int proto)
|
| 1099 | {
|
| 1100 | const struct net_protocol *ipprot;
|
| 1101 | bool ok;
|
| 1102 |
|
| 1103 | rcu_read_lock();
|
| 1104 | ipprot = rcu_dereference(inet_protos[proto]);
|
| 1105 | ok = ipprot ? ipprot->icmp_strict_tag_validation : false;
|
| 1106 | rcu_read_unlock();
|
| 1107 | return ok;
|
| 1108 | }
|
| 1109 |
|
| 1110 | |
| 1111 | * Handle ICMP_DEST_UNREACH, ICMP_TIME_EXCEEDED, ICMP_QUENCH, and
|
| 1112 | * ICMP_PARAMETERPROB.
|
| 1113 |
|
| 1114 |
|
| 1115 | static enum skb_drop_reason icmp_unreach(struct sk_buff *skb)
|
| 1116 | {
|
| 1117 | enum skb_drop_reason reason = SKB_NOT_DROPPED_YET;
|
| 1118 | const struct iphdr *iph;
|
| 1119 | struct icmphdr *icmph;
|
| 1120 | struct net *net;
|
| 1121 | u32 info = 0;
|
| 1122 |
|
| 1123 | net = skb_dst_dev_net_rcu(skb);
|
| 1124 |
|
| 1125 | |
| 1126 | * Incomplete header ?
|
| 1127 | * Only checks for the IP header, there should be an
|
| 1128 | * additional check for longer headers in upper levels.
|
| 1129 |
|
| 1130 |
|
| 1131 | if (!pskb_may_pull(skb, sizeof(struct iphdr)))
|
| 1132 | goto out_err;
|
| 1133 |
|
| 1134 | icmph = icmp_hdr(skb);
|
| 1135 | iph = (const struct iphdr *)skb->data;
|
| 1136 |
|
| 1137 | if (iph->ihl < 5) {
|
| 1138 | reason = SKB_DROP_REASON_IP_INHDR;
|
| 1139 | goto out_err;
|
| 1140 | }
|
| 1141 |
|
| 1142 | switch (icmph->type) {
|
| 1143 | case ICMP_DEST_UNREACH:
|
| 1144 | switch (icmph->code & 15) {
|
| 1145 | case ICMP_NET_UNREACH:
|
| 1146 | case ICMP_HOST_UNREACH:
|
| 1147 | case ICMP_PROT_UNREACH:
|
| 1148 | case ICMP_PORT_UNREACH:
|
| 1149 | break;
|
| 1150 | case ICMP_FRAG_NEEDED:
|
| 1151 | |
| 1152 | * values please see
|
| 1153 | * Documentation/networking/ip-sysctl.rst
|
| 1154 |
|
| 1155 | switch (READ_ONCE(net->ipv4.sysctl_ip_no_pmtu_disc)) {
|
| 1156 | default:
|
| 1157 | net_dbg_ratelimited("%pI4: fragmentation needed and DF set\n",
|
| 1158 | &iph->daddr);
|
| 1159 | break;
|
| 1160 | case 2:
|
| 1161 | goto out;
|
| 1162 | case 3:
|
| 1163 | if (!icmp_tag_validation(iph->protocol))
|
| 1164 | goto out;
|
| 1165 | fallthrough;
|
| 1166 | case 0:
|
| 1167 | info = ntohs(icmph->un.frag.mtu);
|
| 1168 | }
|
| 1169 | break;
|
| 1170 | case ICMP_SR_FAILED:
|
| 1171 | net_dbg_ratelimited("%pI4: Source Route Failed\n",
|
| 1172 | &iph->daddr);
|
| 1173 | break;
|
| 1174 | default:
|
| 1175 | break;
|
| 1176 | }
|
| 1177 | if (icmph->code > NR_ICMP_UNREACH)
|
| 1178 | goto out;
|
| 1179 | break;
|
| 1180 | case ICMP_PARAMETERPROB:
|
| 1181 | info = ntohl(icmph->un.gateway) >> 24;
|
| 1182 | break;
|
| 1183 | case ICMP_TIME_EXCEEDED:
|
| 1184 | __ICMP_INC_STATS(net, ICMP_MIB_INTIMEEXCDS);
|
| 1185 | if (icmph->code == ICMP_EXC_FRAGTIME)
|
| 1186 | goto out;
|
| 1187 | break;
|
| 1188 | }
|
| 1189 |
|
| 1190 | |
| 1191 | * Throw it at our lower layers
|
| 1192 | *
|
| 1193 | * RFC 1122: 3.2.2 MUST extract the protocol ID from the passed
|
| 1194 | * header.
|
| 1195 | * RFC 1122: 3.2.2.1 MUST pass ICMP unreach messages to the
|
| 1196 | * transport layer.
|
| 1197 | * RFC 1122: 3.2.2.2 MUST pass ICMP time expired messages to
|
| 1198 | * transport layer.
|
| 1199 |
|
| 1200 |
|
| 1201 | |
| 1202 | * Check the other end isn't violating RFC 1122. Some routers send
|
| 1203 | * bogus responses to broadcast frames. If you see this message
|
| 1204 | * first check your netmask matches at both ends, if it does then
|
| 1205 | * get the other vendor to fix their kit.
|
| 1206 |
|
| 1207 |
|
| 1208 | if (!READ_ONCE(net->ipv4.sysctl_icmp_ignore_bogus_error_responses) &&
|
| 1209 | inet_addr_type_dev_table(net, skb->dev, iph->daddr) == RTN_BROADCAST) {
|
| 1210 | net_warn_ratelimited("%pI4 sent an invalid ICMP type %u, code %u error to a broadcast: %pI4 on %s\n",
|
| 1211 | &ip_hdr(skb)->saddr,
|
| 1212 | icmph->type, icmph->code,
|
| 1213 | &iph->daddr, skb->dev->name);
|
| 1214 | goto out;
|
| 1215 | }
|
| 1216 |
|
| 1217 | icmp_socket_deliver(skb, info);
|
| 1218 |
|
| 1219 | out:
|
| 1220 | return reason;
|
| 1221 | out_err:
|
| 1222 | __ICMP_INC_STATS(net, ICMP_MIB_INERRORS);
|
| 1223 | return reason ?: SKB_DROP_REASON_NOT_SPECIFIED;
|
| 1224 | }
|
| 1225 |
|
| 1226 |
|
| 1227 | |
| 1228 | * Handle ICMP_REDIRECT.
|
| 1229 |
|
| 1230 |
|
| 1231 | static enum skb_drop_reason icmp_redirect(struct sk_buff *skb)
|
| 1232 | {
|
| 1233 | if (skb->len < sizeof(struct iphdr)) {
|
| 1234 | __ICMP_INC_STATS(dev_net_rcu(skb->dev), ICMP_MIB_INERRORS);
|
| 1235 | return SKB_DROP_REASON_PKT_TOO_SMALL;
|
| 1236 | }
|
| 1237 |
|
| 1238 | if (!pskb_may_pull(skb, sizeof(struct iphdr))) {
|
| 1239 |
|
| 1240 | return SKB_DROP_REASON_NOMEM;
|
| 1241 | }
|
| 1242 |
|
| 1243 | icmp_socket_deliver(skb, ntohl(icmp_hdr(skb)->un.gateway));
|
| 1244 | return SKB_NOT_DROPPED_YET;
|
| 1245 | }
|
| 1246 |
|
| 1247 | |
| 1248 | * Handle ICMP_ECHO ("ping") and ICMP_EXT_ECHO ("PROBE") requests.
|
| 1249 | *
|
| 1250 | * RFC 1122: 3.2.2.6 MUST have an echo server that answers ICMP echo
|
| 1251 | * requests.
|
| 1252 | * RFC 1122: 3.2.2.6 Data received in the ICMP_ECHO request MUST be
|
| 1253 | * included in the reply.
|
| 1254 | * RFC 1812: 4.3.3.6 SHOULD have a config option for silently ignoring
|
| 1255 | * echo requests, MUST have default=NOT.
|
| 1256 | * RFC 8335: 8 MUST have a config option to enable/disable ICMP
|
| 1257 | * Extended Echo Functionality, MUST be disabled by default
|
| 1258 | * See also WRT handling of options once they are done and working.
|
| 1259 |
|
| 1260 |
|
| 1261 | static enum skb_drop_reason icmp_echo(struct sk_buff *skb)
|
| 1262 | {
|
| 1263 | DEFINE_RAW_FLEX(struct icmp_bxm, icmp_param, replyopts.opt.__data,
|
| 1264 | IP_OPTIONS_DATA_FIXED_SIZE);
|
| 1265 | struct net *net;
|
| 1266 |
|
| 1267 | net = skb_dst_dev_net_rcu(skb);
|
| 1268 |
|
| 1269 | if (READ_ONCE(net->ipv4.sysctl_icmp_echo_ignore_all))
|
| 1270 | return SKB_NOT_DROPPED_YET;
|
| 1271 |
|
| 1272 | icmp_param->data.icmph = *icmp_hdr(skb);
|
| 1273 | icmp_param->skb = skb;
|
| 1274 | icmp_param->offset = 0;
|
| 1275 | icmp_param->data_len = skb->len;
|
| 1276 | icmp_param->head_len = sizeof(struct icmphdr);
|
| 1277 |
|
| 1278 | if (icmp_param->data.icmph.type == ICMP_ECHO)
|
| 1279 | icmp_param->data.icmph.type = ICMP_ECHOREPLY;
|
| 1280 | else if (!icmp_build_probe(skb, &icmp_param->data.icmph))
|
| 1281 | return SKB_NOT_DROPPED_YET;
|
| 1282 |
|
| 1283 | icmp_reply(icmp_param, skb);
|
| 1284 | return SKB_NOT_DROPPED_YET;
|
| 1285 | }
|
| 1286 |
|
| 1287 | |
| 1288 | * Searches for net_device that matches PROBE interface identifier
|
| 1289 | * and builds PROBE reply message in icmphdr.
|
| 1290 | *
|
| 1291 | * Returns false if PROBE responses are disabled via sysctl
|
| 1292 |
|
| 1293 |
|
| 1294 | bool icmp_build_probe(struct sk_buff *skb, struct icmphdr *icmphdr)
|
| 1295 | {
|
| 1296 | struct net *net = dev_net_rcu(skb->dev);
|
| 1297 | struct icmp_ext_hdr *ext_hdr, _ext_hdr;
|
| 1298 | struct icmp_ext_echo_iio *iio, _iio;
|
| 1299 | struct inet6_dev *in6_dev;
|
| 1300 | struct in_device *in_dev;
|
| 1301 | struct net_device *dev;
|
| 1302 | char buff[IFNAMSIZ];
|
| 1303 | u16 ident_len;
|
| 1304 | u8 status;
|
| 1305 |
|
| 1306 | if (!READ_ONCE(net->ipv4.sysctl_icmp_echo_enable_probe))
|
| 1307 | return false;
|
| 1308 |
|
| 1309 | |
| 1310 | * Check to ensure L-bit is set
|
| 1311 |
|
| 1312 | if (!(ntohs(icmphdr->un.echo.sequence) & 1))
|
| 1313 | return false;
|
| 1314 |
|
| 1315 | icmphdr->un.echo.sequence &= htons(0xFF00);
|
| 1316 | if (icmphdr->type == ICMP_EXT_ECHO)
|
| 1317 | icmphdr->type = ICMP_EXT_ECHOREPLY;
|
| 1318 | else
|
| 1319 | icmphdr->type = ICMPV6_EXT_ECHO_REPLY;
|
| 1320 | ext_hdr = skb_header_pointer(skb, 0, sizeof(_ext_hdr), &_ext_hdr);
|
| 1321 | |
| 1322 | * Only check header here and assign length based on ctype in the switch statement
|
| 1323 |
|
| 1324 | iio = skb_header_pointer(skb, sizeof(_ext_hdr), sizeof(iio->extobj_hdr), &_iio);
|
| 1325 | if (!ext_hdr || !iio)
|
| 1326 | goto send_mal_query;
|
| 1327 | if (ntohs(iio->extobj_hdr.length) <= sizeof(iio->extobj_hdr) ||
|
| 1328 | ntohs(iio->extobj_hdr.length) > sizeof(_iio))
|
| 1329 | goto send_mal_query;
|
| 1330 | ident_len = ntohs(iio->extobj_hdr.length) - sizeof(iio->extobj_hdr);
|
| 1331 | iio = skb_header_pointer(skb, sizeof(_ext_hdr),
|
| 1332 | sizeof(iio->extobj_hdr) + ident_len, &_iio);
|
| 1333 | if (!iio)
|
| 1334 | goto send_mal_query;
|
| 1335 |
|
| 1336 | status = 0;
|
| 1337 | dev = NULL;
|
| 1338 | switch (iio->extobj_hdr.class_type) {
|
| 1339 | case ICMP_EXT_ECHO_CTYPE_NAME:
|
| 1340 | if (ident_len >= IFNAMSIZ)
|
| 1341 | goto send_mal_query;
|
| 1342 | memset(buff, 0, sizeof(buff));
|
| 1343 | memcpy(buff, &iio->ident.name, ident_len);
|
| 1344 | dev = dev_get_by_name(net, buff);
|
| 1345 | break;
|
| 1346 | case ICMP_EXT_ECHO_CTYPE_INDEX:
|
| 1347 | if (ident_len != sizeof(iio->ident.ifindex))
|
| 1348 | goto send_mal_query;
|
| 1349 | dev = dev_get_by_index(net, ntohl(iio->ident.ifindex));
|
| 1350 | break;
|
| 1351 | case ICMP_EXT_ECHO_CTYPE_ADDR:
|
| 1352 | if (ident_len < sizeof(iio->ident.addr.ctype3_hdr) ||
|
| 1353 | ident_len != sizeof(iio->ident.addr.ctype3_hdr) +
|
| 1354 | iio->ident.addr.ctype3_hdr.addrlen)
|
| 1355 | goto send_mal_query;
|
| 1356 | switch (ntohs(iio->ident.addr.ctype3_hdr.afi)) {
|
| 1357 | case ICMP_AFI_IP:
|
| 1358 | if (iio->ident.addr.ctype3_hdr.addrlen != sizeof(struct in_addr))
|
| 1359 | goto send_mal_query;
|
| 1360 | dev = ip_dev_find(net, iio->ident.addr.ip_addr.ipv4_addr);
|
| 1361 | break;
|
| 1362 | #if IS_ENABLED(CONFIG_IPV6)
|
| 1363 | case ICMP_AFI_IP6:
|
| 1364 | if (iio->ident.addr.ctype3_hdr.addrlen != sizeof(struct in6_addr))
|
| 1365 | goto send_mal_query;
|
| 1366 | dev = ipv6_dev_find(net, &iio->ident.addr.ip_addr.ipv6_addr, dev);
|
| 1367 | dev_hold(dev);
|
| 1368 | break;
|
| 1369 | #endif
|
| 1370 | default:
|
| 1371 | goto send_mal_query;
|
| 1372 | }
|
| 1373 | break;
|
| 1374 | default:
|
| 1375 | goto send_mal_query;
|
| 1376 | }
|
| 1377 | if (!dev) {
|
| 1378 | icmphdr->code = ICMP_EXT_CODE_NO_IF;
|
| 1379 | return true;
|
| 1380 | }
|
| 1381 |
|
| 1382 | if (dev->flags & IFF_UP)
|
| 1383 | status |= ICMP_EXT_ECHOREPLY_ACTIVE;
|
| 1384 |
|
| 1385 | in_dev = __in_dev_get_rcu(dev);
|
| 1386 | if (in_dev && rcu_access_pointer(in_dev->ifa_list))
|
| 1387 | status |= ICMP_EXT_ECHOREPLY_IPV4;
|
| 1388 |
|
| 1389 | in6_dev = __in6_dev_get(dev);
|
| 1390 | if (in6_dev && !list_empty(&in6_dev->addr_list))
|
| 1391 | status |= ICMP_EXT_ECHOREPLY_IPV6;
|
| 1392 |
|
| 1393 | dev_put(dev);
|
| 1394 | icmphdr->un.echo.sequence |= htons(status);
|
| 1395 | return true;
|
| 1396 | send_mal_query:
|
| 1397 | icmphdr->code = ICMP_EXT_CODE_MAL_QUERY;
|
| 1398 | return true;
|
| 1399 | }
|
| 1400 |
|
| 1401 | |
| 1402 | * Handle ICMP Timestamp requests.
|
| 1403 | * RFC 1122: 3.2.2.8 MAY implement ICMP timestamp requests.
|
| 1404 | * SHOULD be in the kernel for minimum random latency.
|
| 1405 | * MUST be accurate to a few minutes.
|
| 1406 | * MUST be updated at least at 15Hz.
|
| 1407 |
|
| 1408 | static enum skb_drop_reason icmp_timestamp(struct sk_buff *skb)
|
| 1409 | {
|
| 1410 | DEFINE_RAW_FLEX(struct icmp_bxm, icmp_param, replyopts.opt.__data,
|
| 1411 | IP_OPTIONS_DATA_FIXED_SIZE);
|
| 1412 | |
| 1413 | * Too short.
|
| 1414 |
|
| 1415 | if (skb->len < 4)
|
| 1416 | goto out_err;
|
| 1417 |
|
| 1418 | |
| 1419 | * Fill in the current time as ms since midnight UT:
|
| 1420 |
|
| 1421 | icmp_param->data.times[1] = inet_current_timestamp();
|
| 1422 | icmp_param->data.times[2] = icmp_param->data.times[1];
|
| 1423 |
|
| 1424 | BUG_ON(skb_copy_bits(skb, 0, &icmp_param->data.times[0], 4));
|
| 1425 |
|
| 1426 | icmp_param->data.icmph = *icmp_hdr(skb);
|
| 1427 | icmp_param->data.icmph.type = ICMP_TIMESTAMPREPLY;
|
| 1428 | icmp_param->data.icmph.code = 0;
|
| 1429 | icmp_param->skb = skb;
|
| 1430 | icmp_param->offset = 0;
|
| 1431 | icmp_param->data_len = 0;
|
| 1432 | icmp_param->head_len = sizeof(struct icmphdr) + 12;
|
| 1433 | icmp_reply(icmp_param, skb);
|
| 1434 | return SKB_NOT_DROPPED_YET;
|
| 1435 |
|
| 1436 | out_err:
|
| 1437 | __ICMP_INC_STATS(skb_dst_dev_net_rcu(skb), ICMP_MIB_INERRORS);
|
| 1438 | return SKB_DROP_REASON_PKT_TOO_SMALL;
|
| 1439 | }
|
| 1440 |
|
| 1441 | static enum skb_drop_reason icmp_discard(struct sk_buff *skb)
|
| 1442 | {
|
| 1443 |
|
| 1444 | return SKB_NOT_DROPPED_YET;
|
| 1445 | }
|
| 1446 |
|
| 1447 | |
| 1448 | * Deal with incoming ICMP packets.
|
| 1449 |
|
| 1450 | int icmp_rcv(struct sk_buff *skb)
|
| 1451 | {
|
| 1452 | enum skb_drop_reason reason = SKB_DROP_REASON_NOT_SPECIFIED;
|
| 1453 | struct rtable *rt = skb_rtable(skb);
|
| 1454 | struct net *net = dev_net_rcu(rt->dst.dev);
|
| 1455 | struct icmphdr *icmph;
|
| 1456 |
|
| 1457 | if (!xfrm4_policy_check(NULL, XFRM_POLICY_IN, skb)) {
|
| 1458 | struct sec_path *sp = skb_sec_path(skb);
|
| 1459 | int nh;
|
| 1460 |
|
| 1461 | if (!(sp && sp->xvec[sp->len - 1]->props.flags &
|
| 1462 | XFRM_STATE_ICMP)) {
|
| 1463 | reason = SKB_DROP_REASON_XFRM_POLICY;
|
| 1464 | goto drop;
|
| 1465 | }
|
| 1466 |
|
| 1467 | if (!pskb_may_pull(skb, sizeof(*icmph) + sizeof(struct iphdr)))
|
| 1468 | goto drop;
|
| 1469 |
|
| 1470 | nh = skb_network_offset(skb);
|
| 1471 | skb_set_network_header(skb, sizeof(*icmph));
|
| 1472 |
|
| 1473 | if (!xfrm4_policy_check_reverse(NULL, XFRM_POLICY_IN,
|
| 1474 | skb)) {
|
| 1475 | reason = SKB_DROP_REASON_XFRM_POLICY;
|
| 1476 | goto drop;
|
| 1477 | }
|
| 1478 |
|
| 1479 | skb_set_network_header(skb, nh);
|
| 1480 | }
|
| 1481 |
|
| 1482 | __ICMP_INC_STATS(net, ICMP_MIB_INMSGS);
|
| 1483 |
|
| 1484 | if (skb_checksum_simple_validate(skb))
|
| 1485 | goto csum_error;
|
| 1486 |
|
| 1487 | if (!pskb_pull(skb, sizeof(*icmph)))
|
| 1488 | goto error;
|
| 1489 |
|
| 1490 | icmph = icmp_hdr(skb);
|
| 1491 |
|
| 1492 | ICMPMSGIN_INC_STATS(net, icmph->type);
|
| 1493 |
|
| 1494 |
|
| 1495 | if (icmph->type == ICMP_EXT_ECHO) {
|
| 1496 | |
| 1497 | * size NR_ICMP_TYPES + 1 (19 elements) and PROBE has code 42.
|
| 1498 |
|
| 1499 | reason = icmp_echo(skb);
|
| 1500 | goto reason_check;
|
| 1501 | }
|
| 1502 |
|
| 1503 | |
| 1504 | * Parse the ICMP message
|
| 1505 |
|
| 1506 |
|
| 1507 | if (rt->rt_flags & (RTCF_BROADCAST | RTCF_MULTICAST)) {
|
| 1508 | |
| 1509 | * RFC 1122: 3.2.2.6 An ICMP_ECHO to broadcast MAY be
|
| 1510 | * silently ignored (we let user decide with a sysctl).
|
| 1511 | * RFC 1122: 3.2.2.8 An ICMP_TIMESTAMP MAY be silently
|
| 1512 | * discarded if to broadcast/multicast.
|
| 1513 |
|
| 1514 | if ((icmph->type == ICMP_ECHO ||
|
| 1515 | icmph->type == ICMP_TIMESTAMP) &&
|
| 1516 | READ_ONCE(net->ipv4.sysctl_icmp_echo_ignore_broadcasts)) {
|
| 1517 | reason = SKB_DROP_REASON_INVALID_PROTO;
|
| 1518 | goto error;
|
| 1519 | }
|
| 1520 | if (icmph->type != ICMP_ECHO &&
|
| 1521 | icmph->type != ICMP_TIMESTAMP &&
|
| 1522 | icmph->type != ICMP_ADDRESS &&
|
| 1523 | icmph->type != ICMP_ADDRESSREPLY) {
|
| 1524 | reason = SKB_DROP_REASON_INVALID_PROTO;
|
| 1525 | goto error;
|
| 1526 | }
|
| 1527 | }
|
| 1528 |
|
| 1529 | if (icmph->type == ICMP_EXT_ECHOREPLY ||
|
| 1530 | icmph->type == ICMP_ECHOREPLY) {
|
| 1531 | reason = ping_rcv(skb);
|
| 1532 | return reason ? NET_RX_DROP : NET_RX_SUCCESS;
|
| 1533 | }
|
| 1534 |
|
| 1535 | |
| 1536 | * 18 is the highest 'known' ICMP type. Anything else is a mystery
|
| 1537 | *
|
| 1538 | * RFC 1122: 3.2.2 Unknown ICMP messages types MUST be silently
|
| 1539 | * discarded.
|
| 1540 |
|
| 1541 | if (icmph->type > NR_ICMP_TYPES) {
|
| 1542 | reason = SKB_DROP_REASON_UNHANDLED_PROTO;
|
| 1543 | goto error;
|
| 1544 | }
|
| 1545 |
|
| 1546 | reason = icmp_pointers[icmph->type].handler(skb);
|
| 1547 | reason_check:
|
| 1548 | if (!reason) {
|
| 1549 | consume_skb(skb);
|
| 1550 | return NET_RX_SUCCESS;
|
| 1551 | }
|
| 1552 |
|
| 1553 | drop:
|
| 1554 | kfree_skb_reason(skb, reason);
|
| 1555 | return NET_RX_DROP;
|
| 1556 | csum_error:
|
| 1557 | reason = SKB_DROP_REASON_ICMP_CSUM;
|
| 1558 | __ICMP_INC_STATS(net, ICMP_MIB_CSUMERRORS);
|
| 1559 | error:
|
| 1560 | __ICMP_INC_STATS(net, ICMP_MIB_INERRORS);
|
| 1561 | goto drop;
|
| 1562 | }
|
| 1563 |
|
| 1564 | static bool ip_icmp_error_rfc4884_validate(const struct sk_buff *skb, int off)
|
| 1565 | {
|
| 1566 | struct icmp_extobj_hdr *objh, _objh;
|
| 1567 | struct icmp_ext_hdr *exth, _exth;
|
| 1568 | u16 olen;
|
| 1569 |
|
| 1570 | exth = skb_header_pointer(skb, off, sizeof(_exth), &_exth);
|
| 1571 | if (!exth)
|
| 1572 | return false;
|
| 1573 | if (exth->version != 2)
|
| 1574 | return true;
|
| 1575 |
|
| 1576 | if (exth->checksum &&
|
| 1577 | csum_fold(skb_checksum(skb, off, skb->len - off, 0)))
|
| 1578 | return false;
|
| 1579 |
|
| 1580 | off += sizeof(_exth);
|
| 1581 | while (off < skb->len) {
|
| 1582 | objh = skb_header_pointer(skb, off, sizeof(_objh), &_objh);
|
| 1583 | if (!objh)
|
| 1584 | return false;
|
| 1585 |
|
| 1586 | olen = ntohs(objh->length);
|
| 1587 | if (olen < sizeof(_objh))
|
| 1588 | return false;
|
| 1589 |
|
| 1590 | off += olen;
|
| 1591 | if (off > skb->len)
|
| 1592 | return false;
|
| 1593 | }
|
| 1594 |
|
| 1595 | return true;
|
| 1596 | }
|
| 1597 |
|
| 1598 | void ip_icmp_error_rfc4884(const struct sk_buff *skb,
|
| 1599 | struct sock_ee_data_rfc4884 *out,
|
| 1600 | int thlen, int off)
|
| 1601 | {
|
| 1602 | int hlen;
|
| 1603 |
|
| 1604 |
|
| 1605 | hlen = -skb_transport_offset(skb) - thlen;
|
| 1606 |
|
| 1607 |
|
| 1608 | if (off < 128 || off < hlen)
|
| 1609 | return;
|
| 1610 |
|
| 1611 |
|
| 1612 | off -= hlen;
|
| 1613 | if (off + sizeof(struct icmp_ext_hdr) > skb->len)
|
| 1614 | return;
|
| 1615 |
|
| 1616 | out->len = off;
|
| 1617 |
|
| 1618 | if (!ip_icmp_error_rfc4884_validate(skb, off))
|
| 1619 | out->flags |= SO_EE_RFC4884_FLAG_INVALID;
|
| 1620 | }
|
| 1621 |
|
| 1622 | int icmp_err(struct sk_buff *skb, u32 info)
|
| 1623 | {
|
| 1624 | struct iphdr *iph = (struct iphdr *)skb->data;
|
| 1625 | int offset = iph->ihl<<2;
|
| 1626 | struct icmphdr *icmph = (struct icmphdr *)(skb->data + offset);
|
| 1627 | struct net *net = dev_net_rcu(skb->dev);
|
| 1628 | int type = icmp_hdr(skb)->type;
|
| 1629 | int code = icmp_hdr(skb)->code;
|
| 1630 |
|
| 1631 | |
| 1632 | * Use ping_err to handle all icmp errors except those
|
| 1633 | * triggered by ICMP_ECHOREPLY which sent from kernel.
|
| 1634 |
|
| 1635 | if (icmph->type != ICMP_ECHOREPLY) {
|
| 1636 | ping_err(skb, offset, info);
|
| 1637 | return 0;
|
| 1638 | }
|
| 1639 |
|
| 1640 | if (type == ICMP_DEST_UNREACH && code == ICMP_FRAG_NEEDED)
|
| 1641 | ipv4_update_pmtu(skb, net, info, 0, IPPROTO_ICMP);
|
| 1642 | else if (type == ICMP_REDIRECT)
|
| 1643 | ipv4_redirect(skb, net, 0, IPPROTO_ICMP);
|
| 1644 |
|
| 1645 | return 0;
|
| 1646 | }
|
| 1647 |
|
| 1648 | |
| 1649 | * This table is the definition of how we handle ICMP.
|
| 1650 |
|
| 1651 | static const struct icmp_control icmp_pointers[NR_ICMP_TYPES + 1] = {
|
| 1652 | [ICMP_ECHOREPLY] = {
|
| 1653 | .handler = ping_rcv,
|
| 1654 | },
|
| 1655 | [1] = {
|
| 1656 | .handler = icmp_discard,
|
| 1657 | .error = 1,
|
| 1658 | },
|
| 1659 | [2] = {
|
| 1660 | .handler = icmp_discard,
|
| 1661 | .error = 1,
|
| 1662 | },
|
| 1663 | [ICMP_DEST_UNREACH] = {
|
| 1664 | .handler = icmp_unreach,
|
| 1665 | .error = 1,
|
| 1666 | },
|
| 1667 | [ICMP_SOURCE_QUENCH] = {
|
| 1668 | .handler = icmp_unreach,
|
| 1669 | .error = 1,
|
| 1670 | },
|
| 1671 | [ICMP_REDIRECT] = {
|
| 1672 | .handler = icmp_redirect,
|
| 1673 | .error = 1,
|
| 1674 | },
|
| 1675 | [6] = {
|
| 1676 | .handler = icmp_discard,
|
| 1677 | .error = 1,
|
| 1678 | },
|
| 1679 | [7] = {
|
| 1680 | .handler = icmp_discard,
|
| 1681 | .error = 1,
|
| 1682 | },
|
| 1683 | [ICMP_ECHO] = {
|
| 1684 | .handler = icmp_echo,
|
| 1685 | },
|
| 1686 | [9] = {
|
| 1687 | .handler = icmp_discard,
|
| 1688 | .error = 1,
|
| 1689 | },
|
| 1690 | [10] = {
|
| 1691 | .handler = icmp_discard,
|
| 1692 | .error = 1,
|
| 1693 | },
|
| 1694 | [ICMP_TIME_EXCEEDED] = {
|
| 1695 | .handler = icmp_unreach,
|
| 1696 | .error = 1,
|
| 1697 | },
|
| 1698 | [ICMP_PARAMETERPROB] = {
|
| 1699 | .handler = icmp_unreach,
|
| 1700 | .error = 1,
|
| 1701 | },
|
| 1702 | [ICMP_TIMESTAMP] = {
|
| 1703 | .handler = icmp_timestamp,
|
| 1704 | },
|
| 1705 | [ICMP_TIMESTAMPREPLY] = {
|
| 1706 | .handler = icmp_discard,
|
| 1707 | },
|
| 1708 | [ICMP_INFO_REQUEST] = {
|
| 1709 | .handler = icmp_discard,
|
| 1710 | },
|
| 1711 | [ICMP_INFO_REPLY] = {
|
| 1712 | .handler = icmp_discard,
|
| 1713 | },
|
| 1714 | [ICMP_ADDRESS] = {
|
| 1715 | .handler = icmp_discard,
|
| 1716 | },
|
| 1717 | [ICMP_ADDRESSREPLY] = {
|
| 1718 | .handler = icmp_discard,
|
| 1719 | },
|
| 1720 | };
|
| 1721 |
|
| 1722 | static int __net_init icmp_sk_init(struct net *net)
|
| 1723 | {
|
| 1724 |
|
| 1725 | net->ipv4.sysctl_icmp_echo_ignore_all = 0;
|
| 1726 | net->ipv4.sysctl_icmp_echo_enable_probe = 0;
|
| 1727 | net->ipv4.sysctl_icmp_echo_ignore_broadcasts = 1;
|
| 1728 |
|
| 1729 |
|
| 1730 | net->ipv4.sysctl_icmp_ignore_bogus_error_responses = 1;
|
| 1731 |
|
| 1732 | |
| 1733 | * Configurable global rate limit.
|
| 1734 | *
|
| 1735 | * ratelimit defines tokens/packet consumed for dst->rate_token
|
| 1736 | * bucket ratemask defines which icmp types are ratelimited by
|
| 1737 | * setting it's bit position.
|
| 1738 | *
|
| 1739 | * default:
|
| 1740 | * dest unreachable (3), source quench (4),
|
| 1741 | * time exceeded (11), parameter problem (12)
|
| 1742 |
|
| 1743 |
|
| 1744 | net->ipv4.sysctl_icmp_ratelimit = 1 * HZ;
|
| 1745 | net->ipv4.sysctl_icmp_ratemask = 0x1818;
|
| 1746 | net->ipv4.sysctl_icmp_errors_use_inbound_ifaddr = 0;
|
| 1747 | net->ipv4.sysctl_icmp_errors_extension_mask = 0;
|
| 1748 | net->ipv4.sysctl_icmp_msgs_per_sec = 10000;
|
| 1749 | net->ipv4.sysctl_icmp_msgs_burst = 10000;
|
| 1750 |
|
| 1751 | return 0;
|
| 1752 | }
|
| 1753 |
|
| 1754 | static struct pernet_operations __net_initdata icmp_sk_ops = {
|
| 1755 | .init = icmp_sk_init,
|
| 1756 | };
|
| 1757 |
|
| 1758 | int __init icmp_init(void)
|
| 1759 | {
|
| 1760 | int err, i;
|
| 1761 |
|
| 1762 | for_each_possible_cpu(i) {
|
| 1763 | struct sock *sk;
|
| 1764 |
|
| 1765 | err = inet_ctl_sock_create(&sk, PF_INET,
|
| 1766 | SOCK_RAW, IPPROTO_ICMP, &init_net);
|
| 1767 | if (err < 0)
|
| 1768 | return err;
|
| 1769 |
|
| 1770 | per_cpu(ipv4_icmp_sk, i) = sk;
|
| 1771 |
|
| 1772 | |
| 1773 | * sk_buff/skb_shared_info struct overhead.
|
| 1774 |
|
| 1775 | sk->sk_sndbuf = 2 * SKB_TRUESIZE(64 * 1024);
|
| 1776 |
|
| 1777 | |
| 1778 | * Speedup sock_wfree()
|
| 1779 |
|
| 1780 | sock_set_flag(sk, SOCK_USE_WRITE_QUEUE);
|
| 1781 | inet_sk(sk)->pmtudisc = IP_PMTUDISC_DONT;
|
| 1782 | }
|
| 1783 | return register_pernet_subsys(&icmp_sk_ops);
|
| 1784 | }
|