18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */
28c2ecf20Sopenharmony_ci#include <linux/ipv6.h>
38c2ecf20Sopenharmony_ci#include <net/dsfield.h>
48c2ecf20Sopenharmony_ci#include <net/xfrm.h>
58c2ecf20Sopenharmony_ci
68c2ecf20Sopenharmony_ci#ifndef XFRM_INOUT_H
78c2ecf20Sopenharmony_ci#define XFRM_INOUT_H 1
88c2ecf20Sopenharmony_ci
98c2ecf20Sopenharmony_cistatic inline void xfrm4_extract_header(struct sk_buff *skb)
108c2ecf20Sopenharmony_ci{
118c2ecf20Sopenharmony_ci	const struct iphdr *iph = ip_hdr(skb);
128c2ecf20Sopenharmony_ci
138c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->ihl = sizeof(*iph);
148c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->id = iph->id;
158c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->frag_off = iph->frag_off;
168c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->tos = iph->tos;
178c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->ttl = iph->ttl;
188c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->optlen = iph->ihl * 4 - sizeof(*iph);
198c2ecf20Sopenharmony_ci	memset(XFRM_MODE_SKB_CB(skb)->flow_lbl, 0,
208c2ecf20Sopenharmony_ci	       sizeof(XFRM_MODE_SKB_CB(skb)->flow_lbl));
218c2ecf20Sopenharmony_ci}
228c2ecf20Sopenharmony_ci
238c2ecf20Sopenharmony_cistatic inline void xfrm6_extract_header(struct sk_buff *skb)
248c2ecf20Sopenharmony_ci{
258c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6)
268c2ecf20Sopenharmony_ci	struct ipv6hdr *iph = ipv6_hdr(skb);
278c2ecf20Sopenharmony_ci
288c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->ihl = sizeof(*iph);
298c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->id = 0;
308c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->frag_off = htons(IP_DF);
318c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->tos = ipv6_get_dsfield(iph);
328c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->ttl = iph->hop_limit;
338c2ecf20Sopenharmony_ci	XFRM_MODE_SKB_CB(skb)->optlen = 0;
348c2ecf20Sopenharmony_ci	memcpy(XFRM_MODE_SKB_CB(skb)->flow_lbl, iph->flow_lbl,
358c2ecf20Sopenharmony_ci	       sizeof(XFRM_MODE_SKB_CB(skb)->flow_lbl));
368c2ecf20Sopenharmony_ci#else
378c2ecf20Sopenharmony_ci	WARN_ON_ONCE(1);
388c2ecf20Sopenharmony_ci#endif
398c2ecf20Sopenharmony_ci}
408c2ecf20Sopenharmony_ci
418c2ecf20Sopenharmony_cistatic inline void xfrm6_beet_make_header(struct sk_buff *skb)
428c2ecf20Sopenharmony_ci{
438c2ecf20Sopenharmony_ci	struct ipv6hdr *iph = ipv6_hdr(skb);
448c2ecf20Sopenharmony_ci
458c2ecf20Sopenharmony_ci	iph->version = 6;
468c2ecf20Sopenharmony_ci
478c2ecf20Sopenharmony_ci	memcpy(iph->flow_lbl, XFRM_MODE_SKB_CB(skb)->flow_lbl,
488c2ecf20Sopenharmony_ci	       sizeof(iph->flow_lbl));
498c2ecf20Sopenharmony_ci	iph->nexthdr = XFRM_MODE_SKB_CB(skb)->protocol;
508c2ecf20Sopenharmony_ci
518c2ecf20Sopenharmony_ci	ipv6_change_dsfield(iph, 0, XFRM_MODE_SKB_CB(skb)->tos);
528c2ecf20Sopenharmony_ci	iph->hop_limit = XFRM_MODE_SKB_CB(skb)->ttl;
538c2ecf20Sopenharmony_ci}
548c2ecf20Sopenharmony_ci
558c2ecf20Sopenharmony_cistatic inline void xfrm4_beet_make_header(struct sk_buff *skb)
568c2ecf20Sopenharmony_ci{
578c2ecf20Sopenharmony_ci	struct iphdr *iph = ip_hdr(skb);
588c2ecf20Sopenharmony_ci
598c2ecf20Sopenharmony_ci	iph->ihl = 5;
608c2ecf20Sopenharmony_ci	iph->version = 4;
618c2ecf20Sopenharmony_ci
628c2ecf20Sopenharmony_ci	iph->protocol = XFRM_MODE_SKB_CB(skb)->protocol;
638c2ecf20Sopenharmony_ci	iph->tos = XFRM_MODE_SKB_CB(skb)->tos;
648c2ecf20Sopenharmony_ci
658c2ecf20Sopenharmony_ci	iph->id = XFRM_MODE_SKB_CB(skb)->id;
668c2ecf20Sopenharmony_ci	iph->frag_off = XFRM_MODE_SKB_CB(skb)->frag_off;
678c2ecf20Sopenharmony_ci	iph->ttl = XFRM_MODE_SKB_CB(skb)->ttl;
688c2ecf20Sopenharmony_ci}
698c2ecf20Sopenharmony_ci
708c2ecf20Sopenharmony_ci#endif
71