qemu/slirp/src/ip6_icmp.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: BSD-3-Clause */
   2/*
   3 * Copyright (c) 2013
   4 * Guillaume Subiron, Yann Bordenave, Serigne Modou Wagne.
   5 */
   6
   7#ifndef SLIRP_IP6_ICMP_H
   8#define SLIRP_IP6_ICMP_H
   9
  10/*
  11 * Interface Control Message Protocol version 6 Definitions.
  12 * Per RFC 4443, March 2006.
  13 *
  14 * Network Discover Protocol Definitions.
  15 * Per RFC 4861, September 2007.
  16 */
  17
  18struct icmp6_echo { /* Echo Messages */
  19    uint16_t id;
  20    uint16_t seq_num;
  21};
  22
  23union icmp6_error_body {
  24    uint32_t unused;
  25    uint32_t pointer;
  26    uint32_t mtu;
  27};
  28
  29/*
  30 * NDP Messages
  31 */
  32struct ndp_rs {     /* Router Solicitation Message */
  33    uint32_t reserved;
  34};
  35
  36struct ndp_ra {     /* Router Advertisement Message */
  37    uint8_t chl;    /* Cur Hop Limit */
  38#if G_BYTE_ORDER == G_BIG_ENDIAN
  39    uint8_t
  40        M:1,
  41        O:1,
  42        reserved:6;
  43#else
  44    uint8_t
  45        reserved:6,
  46        O:1,
  47        M:1;
  48#endif
  49    uint16_t lifetime;      /* Router Lifetime */
  50    uint32_t reach_time;    /* Reachable Time */
  51    uint32_t retrans_time;  /* Retrans Timer */
  52};
  53
  54G_STATIC_ASSERT(sizeof(struct ndp_ra) == 12);
  55
  56struct ndp_ns {     /* Neighbor Solicitation Message */
  57    uint32_t reserved;
  58    struct in6_addr target; /* Target Address */
  59};
  60
  61G_STATIC_ASSERT(sizeof(struct ndp_ns) == 20);
  62
  63struct ndp_na {     /* Neighbor Advertisement Message */
  64#if G_BYTE_ORDER == G_BIG_ENDIAN
  65    uint32_t
  66        R:1,                /* Router Flag */
  67        S:1,                /* Solicited Flag */
  68        O:1,                /* Override Flag */
  69        reserved_hi:5,
  70        reserved_lo:24;
  71#else
  72    uint32_t
  73        reserved_hi:5,
  74        O:1,
  75        S:1,
  76        R:1,
  77        reserved_lo:24;
  78#endif
  79    struct in6_addr target; /* Target Address */
  80};
  81
  82G_STATIC_ASSERT(sizeof(struct ndp_na) == 20);
  83
  84struct ndp_redirect {
  85    uint32_t reserved;
  86    struct in6_addr target; /* Target Address */
  87    struct in6_addr dest;   /* Destination Address */
  88};
  89
  90G_STATIC_ASSERT(sizeof(struct ndp_redirect) == 36);
  91
  92/*
  93 * Structure of an icmpv6 header.
  94 */
  95struct icmp6 {
  96    uint8_t     icmp6_type;         /* type of message, see below */
  97    uint8_t     icmp6_code;         /* type sub code */
  98    uint16_t    icmp6_cksum;        /* ones complement cksum of struct */
  99    union {
 100        union icmp6_error_body error_body;
 101        struct icmp6_echo echo;
 102        struct ndp_rs ndp_rs;
 103        struct ndp_ra ndp_ra;
 104        struct ndp_ns ndp_ns;
 105        struct ndp_na ndp_na;
 106        struct ndp_redirect ndp_redirect;
 107    } icmp6_body;
 108#define icmp6_err icmp6_body.error_body
 109#define icmp6_echo icmp6_body.echo
 110#define icmp6_nrs icmp6_body.ndp_rs
 111#define icmp6_nra icmp6_body.ndp_ra
 112#define icmp6_nns icmp6_body.ndp_ns
 113#define icmp6_nna icmp6_body.ndp_na
 114#define icmp6_redirect icmp6_body.ndp_redirect
 115};
 116
 117G_STATIC_ASSERT(sizeof(struct icmp6) == 40);
 118
 119#define ICMP6_MINLEN    4
 120#define ICMP6_ERROR_MINLEN  8
 121#define ICMP6_ECHO_MINLEN   8
 122#define ICMP6_NDP_RS_MINLEN 8
 123#define ICMP6_NDP_RA_MINLEN 16
 124#define ICMP6_NDP_NS_MINLEN 24
 125#define ICMP6_NDP_NA_MINLEN 24
 126#define ICMP6_NDP_REDIRECT_MINLEN 40
 127
 128/*
 129 * NDP Options
 130 */
 131struct ndpopt {
 132    uint8_t     ndpopt_type;                    /* Option type */
 133    uint8_t     ndpopt_len;                     /* /!\ In units of 8 octets */
 134    union {
 135        unsigned char   linklayer_addr[6];      /* Source/Target Link-layer */
 136#define ndpopt_linklayer ndpopt_body.linklayer_addr
 137        struct prefixinfo {                     /* Prefix Information */
 138            uint8_t     prefix_length;
 139#if G_BYTE_ORDER == G_BIG_ENDIAN
 140            uint8_t     L:1, A:1, reserved1:6;
 141#else
 142            uint8_t     reserved1:6, A:1, L:1;
 143#endif
 144            uint32_t    valid_lt;               /* Valid Lifetime */
 145            uint32_t    pref_lt;                /* Preferred Lifetime */
 146            uint32_t    reserved2;
 147            struct in6_addr prefix;
 148        } SLIRP_PACKED prefixinfo;
 149#define ndpopt_prefixinfo ndpopt_body.prefixinfo
 150        struct rdnss {
 151            uint16_t reserved;
 152            uint32_t lifetime;
 153            struct in6_addr addr;
 154        } SLIRP_PACKED rdnss;
 155#define ndpopt_rdnss ndpopt_body.rdnss
 156    } ndpopt_body;
 157} SLIRP_PACKED;
 158
 159/* NDP options type */
 160#define NDPOPT_LINKLAYER_SOURCE     1   /* Source Link-Layer Address */
 161#define NDPOPT_LINKLAYER_TARGET     2   /* Target Link-Layer Address */
 162#define NDPOPT_PREFIX_INFO          3   /* Prefix Information */
 163#define NDPOPT_RDNSS                25  /* Recursive DNS Server Address */
 164
 165/* NDP options size, in octets. */
 166#define NDPOPT_LINKLAYER_LEN    8
 167#define NDPOPT_PREFIXINFO_LEN   32
 168#define NDPOPT_RDNSS_LEN        24
 169
 170/*
 171 * Definition of type and code field values.
 172 * Per https://www.iana.org/assignments/icmpv6-parameters/icmpv6-parameters.xml
 173 * Last Updated 2012-11-12
 174 */
 175
 176/* Errors */
 177#define ICMP6_UNREACH   1   /* Destination Unreachable */
 178#define     ICMP6_UNREACH_NO_ROUTE      0   /* no route to dest */
 179#define     ICMP6_UNREACH_DEST_PROHIB   1   /* com with dest prohibited */
 180#define     ICMP6_UNREACH_SCOPE         2   /* beyond scope of src addr */
 181#define     ICMP6_UNREACH_ADDRESS       3   /* address unreachable */
 182#define     ICMP6_UNREACH_PORT          4   /* port unreachable */
 183#define     ICMP6_UNREACH_SRC_FAIL      5   /* src addr failed */
 184#define     ICMP6_UNREACH_REJECT_ROUTE  6   /* reject route to dest */
 185#define     ICMP6_UNREACH_SRC_HDR_ERROR 7   /* error in src routing header */
 186#define ICMP6_TOOBIG    2   /* Packet Too Big */
 187#define ICMP6_TIMXCEED  3   /* Time Exceeded */
 188#define     ICMP6_TIMXCEED_INTRANS      0   /* hop limit exceeded in transit */
 189#define     ICMP6_TIMXCEED_REASS        1   /* ttl=0 in reass */
 190#define ICMP6_PARAMPROB 4   /* Parameter Problem */
 191#define     ICMP6_PARAMPROB_HDR_FIELD   0   /* err header field */
 192#define     ICMP6_PARAMPROB_NXTHDR_TYPE 1   /* unrecognized Next Header type */
 193#define     ICMP6_PARAMPROB_IPV6_OPT    2   /* unrecognized IPv6 option */
 194
 195/* Informational Messages */
 196#define ICMP6_ECHO_REQUEST      128 /* Echo Request */
 197#define ICMP6_ECHO_REPLY        129 /* Echo Reply */
 198#define ICMP6_NDP_RS            133 /* Router Solicitation (NDP) */
 199#define ICMP6_NDP_RA            134 /* Router Advertisement (NDP) */
 200#define ICMP6_NDP_NS            135 /* Neighbor Solicitation (NDP) */
 201#define ICMP6_NDP_NA            136 /* Neighbor Advertisement (NDP) */
 202#define ICMP6_NDP_REDIRECT      137 /* Redirect Message (NDP) */
 203
 204/*
 205 * Router Configuration Variables (rfc4861#section-6)
 206 */
 207#define NDP_IsRouter                1
 208#define NDP_AdvSendAdvertisements   1
 209#define NDP_MaxRtrAdvInterval       600000
 210#define NDP_MinRtrAdvInterval       ((NDP_MaxRtrAdvInterval >= 9) ? \
 211                                        NDP_MaxRtrAdvInterval / 3 : \
 212                                        NDP_MaxRtrAdvInterval)
 213#define NDP_AdvManagedFlag          0
 214#define NDP_AdvOtherConfigFlag      0
 215#define NDP_AdvLinkMTU              0
 216#define NDP_AdvReachableTime        0
 217#define NDP_AdvRetransTime          0
 218#define NDP_AdvCurHopLimit          64
 219#define NDP_AdvDefaultLifetime      ((3 * NDP_MaxRtrAdvInterval) / 1000)
 220#define NDP_AdvValidLifetime        86400
 221#define NDP_AdvOnLinkFlag           1
 222#define NDP_AdvPrefLifetime         14400
 223#define NDP_AdvAutonomousFlag       1
 224
 225void icmp6_init(Slirp *slirp);
 226void icmp6_cleanup(Slirp *slirp);
 227void icmp6_input(struct mbuf *);
 228void icmp6_send_error(struct mbuf *m, uint8_t type, uint8_t code);
 229void ndp_send_ra(Slirp *slirp);
 230void ndp_send_ns(Slirp *slirp, struct in6_addr addr);
 231
 232#endif
 233