net/openvswitch/actions.c
Source file repositories/reference/linux-study-clean/net/openvswitch/actions.c
File Facts
- System
- Linux kernel
- Corpus path
net/openvswitch/actions.c- Extension
.c- Size
- 40502 bytes
- Lines
- 1599
- Domain
- Networking Core
- Bucket
- Sockets, Protocols, Packet Path, And Network Policy
- Inferred role
- Networking Core: implementation source
- Status
- source implementation candidate
Why This File Exists
Networking stack implementation surface: socket APIs, protocol dispatch, packet flow, routing, filtering, and network namespaces.
- Networking stack implementation surface: socket APIs, protocol dispatch, packet flow, routing, filtering, and network namespaces.
- Touches user memory; correctness depends on fault-safe copying and privilege boundary handling.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/skbuff.hlinux/in.hlinux/ip.hlinux/openvswitch.hlinux/sctp.hlinux/tcp.hlinux/udp.hlinux/in6.hlinux/if_arp.hlinux/if_vlan.hnet/dst.hnet/gso.hnet/ip.hnet/ipv6.hnet/ip6_fib.hnet/ip6_route.hnet/checksum.hnet/dsfield.hnet/mpls.hnet/psample.hnet/sctp/checksum.hdatapath.hdrop.hflow.hconntrack.hvport.hflow_netlink.hopenvswitch_trace.h
Detected Declarations
function action_fifo_initfunction action_fifo_is_emptyfunction invalidate_flow_keyfunction is_flow_key_validfunction push_mplsfunction pop_mplsfunction set_mplsfunction pop_vlanfunction push_vlanfunction ether_addr_copy_maskedfunction set_eth_addrfunction pop_ethfunction push_ethfunction push_nshfunction pop_nshfunction update_ip_l4_checksumfunction set_ip_addrfunction update_ipv6_checksumfunction mask_ipv6_addrfunction set_ipv6_addrfunction set_ipv6_dsfieldfunction set_ipv6_flfunction set_ipv6_ttlfunction set_ip_ttlfunction set_ipv4function is_ipv6_mask_nonzerofunction set_ipv6function set_tp_portfunction set_udpfunction set_tcpfunction set_sctpfunction ovs_vport_outputfunction ovs_dst_get_mtufunction ovs_vport_outputfunction ovs_fragmentfunction do_outputfunction output_userspacefunction nla_for_each_nestedfunction dec_ttl_exception_handlerfunction samplefunction clonefunction execute_hashfunction execute_set_actionfunction execute_masked_set_actionfunction execute_recircfunction execute_check_pkt_lenfunction execute_dec_ttlfunction execute_psample
Annotated Snippet
if (likely(transport_len >= sizeof(struct udphdr))) {
struct udphdr *uh = udp_hdr(skb);
if (uh->check || skb->ip_summed == CHECKSUM_PARTIAL) {
inet_proto_csum_replace4(&uh->check, skb,
addr, new_addr, true);
if (!uh->check)
uh->check = CSUM_MANGLED_0;
}
}
}
}
static void set_ip_addr(struct sk_buff *skb, struct iphdr *nh,
__be32 *addr, __be32 new_addr)
{
update_ip_l4_checksum(skb, nh, *addr, new_addr);
csum_replace4(&nh->check, *addr, new_addr);
skb_clear_hash(skb);
ovs_ct_clear(skb, NULL);
*addr = new_addr;
}
static void update_ipv6_checksum(struct sk_buff *skb, u8 l4_proto,
__be32 addr[4], const __be32 new_addr[4])
{
int transport_len = skb->len - skb_transport_offset(skb);
if (l4_proto == NEXTHDR_TCP) {
if (likely(transport_len >= sizeof(struct tcphdr)))
inet_proto_csum_replace16(&tcp_hdr(skb)->check, skb,
addr, new_addr, true);
} else if (l4_proto == NEXTHDR_UDP) {
if (likely(transport_len >= sizeof(struct udphdr))) {
struct udphdr *uh = udp_hdr(skb);
if (uh->check || skb->ip_summed == CHECKSUM_PARTIAL) {
inet_proto_csum_replace16(&uh->check, skb,
addr, new_addr, true);
if (!uh->check)
uh->check = CSUM_MANGLED_0;
}
}
} else if (l4_proto == NEXTHDR_ICMP) {
if (likely(transport_len >= sizeof(struct icmp6hdr)))
inet_proto_csum_replace16(&icmp6_hdr(skb)->icmp6_cksum,
skb, addr, new_addr, true);
}
}
static void mask_ipv6_addr(const __be32 old[4], const __be32 addr[4],
const __be32 mask[4], __be32 masked[4])
{
masked[0] = OVS_MASKED(old[0], addr[0], mask[0]);
masked[1] = OVS_MASKED(old[1], addr[1], mask[1]);
masked[2] = OVS_MASKED(old[2], addr[2], mask[2]);
masked[3] = OVS_MASKED(old[3], addr[3], mask[3]);
}
static void set_ipv6_addr(struct sk_buff *skb, u8 l4_proto,
__be32 addr[4], const __be32 new_addr[4],
bool recalculate_csum)
{
if (recalculate_csum)
update_ipv6_checksum(skb, l4_proto, addr, new_addr);
skb_clear_hash(skb);
ovs_ct_clear(skb, NULL);
memcpy(addr, new_addr, sizeof(__be32[4]));
}
static void set_ipv6_dsfield(struct sk_buff *skb, struct ipv6hdr *nh, u8 ipv6_tclass, u8 mask)
{
u8 old_ipv6_tclass = ipv6_get_dsfield(nh);
ipv6_tclass = OVS_MASKED(old_ipv6_tclass, ipv6_tclass, mask);
if (skb->ip_summed == CHECKSUM_COMPLETE)
csum_replace(&skb->csum, (__force __wsum)(old_ipv6_tclass << 12),
(__force __wsum)(ipv6_tclass << 12));
ipv6_change_dsfield(nh, ~mask, ipv6_tclass);
}
static void set_ipv6_fl(struct sk_buff *skb, struct ipv6hdr *nh, u32 fl, u32 mask)
{
u32 ofl;
ofl = nh->flow_lbl[0] << 16 | nh->flow_lbl[1] << 8 | nh->flow_lbl[2];
fl = OVS_MASKED(ofl, fl, mask);
Annotation
- Immediate include surface: `linux/skbuff.h`, `linux/in.h`, `linux/ip.h`, `linux/openvswitch.h`, `linux/sctp.h`, `linux/tcp.h`, `linux/udp.h`, `linux/in6.h`.
- Detected declarations: `function action_fifo_init`, `function action_fifo_is_empty`, `function invalidate_flow_key`, `function is_flow_key_valid`, `function push_mpls`, `function pop_mpls`, `function set_mpls`, `function pop_vlan`, `function push_vlan`, `function ether_addr_copy_masked`.
- Atlas domain: Networking Core / Sockets, Protocols, Packet Path, And Network Policy.
- Implementation status: source implementation candidate.
- This snippet crosses the user/kernel memory boundary; validate fault handling and access checks before translating the pattern.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.