|
// 14 bytes |
|
hdr.inner_eth.setValid(); |
|
hdr.inner_eth.dst_mac = meta.nat_inner_mac; |
|
hdr.inner_eth.src_mac = 0; |
|
hdr.inner_eth.ether_type = hdr.ethernet.ether_type; |
|
|
|
// 8 bytes |
|
hdr.udp.setValid(); |
|
hdr.udp.src_port = GENEVE_UDP_PORT; |
|
hdr.udp.dst_port = GENEVE_UDP_PORT; |
|
hdr.udp.hdr_length = udp_len; |
|
hdr.udp.checksum = 0; |
|
|
|
// 40 bytes |
|
hdr.ethernet.ether_type = ETHERTYPE_IPV6; |
|
hdr.ipv6.setValid(); |
|
hdr.ipv6.version = 6; |
|
hdr.ipv6.traffic_class = 0; |
|
hdr.ipv6.flow_label = 0; |
|
hdr.ipv6.payload_len = udp_len; |
|
hdr.ipv6.next_hdr = IPPROTO_UDP; |
|
hdr.ipv6.hop_limit = 255; |
|
hdr.ipv6.src_addr = 0; |
|
hdr.ipv6.dst_addr = meta.nat_ingress_tgt; |
I ran into this while writing up tests for ICMP generation in OPTE and double-checking what fields to expect in various cases -- the case in question being generating ICMP hairpins for traffic from the external network.
The lack of a useful source address makes it challenging/fiddly to ensure that inner ICMP packet-too-big traffic goes back via the switch the original packet came from. The switch will only decapsulate packets which have one of its switch addresses as the outer IPv6 destination, so mirroring the source/destination addresses on the encap will lead to unroutable packets. As a result we have to perform a V2B lookup on the inner destination to fill this field, which may return the address of the other switch.
A minor point is that the inner source mac could also be set to something like oxide_vpc::engine::overlay::TUNNEL_ENDPOINT_MAC (A8:40:25:77:77:77), for symmetry with how OPTE sends packets to boundary services.
dendrite/dpd/p4/sidecar.p4
Lines 507 to 530 in f9fba02
I ran into this while writing up tests for ICMP generation in OPTE and double-checking what fields to expect in various cases -- the case in question being generating ICMP hairpins for traffic from the external network.
The lack of a useful source address makes it challenging/fiddly to ensure that inner ICMP packet-too-big traffic goes back via the switch the original packet came from. The switch will only decapsulate packets which have one of its switch addresses as the outer IPv6 destination, so mirroring the source/destination addresses on the encap will lead to unroutable packets. As a result we have to perform a V2B lookup on the inner destination to fill this field, which may return the address of the other switch.
A minor point is that the inner source mac could also be set to something like
oxide_vpc::engine::overlay::TUNNEL_ENDPOINT_MAC(A8:40:25:77:77:77), for symmetry with how OPTE sends packets to boundary services.