📄 draft-ietf-ipngwg-rfc2292bis-02.txt
字号:
The protocol stack should not automatically discard packets if the ICMP type is unknown to the stack. For extensibility reasons received ICMP packets with any type (informational or error) must be passed to the applications (subject to ICMP6_FILTER filtering on the type value and the checksum verification).4. Access to IPv6 and Extension Headers Applications need to be able to control IPv6 header and extension header content when sending as well as being able to receive the content of these headers. This is done by defining socket option types which can be used both with setsockopt and with ancillary data. Ancillary data is discussed in Appendix A. The following optional information can be exchanged between the application and the kernel: 1. The send/receive interface and source/destination address, 2. The hop limit, 3. Next hop address, 4. Routing header. 5. Hop-by-Hop options, and 6. Destination options (both before and after a Routing header). First, to receive any of this optional information (other than the next hop address, which can only be set), the application must call setsockopt() to turn on the corresponding flag:draft-ietf-ipngwg-2292bis-02.txt [Page 25]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 int on = 1; setsockopt(fd, IPPROTO_IPV6, IPV6_RECVPKTINFO, &on, sizeof(on)); setsockopt(fd, IPPROTO_IPV6, IPV6_RECVHOPLIMIT, &on, sizeof(on)); setsockopt(fd, IPPROTO_IPV6, IPV6_RECVRTHDR, &on, sizeof(on)); setsockopt(fd, IPPROTO_IPV6, IPV6_RECVHOPOPTS, &on, sizeof(on)); setsockopt(fd, IPPROTO_IPV6, IPV6_RECVDSTOPTS, &on, sizeof(on)); setsockopt(fd, IPPROTO_IPV6, IPV6_RECVRTHDRDSTOPTS, &on, sizeof(on)); When any of these options are enabled, the corresponding data is returned as control information by recvmsg(), as one or more ancillary data objects. Two different mechanisms exist for sending this optional information: 1. Using setsockopt to specify the option content for a socket. These are known an "sticky" options since they affect all transmitted packets on the socket until either the a new setsockopt is done or the options are overridden using ancillary data. 2. Using ancillary data to specify the option content for a single datagram. This only applies to datagram and raw sockets; not to TCP sockets. The three socket option parameters and the three cmsghdr fields that describe the options/ancillary data objects are summarized as: opt level/ optname/ optval/ cmsg_level cmsg_type cmsg_data[] ------------ ------------ ------------------------ IPPROTO_IPV6 IPV6_PKTINFO in6_pktinfo structure IPPROTO_IPV6 IPV6_HOPLIMIT int IPPROTO_IPV6 IPV6_NEXTHOP socket address structure IPPROTO_IPV6 IPV6_RTHDR ip6_rthdr structure IPPROTO_IPV6 IPV6_HOPOPTS ip6_hbh structure IPPROTO_IPV6 IPV6_DSTOPTS ip6_dest structure IPPROTO_IPV6 IPV6_RTHDRDSTOPTS ip6_dest structure All these options are described in detail in Section 6, 7, 8 and 9. All the constants beginning with IPV6_ are defined as a result of including the <netinet/in.h>. Issuing getsockopt() for the above options will return the stickydraft-ietf-ipngwg-2292bis-02.txt [Page 26]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 option value i.e. the value set with setsockopt(). If no sticky option value has been set getsockopt() will return the default value. Note: We intentionally use the same constant for the cmsg_level member as is used as the second argument to getsockopt() and setsockopt() (what is called the "level"), and the same constant for the cmsg_type member as is used as the third argument to getsockopt() and setsockopt() (what is called the "option name"). The application does not explicitly need to access the data structures for the Routing header option, Hop-by-Hop option, and Destination options, since the API to these features is through a set of inet6_rth_XXX() and inet6_opt_XXX() functions that we define in Section 8 and Section 10. Those functions simplify the interface to these features instead of requiring the application to know the intimate details of the extension header formats.4.1. TCP Implications It is not possible to use ancillary data to transmit the above options for TCP since there is not a one-to-one mapping between send operations and the TCP segments being transmitted. Instead an application can use setsockopt to specify them as sticky options. When the application uses setsockopt to specify the above options it is expected that TCP will start using the new information when sending segments. However, TCP may or may not use the new information when retransmitting segments that were originally sent when the old sticky options were in effect. Applications using TCP can use ancillary data (after enabling the desired IPV6_RECVxxx options) to receive the IPv6 and extension header information. However, since there is not a one-to-one mapping between received TCP segments and recv operations seen by the application, when different TCP segments have different IPv6 and extension headers the application might not be able to observe all received headers. For efficiency reasons it is recommended that a TCP implementation not send ancillary data items with every received segment but instead try to detect the points in the data stream when the requested IPv6 and extension header content changes and only send a single ancillary data item at the time of the change. Also, TCP should send ancillary data items at the start of the connection and when the application enables a new IPV6_RECVxxx option. For example, assume an application has enabled IPV6_RECVHOPLIMIT before a connection is established. Then the first recvmsg() would have an IPV6_HOPLIMIT item indicating the hop limit in the first data segment. Should the hoplimit in the received data segment change adraft-ietf-ipngwg-2292bis-02.txt [Page 27]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 subsequent recvmsg() will also have an IPV6_HOPLIMIT item. However, the application must be prepared to handle ancillary data items even though the hop limit did not change. Note that should the hop limit in received ACK-only segments be different than the hop limit in data segments the application might only be able to observe the hop limit in the received data segments. The above example was for hop limit but the application should be prepared to handle the corresponding behavior for the other option information. The above recvmsg() behavior allows the application to detect changes in the received IPv6 and extension headers without resorting to periodic getsockopt() calls.4.2. UDP and Raw Socket Implications The receive behavior for UDP and raw sockets is quite straightforward. After the application has enabled an IPV6_RECVxxx socket option it will receive ancillary data items for every recvmsg() call containing the requested information. However, if the information is not present in the packet the ancillary data item will not be included. For example, if the application enables IPV6_RECVRTHDR and a received datagram does not contain a Routing header there will not be an IPV6_RTHDR ancillary data item. Note that due to buffering in the socket implementation there might be some packets queued when an IPV6_RECVxxx option is enabled and they might not have the ancillary data information. For sending the application has the choice between using sticky options and ancillary data. The application can also use both having the sticky options specify the "default" and using ancillary data to override the default options. Note that if any ancillary data is specified in a call to sendmsg(), all of the sticky options are overridden for that datagram. For example, if the application has set IPV6_RTHDR using a sticky option and later passes IPV6_HOPLIMIT as ancillary data this will override the IPV6_RTHDR sticky option and no Routing header will be sent with that datagram.5. Extensions to Socket Ancillary Data This specification uses ancillary data as defined in Posix.1g which the following compatible extensions: - CMSG_NXTHDR has been extended to handle a NULL 2nd argument to mean "get the first header". See Section 22.3.2.draft-ietf-ipngwg-2292bis-02.txt [Page 28]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 - A new CMSG_SPACE macro is defined. It is used to determine how much space need to be allocated for an ancillary data item. See Section 22.3.4. - A new CMSG_LEN macro is defined. It returns the value to store in the cmsg_len member of the cmsghdr structure, taking into account any padding needed to satisfy alignment requirements. See Section 22.3.5.6. Packet Information There are four pieces of information that an application can specify for an outgoing packet using ancillary data: 1. the source IPv6 address, 2. the outgoing interface index, 3. the outgoing hop limit, and 4. the next hop address. Three similar pieces of information can be returned for a received packet as ancillary data: 1. the destination IPv6 address, 2. the arriving interface index, and 3. the arriving hop limit. The first two pieces of information are contained in an in6_pktinfo structure that is set with setsockopt() or sent as ancillary data with sendmsg() and received as ancillary data with recvmsg(). This structure is defined as a result of including the <netinet/in.h>. struct in6_pktinfo { struct in6_addr ipi6_addr; /* src/dst IPv6 address */ unsigned int ipi6_ifindex; /* send/recv interface index */ }; In the socket option and cmsghdr level will be IPPROTO_IPV6, the type will be IPV6_PKTINFO, and the first byte of the option value and cmsg_data[] will be the first byte of the in6_pktinfo structure. An application can clear any sticky IPV6_PKTINFO option by either doing a setsockopt for option with optlen being zero, or by doing a "regular" setsockopt with ipi6_addr being in6addr_any and ipi6_ifindex being zero. This information is returned as ancillary data by recvmsg() only if the application has enabled the IPV6_RECVPKTINFO socket option:draft-ietf-ipngwg-2292bis-02.txt [Page 29]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 int on = 1; setsockopt(fd, IPPROTO_IPV6, IPV6_RECVPKTINFO, &on, sizeof(on)); (Note: The hop limit is not contained in the in6_pktinfo structure for the following reason. Some UDP servers want to respond to client requests by sending their reply out the same interface on which the request was received and with the source IPv6 address of the reply equal to the destination IPv6 address of the request. To do this the application can enable just the IPV6_RECVPKTINFO socket option and then use the received control information from recvmsg() as the outgoing control information for sendmsg(). The application need not examine or modify the in6_pktinfo structure at all. But if the hop limit were contained in this structure, the application would have to parse the received control information and change the hop limit member, since the received hop limit is not the desired value for an outgoing packet.)6.1. Specifying/Receiving the Interface Interfaces on an IPv6 node are identified by a small positive integer, as described in Section 4 of [RFC-2553]. That document also describes a function to map an interface name to its interface index, a function to map an interface index to its interface name, and a function to return all the interface names and indexes. Notice from this document that no interface is ever assigned an index of 0. When specifying the outgoing interface, if the ipi6_ifindex value is 0, the kernel will choose the outgoing interface. If the application specifies an outgoing interface for a multicast packet, the interface specified by the ancillary data overrides any interface specified by the IPV6_MULTICAST_IF socket option (described in [RFC-2553]), for that call to sendmsg() only. When the IPV6_RECVPKTINFO socket option is enabled, the received interface index is always returned as the ipi6_ifindex member of the in6_pktinfo structure.6.2. Specifying/Receiving Source/Destination Address The source IPv6 address can be specified by calling bind() before each output operation, but supplying the source address together with the data requires less overhead (i.e., fewer system calls) and requires less state to be stored and protected in a multithreaded application.draft-ietf-ipngwg-2292bis-02.txt [Page 30]INTERNET-DRAFT Advanced Sockets API for IPv6 Nov. 7, 2000 When specifying the source IPv6 address as ancillary data, if the ipi6_addr member of the in6_pktinfo structure is the unspecified address (IN6ADDR_ANY_INIT or in6addr_any), then (a) if an address is currently bound to the socket, it is used as the source address, or (b) if no address is currently bound to the socket, the kernel will choose the source address. If the ipi6_addr member is not the unspecified address, but the socket has already bound a source address, then the ipi6_addr value overrides the already-bound source address for this output operation only. The kernel must verify that the requested source address is indeed a unicast address assigned to the node. When the in6_pktinfo structure is returned as ancillary data by recvmsg(), the ipi6_addr member contains the destination IPv6 address from the received packet.6.3. Specifying/Re
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -