18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-or-later */
28c2ecf20Sopenharmony_ci/*
38c2ecf20Sopenharmony_ci *  SR-IPv6 implementation
48c2ecf20Sopenharmony_ci *
58c2ecf20Sopenharmony_ci *  Author:
68c2ecf20Sopenharmony_ci *  David Lebrun <david.lebrun@uclouvain.be>
78c2ecf20Sopenharmony_ci */
88c2ecf20Sopenharmony_ci
98c2ecf20Sopenharmony_ci#ifndef _NET_SEG6_H
108c2ecf20Sopenharmony_ci#define _NET_SEG6_H
118c2ecf20Sopenharmony_ci
128c2ecf20Sopenharmony_ci#include <linux/net.h>
138c2ecf20Sopenharmony_ci#include <linux/ipv6.h>
148c2ecf20Sopenharmony_ci#include <linux/seg6.h>
158c2ecf20Sopenharmony_ci#include <linux/rhashtable-types.h>
168c2ecf20Sopenharmony_ci
178c2ecf20Sopenharmony_cistatic inline void update_csum_diff4(struct sk_buff *skb, __be32 from,
188c2ecf20Sopenharmony_ci				     __be32 to)
198c2ecf20Sopenharmony_ci{
208c2ecf20Sopenharmony_ci	__be32 diff[] = { ~from, to };
218c2ecf20Sopenharmony_ci
228c2ecf20Sopenharmony_ci	skb->csum = ~csum_partial((char *)diff, sizeof(diff), ~skb->csum);
238c2ecf20Sopenharmony_ci}
248c2ecf20Sopenharmony_ci
258c2ecf20Sopenharmony_cistatic inline void update_csum_diff16(struct sk_buff *skb, __be32 *from,
268c2ecf20Sopenharmony_ci				      __be32 *to)
278c2ecf20Sopenharmony_ci{
288c2ecf20Sopenharmony_ci	__be32 diff[] = {
298c2ecf20Sopenharmony_ci		~from[0], ~from[1], ~from[2], ~from[3],
308c2ecf20Sopenharmony_ci		to[0], to[1], to[2], to[3],
318c2ecf20Sopenharmony_ci	};
328c2ecf20Sopenharmony_ci
338c2ecf20Sopenharmony_ci	skb->csum = ~csum_partial((char *)diff, sizeof(diff), ~skb->csum);
348c2ecf20Sopenharmony_ci}
358c2ecf20Sopenharmony_ci
368c2ecf20Sopenharmony_cistruct seg6_pernet_data {
378c2ecf20Sopenharmony_ci	struct mutex lock;
388c2ecf20Sopenharmony_ci	struct in6_addr __rcu *tun_src;
398c2ecf20Sopenharmony_ci#ifdef CONFIG_IPV6_SEG6_HMAC
408c2ecf20Sopenharmony_ci	struct rhashtable hmac_infos;
418c2ecf20Sopenharmony_ci#endif
428c2ecf20Sopenharmony_ci};
438c2ecf20Sopenharmony_ci
448c2ecf20Sopenharmony_cistatic inline struct seg6_pernet_data *seg6_pernet(struct net *net)
458c2ecf20Sopenharmony_ci{
468c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6)
478c2ecf20Sopenharmony_ci	return net->ipv6.seg6_data;
488c2ecf20Sopenharmony_ci#else
498c2ecf20Sopenharmony_ci	return NULL;
508c2ecf20Sopenharmony_ci#endif
518c2ecf20Sopenharmony_ci}
528c2ecf20Sopenharmony_ci
538c2ecf20Sopenharmony_ciextern int seg6_init(void);
548c2ecf20Sopenharmony_ciextern void seg6_exit(void);
558c2ecf20Sopenharmony_ciextern int seg6_iptunnel_init(void);
568c2ecf20Sopenharmony_ciextern void seg6_iptunnel_exit(void);
578c2ecf20Sopenharmony_ciextern int seg6_local_init(void);
588c2ecf20Sopenharmony_ciextern void seg6_local_exit(void);
598c2ecf20Sopenharmony_ci
608c2ecf20Sopenharmony_ciextern bool seg6_validate_srh(struct ipv6_sr_hdr *srh, int len, bool reduced);
618c2ecf20Sopenharmony_ciextern int seg6_do_srh_encap(struct sk_buff *skb, struct ipv6_sr_hdr *osrh,
628c2ecf20Sopenharmony_ci			     int proto);
638c2ecf20Sopenharmony_ciextern int seg6_do_srh_inline(struct sk_buff *skb, struct ipv6_sr_hdr *osrh);
648c2ecf20Sopenharmony_ciextern int seg6_lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
658c2ecf20Sopenharmony_ci			       u32 tbl_id);
668c2ecf20Sopenharmony_ci#endif
67