The advanced API provides support for advanced applications that may
need knowledge of IPv6 headers. These applications commonly use raw
sockets to access IPv6 or ICMPv6 header fields. The advanced interface
provides the following:

Support for portable interfaces for applications that use raw
sockets under IPv6.

This enables the kernel to compute and store a checksum for output and
to verify the checksum on input. This relieves the application from
having to perform source address selection on all outgoing packets.
This socket option is disabled by default. You can explicitly disable
this option by setting the offset variable to -1.

Using IPv6 raw sockets, an application can access the following
information:

An ICMPv6 raw socket is a socket that is created by calling the
socket()
function with the
PF_INET6
,
SOCK_RAW
, and
IPPROTO_ICMPV6
arguments.

The kernel calculates and inserts the ICMPv6 checksum for all outbound
ICMPv6 packets and verifies the checksum for all received packets. If
the received checksum is incorrect, the packet is discarded.

Because ICMPv6 is a superset of ICMPv4, an ICMPv6 raw socket can
receive many more messages than an ICMPv4 raw socket. By default, when
you create an ICMPv6 raw socket, it passes all ICMPv6 message types to
an application. An application, however, does not need access to all
messages. An application can specify the ICMPv6 message types it wants
passed by creating an ICMPv6 filter.

The ICMPv6 filter has a datatype of
struct icmp6_filter
. Use
getsockopt()
to retrieve the current filter and
setsockopt()
to store the filter. For example, to enable filtering of ICMPv6
messages, use the
ICMP6_FILTER
option, as follows:

Source and destination IPv6 address, and sending and receiving interface

IPV6_RECVPKTINFO

IPV6_PKTINFO

Hop limit

IPV6_RECVHOPLIMIT

IPV6_HOPLIMIT

Routing header

IPV6_RECVRTHDR

IPV6_RTHDR

Hop-by-hop options

IPV6_RECVHOPOPTS

IPV6_HOPOPTS

Destination options

IPV6_RECVDSTOPTS

IPV6_DSTOPTS

The
recvmsg()
function returns the received data as one or more ancillary data
objects in a
cmsghdr
data structure.

To determine the value of a socket option, use the
getsockopt()
function with the corresponding option. If the
IPV6_RECVPKTINFO
option is not set, the function returns an
in6_pktinfo
data structure with
ipi6_addr
set to
in6addr_any
and
ipi6_addr
set to zero. For other options, the function returns an
option_len
value of zero if there is no option value.

An application can receive the following IPv6 header information as
ancillary data from incoming packets:

Destination IPv6 address

Interface index

Hop limit

The IPv6 address and interface index are contained in a
in6_pktinfo
data structure that is received as ancillary data with the
recvmsg()
function. The
in6_pktinfo
data structure is defined in IN.H. The tasks associated with the IPv6
header are:

Receiving an IPv6 address If the
IPV6_RECVPKTINFO
option is enabled, the
recvmsg()
function returns a
in6_pktinfo
data structure as ancillary data. The
ipi6_addr
member contains the destination IPv6 address from the received packet.
For TCP sockets, the destination address is the local address of the
connection.

Receiving an interface If the
IPV6_RECVPKTINFO
option is enabled, the
recvmsg()
function returns a
in6_pktinfo
data structure as ancillary data. The
ipi6_ifindex
member contains the interface index of the interface that received the
packet.

Receiving a hop limit If the
IPV6_RECVHOPLIMIT
option is enabled, the
recvmsg()
function returns a
cmsghdr
data structure as ancillary data. The
cmsg_type
member is
IPV6_HOPLIMIT
and the
cmsg_data[]
member contains the first byte of the integer hop limit.

The advanced Sockets API enables you to access the IPv6 routing header.
The routing header is an IPv6 extension header that enables an
application to perform source routing. The type 0 routing header
supports up to 127 intermediate nodes, or 128 hops.

Table 3-9 describes the sockets calls that an application uses to
build and examine routing headers.

Receiving a routing header To receive a routing header, an
application calls
setsockopt()
with the
IPV6_RECVRTHDR
option enabled. For each received routing header, the kernel passes
one ancillary data object in a
cmsghdr
structure with the
cmsg_type
member set to
IPV6_RTHDR
. An application processes a routing header by calling
inet6_rth_reverse()
,
inet6_rth_segments()
, and
inet6_rth_getaddr()
.

Sending a routing header To send a routing header, an
application specifies the header either as ancillary data in a call to
sendmsg()
or by calling
setsockopt()
. An application can remove a sticky routing header by calling
setsockopt()
for the
IPV6_RTHDR
option and specifying an option length of zero. When using
ancillary data, the application sets the
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_RTHDR
. Use the
inet6_rth_space()
,
inet6_rth_init()
, and
inet6_rth_add()
functions to build the routing header. When an application
specifies a routing header, the destination address specified in a call
to the
connect()
,
sendto()
, or
sendmsg()
function is the final destination of the datagram. Therefore, the
routing header contains the addresses of all intermediate nodes.
The order of extension headers is static; therefore, an application
can specify only one outgoing routing header.

The advanced Sockets API enables applications to access the following
IPv6 options headers:

Hop-by-hop header A single hop-by-hop options header can
contain a variable number of hop-by-hop options. Each option is encoded
with a type, length, and value (TLV). The application uses sticky
options or ancillary data to communicate this information with the
kernel.

Destination header
One or more destination options headers can contain a variable
number of destination options. A destination options header appearing
before a routing header is processed by the first and subsequent
destinations specified in the routing header. A destination option
appearing after the routing header is processed only by the final
destination. Each option is encoded with a type, length, and value
(TLV). The application uses sticky options or ancillary data to
communicate this information with the kernel.

For additional information about the alignment requirements of the
headers and ordering of the extensions headers, see RFC 2460.

Table 3-10 lists the sockets calls that an application uses to build
and examine hop-by-hop and destination headers.

Retrieves one component of the option content from the options header.

The tasks associated with the options headers are:

Receiving hop-by-hop options To receive a hop-by-hop options
header, an application calls
setsockopt()
with the
IPV6_RECVHOPOPTS
option enabled. When using ancillary data, the kernel passes a
hop-by-hop options header to the application and sets the
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_HOPOPTS
. An application retrieves these options by calling
inet6_opt_next()
,
inet6_opt_find()
, and
inet6_opt_get_val()
.

Sending hop-by-hop options
To send a hop-by-hop options header, an application specifies the
header either as ancillary data in a call to
sendmsg()
or by calling
setsockopt()
An application can remove a sticky hop-by-hop options header by calling
setsockopt()
for the
IPV6_HOPOPTS
option and specifying an option length of zero (0). When using
ancillary data, all hop-by-hop options are specified by a single
ancillary data object. The application sets
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_HOPOPTS
. Use the
inet6_opt_init()
,
inet6_opt_append()
,
inet6_opt_finish()
, and
inet6_opt_set_val()
calls to build the option header.

Receiving destination options
To receive a destination options header, an application calls
setsockopt()
with the
IPV6_RECVDSTOPTS
option enabled. The kernel passes each destination option to the
application as one ancillary data object and sets the
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_DSTOPTS
. An application processes these options by calling
inet6_opt_next()
,
inet6_opt_find()
, and
inet6_opt_get_val()
.

Sending destination options
To send a destination options header, an application specifies the
header either as ancillary data in a call to
sendmsg()
or by calling
setsockopt()
. An application can remove a sticky hop-by-hop options header by
calling
setsockopt()
for either the
IPV6_RTHDRDSTOPTS
or the
IPV6_DSTOPTS
option and specifying a option length of zero (0). The API assumes
that the extension headers are in order. Only one set of destination
options can precede a routing header and only one set of destination
options can follow a routing header. Each set can contain one or
more options, but each set is considered a single extension header.
When using ancillary data, the application passes a destination
options header to the kernel in one of the following ways:

For destination options that precede a routing header, the
application sets the
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_RTHDRDSTOPTS
. Any
setsockopt()
or ancillary data is ignored unless the application explicitly
specifies its own routing header.

For destination options that follow a routing header or when no
routing header is specified, the application sets the
cmsg_level
member to
IPPROTO_IPV6
and the
cmsg_type
member to
IPV6_DSTOPTS
.