18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-or-later */
28c2ecf20Sopenharmony_ci/*
38c2ecf20Sopenharmony_ci * INET		An implementation of the TCP/IP protocol suite for the LINUX
48c2ecf20Sopenharmony_ci *		operating system.  INET is implemented using the  BSD Socket
58c2ecf20Sopenharmony_ci *		interface as the means of communication with the user level.
68c2ecf20Sopenharmony_ci *
78c2ecf20Sopenharmony_ci *		Definitions for inet_sock
88c2ecf20Sopenharmony_ci *
98c2ecf20Sopenharmony_ci * Authors:	Many, reorganised here by
108c2ecf20Sopenharmony_ci * 		Arnaldo Carvalho de Melo <acme@mandriva.com>
118c2ecf20Sopenharmony_ci */
128c2ecf20Sopenharmony_ci#ifndef _INET_SOCK_H
138c2ecf20Sopenharmony_ci#define _INET_SOCK_H
148c2ecf20Sopenharmony_ci
158c2ecf20Sopenharmony_ci#include <linux/bitops.h>
168c2ecf20Sopenharmony_ci#include <linux/string.h>
178c2ecf20Sopenharmony_ci#include <linux/types.h>
188c2ecf20Sopenharmony_ci#include <linux/jhash.h>
198c2ecf20Sopenharmony_ci#include <linux/netdevice.h>
208c2ecf20Sopenharmony_ci
218c2ecf20Sopenharmony_ci#include <net/flow.h>
228c2ecf20Sopenharmony_ci#include <net/sock.h>
238c2ecf20Sopenharmony_ci#include <net/request_sock.h>
248c2ecf20Sopenharmony_ci#include <net/netns/hash.h>
258c2ecf20Sopenharmony_ci#include <net/tcp_states.h>
268c2ecf20Sopenharmony_ci#include <net/l3mdev.h>
278c2ecf20Sopenharmony_ci
288c2ecf20Sopenharmony_ci/** struct ip_options - IP Options
298c2ecf20Sopenharmony_ci *
308c2ecf20Sopenharmony_ci * @faddr - Saved first hop address
318c2ecf20Sopenharmony_ci * @nexthop - Saved nexthop address in LSRR and SSRR
328c2ecf20Sopenharmony_ci * @is_strictroute - Strict source route
338c2ecf20Sopenharmony_ci * @srr_is_hit - Packet destination addr was our one
348c2ecf20Sopenharmony_ci * @is_changed - IP checksum more not valid
358c2ecf20Sopenharmony_ci * @rr_needaddr - Need to record addr of outgoing dev
368c2ecf20Sopenharmony_ci * @ts_needtime - Need to record timestamp
378c2ecf20Sopenharmony_ci * @ts_needaddr - Need to record addr of outgoing dev
388c2ecf20Sopenharmony_ci */
398c2ecf20Sopenharmony_cistruct ip_options {
408c2ecf20Sopenharmony_ci	__be32		faddr;
418c2ecf20Sopenharmony_ci	__be32		nexthop;
428c2ecf20Sopenharmony_ci	unsigned char	optlen;
438c2ecf20Sopenharmony_ci	unsigned char	srr;
448c2ecf20Sopenharmony_ci	unsigned char	rr;
458c2ecf20Sopenharmony_ci	unsigned char	ts;
468c2ecf20Sopenharmony_ci	unsigned char	is_strictroute:1,
478c2ecf20Sopenharmony_ci			srr_is_hit:1,
488c2ecf20Sopenharmony_ci			is_changed:1,
498c2ecf20Sopenharmony_ci			rr_needaddr:1,
508c2ecf20Sopenharmony_ci			ts_needtime:1,
518c2ecf20Sopenharmony_ci			ts_needaddr:1;
528c2ecf20Sopenharmony_ci	unsigned char	router_alert;
538c2ecf20Sopenharmony_ci	unsigned char	cipso;
548c2ecf20Sopenharmony_ci	unsigned char	__pad2;
558c2ecf20Sopenharmony_ci	unsigned char	__data[];
568c2ecf20Sopenharmony_ci};
578c2ecf20Sopenharmony_ci
588c2ecf20Sopenharmony_cistruct ip_options_rcu {
598c2ecf20Sopenharmony_ci	struct rcu_head rcu;
608c2ecf20Sopenharmony_ci	struct ip_options opt;
618c2ecf20Sopenharmony_ci};
628c2ecf20Sopenharmony_ci
638c2ecf20Sopenharmony_cistruct ip_options_data {
648c2ecf20Sopenharmony_ci	struct ip_options_rcu	opt;
658c2ecf20Sopenharmony_ci	char			data[40];
668c2ecf20Sopenharmony_ci};
678c2ecf20Sopenharmony_ci
688c2ecf20Sopenharmony_cistruct inet_request_sock {
698c2ecf20Sopenharmony_ci	struct request_sock	req;
708c2ecf20Sopenharmony_ci#define ir_loc_addr		req.__req_common.skc_rcv_saddr
718c2ecf20Sopenharmony_ci#define ir_rmt_addr		req.__req_common.skc_daddr
728c2ecf20Sopenharmony_ci#define ir_num			req.__req_common.skc_num
738c2ecf20Sopenharmony_ci#define ir_rmt_port		req.__req_common.skc_dport
748c2ecf20Sopenharmony_ci#define ir_v6_rmt_addr		req.__req_common.skc_v6_daddr
758c2ecf20Sopenharmony_ci#define ir_v6_loc_addr		req.__req_common.skc_v6_rcv_saddr
768c2ecf20Sopenharmony_ci#define ir_iif			req.__req_common.skc_bound_dev_if
778c2ecf20Sopenharmony_ci#define ir_cookie		req.__req_common.skc_cookie
788c2ecf20Sopenharmony_ci#define ireq_net		req.__req_common.skc_net
798c2ecf20Sopenharmony_ci#define ireq_state		req.__req_common.skc_state
808c2ecf20Sopenharmony_ci#define ireq_family		req.__req_common.skc_family
818c2ecf20Sopenharmony_ci
828c2ecf20Sopenharmony_ci	u16			snd_wscale : 4,
838c2ecf20Sopenharmony_ci				rcv_wscale : 4,
848c2ecf20Sopenharmony_ci				tstamp_ok  : 1,
858c2ecf20Sopenharmony_ci				sack_ok	   : 1,
868c2ecf20Sopenharmony_ci				wscale_ok  : 1,
878c2ecf20Sopenharmony_ci				ecn_ok	   : 1,
888c2ecf20Sopenharmony_ci				acked	   : 1,
898c2ecf20Sopenharmony_ci				no_srccheck: 1,
908c2ecf20Sopenharmony_ci				smc_ok	   : 1;
918c2ecf20Sopenharmony_ci	u32                     ir_mark;
928c2ecf20Sopenharmony_ci	union {
938c2ecf20Sopenharmony_ci		struct ip_options_rcu __rcu	*ireq_opt;
948c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6)
958c2ecf20Sopenharmony_ci		struct {
968c2ecf20Sopenharmony_ci			struct ipv6_txoptions	*ipv6_opt;
978c2ecf20Sopenharmony_ci			struct sk_buff		*pktopts;
988c2ecf20Sopenharmony_ci		};
998c2ecf20Sopenharmony_ci#endif
1008c2ecf20Sopenharmony_ci	};
1018c2ecf20Sopenharmony_ci};
1028c2ecf20Sopenharmony_ci
1038c2ecf20Sopenharmony_cistatic inline struct inet_request_sock *inet_rsk(const struct request_sock *sk)
1048c2ecf20Sopenharmony_ci{
1058c2ecf20Sopenharmony_ci	return (struct inet_request_sock *)sk;
1068c2ecf20Sopenharmony_ci}
1078c2ecf20Sopenharmony_ci
1088c2ecf20Sopenharmony_cistatic inline u32 inet_request_mark(const struct sock *sk, struct sk_buff *skb)
1098c2ecf20Sopenharmony_ci{
1108c2ecf20Sopenharmony_ci	if (!sk->sk_mark &&
1118c2ecf20Sopenharmony_ci	    READ_ONCE(sock_net(sk)->ipv4.sysctl_tcp_fwmark_accept))
1128c2ecf20Sopenharmony_ci		return skb->mark;
1138c2ecf20Sopenharmony_ci
1148c2ecf20Sopenharmony_ci	return sk->sk_mark;
1158c2ecf20Sopenharmony_ci}
1168c2ecf20Sopenharmony_ci
1178c2ecf20Sopenharmony_cistatic inline int inet_request_bound_dev_if(const struct sock *sk,
1188c2ecf20Sopenharmony_ci					    struct sk_buff *skb)
1198c2ecf20Sopenharmony_ci{
1208c2ecf20Sopenharmony_ci	int bound_dev_if = READ_ONCE(sk->sk_bound_dev_if);
1218c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_L3_MASTER_DEV
1228c2ecf20Sopenharmony_ci	struct net *net = sock_net(sk);
1238c2ecf20Sopenharmony_ci
1248c2ecf20Sopenharmony_ci	if (!bound_dev_if && READ_ONCE(net->ipv4.sysctl_tcp_l3mdev_accept))
1258c2ecf20Sopenharmony_ci		return l3mdev_master_ifindex_by_index(net, skb->skb_iif);
1268c2ecf20Sopenharmony_ci#endif
1278c2ecf20Sopenharmony_ci
1288c2ecf20Sopenharmony_ci	return bound_dev_if;
1298c2ecf20Sopenharmony_ci}
1308c2ecf20Sopenharmony_ci
1318c2ecf20Sopenharmony_cistatic inline int inet_sk_bound_l3mdev(const struct sock *sk)
1328c2ecf20Sopenharmony_ci{
1338c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_L3_MASTER_DEV
1348c2ecf20Sopenharmony_ci	struct net *net = sock_net(sk);
1358c2ecf20Sopenharmony_ci
1368c2ecf20Sopenharmony_ci	if (!READ_ONCE(net->ipv4.sysctl_tcp_l3mdev_accept))
1378c2ecf20Sopenharmony_ci		return l3mdev_master_ifindex_by_index(net,
1388c2ecf20Sopenharmony_ci						      sk->sk_bound_dev_if);
1398c2ecf20Sopenharmony_ci#endif
1408c2ecf20Sopenharmony_ci
1418c2ecf20Sopenharmony_ci	return 0;
1428c2ecf20Sopenharmony_ci}
1438c2ecf20Sopenharmony_ci
1448c2ecf20Sopenharmony_cistatic inline bool inet_bound_dev_eq(bool l3mdev_accept, int bound_dev_if,
1458c2ecf20Sopenharmony_ci				     int dif, int sdif)
1468c2ecf20Sopenharmony_ci{
1478c2ecf20Sopenharmony_ci	if (!bound_dev_if)
1488c2ecf20Sopenharmony_ci		return !sdif || l3mdev_accept;
1498c2ecf20Sopenharmony_ci	return bound_dev_if == dif || bound_dev_if == sdif;
1508c2ecf20Sopenharmony_ci}
1518c2ecf20Sopenharmony_ci
1528c2ecf20Sopenharmony_cistatic inline bool inet_sk_bound_dev_eq(struct net *net, int bound_dev_if,
1538c2ecf20Sopenharmony_ci					int dif, int sdif)
1548c2ecf20Sopenharmony_ci{
1558c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_NET_L3_MASTER_DEV)
1568c2ecf20Sopenharmony_ci	return inet_bound_dev_eq(!!READ_ONCE(net->ipv4.sysctl_tcp_l3mdev_accept),
1578c2ecf20Sopenharmony_ci				 bound_dev_if, dif, sdif);
1588c2ecf20Sopenharmony_ci#else
1598c2ecf20Sopenharmony_ci	return inet_bound_dev_eq(true, bound_dev_if, dif, sdif);
1608c2ecf20Sopenharmony_ci#endif
1618c2ecf20Sopenharmony_ci}
1628c2ecf20Sopenharmony_ci
1638c2ecf20Sopenharmony_cistruct inet_cork {
1648c2ecf20Sopenharmony_ci	unsigned int		flags;
1658c2ecf20Sopenharmony_ci	__be32			addr;
1668c2ecf20Sopenharmony_ci	struct ip_options	*opt;
1678c2ecf20Sopenharmony_ci	unsigned int		fragsize;
1688c2ecf20Sopenharmony_ci	int			length; /* Total length of all frames */
1698c2ecf20Sopenharmony_ci	struct dst_entry	*dst;
1708c2ecf20Sopenharmony_ci	u8			tx_flags;
1718c2ecf20Sopenharmony_ci	__u8			ttl;
1728c2ecf20Sopenharmony_ci	__s16			tos;
1738c2ecf20Sopenharmony_ci	char			priority;
1748c2ecf20Sopenharmony_ci	__u16			gso_size;
1758c2ecf20Sopenharmony_ci	u64			transmit_time;
1768c2ecf20Sopenharmony_ci	u32			mark;
1778c2ecf20Sopenharmony_ci};
1788c2ecf20Sopenharmony_ci
1798c2ecf20Sopenharmony_cistruct inet_cork_full {
1808c2ecf20Sopenharmony_ci	struct inet_cork	base;
1818c2ecf20Sopenharmony_ci	struct flowi		fl;
1828c2ecf20Sopenharmony_ci};
1838c2ecf20Sopenharmony_ci
1848c2ecf20Sopenharmony_cistruct ip_mc_socklist;
1858c2ecf20Sopenharmony_cistruct ipv6_pinfo;
1868c2ecf20Sopenharmony_cistruct rtable;
1878c2ecf20Sopenharmony_ci
1888c2ecf20Sopenharmony_ci/** struct inet_sock - representation of INET sockets
1898c2ecf20Sopenharmony_ci *
1908c2ecf20Sopenharmony_ci * @sk - ancestor class
1918c2ecf20Sopenharmony_ci * @pinet6 - pointer to IPv6 control block
1928c2ecf20Sopenharmony_ci * @inet_daddr - Foreign IPv4 addr
1938c2ecf20Sopenharmony_ci * @inet_rcv_saddr - Bound local IPv4 addr
1948c2ecf20Sopenharmony_ci * @inet_dport - Destination port
1958c2ecf20Sopenharmony_ci * @inet_num - Local port
1968c2ecf20Sopenharmony_ci * @inet_saddr - Sending source
1978c2ecf20Sopenharmony_ci * @uc_ttl - Unicast TTL
1988c2ecf20Sopenharmony_ci * @inet_sport - Source port
1998c2ecf20Sopenharmony_ci * @inet_id - ID counter for DF pkts
2008c2ecf20Sopenharmony_ci * @tos - TOS
2018c2ecf20Sopenharmony_ci * @mc_ttl - Multicasting TTL
2028c2ecf20Sopenharmony_ci * @is_icsk - is this an inet_connection_sock?
2038c2ecf20Sopenharmony_ci * @uc_index - Unicast outgoing device index
2048c2ecf20Sopenharmony_ci * @mc_index - Multicast device index
2058c2ecf20Sopenharmony_ci * @mc_list - Group array
2068c2ecf20Sopenharmony_ci * @cork - info to build ip hdr on each ip frag while socket is corked
2078c2ecf20Sopenharmony_ci */
2088c2ecf20Sopenharmony_cistruct inet_sock {
2098c2ecf20Sopenharmony_ci	/* sk and pinet6 has to be the first two members of inet_sock */
2108c2ecf20Sopenharmony_ci	struct sock		sk;
2118c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6)
2128c2ecf20Sopenharmony_ci	struct ipv6_pinfo	*pinet6;
2138c2ecf20Sopenharmony_ci#endif
2148c2ecf20Sopenharmony_ci	/* Socket demultiplex comparisons on incoming packets. */
2158c2ecf20Sopenharmony_ci#define inet_daddr		sk.__sk_common.skc_daddr
2168c2ecf20Sopenharmony_ci#define inet_rcv_saddr		sk.__sk_common.skc_rcv_saddr
2178c2ecf20Sopenharmony_ci#define inet_dport		sk.__sk_common.skc_dport
2188c2ecf20Sopenharmony_ci#define inet_num		sk.__sk_common.skc_num
2198c2ecf20Sopenharmony_ci
2208c2ecf20Sopenharmony_ci	__be32			inet_saddr;
2218c2ecf20Sopenharmony_ci	__s16			uc_ttl;
2228c2ecf20Sopenharmony_ci	__u16			cmsg_flags;
2238c2ecf20Sopenharmony_ci	__be16			inet_sport;
2248c2ecf20Sopenharmony_ci	__u16			inet_id;
2258c2ecf20Sopenharmony_ci
2268c2ecf20Sopenharmony_ci	struct ip_options_rcu __rcu	*inet_opt;
2278c2ecf20Sopenharmony_ci	int			rx_dst_ifindex;
2288c2ecf20Sopenharmony_ci	__u8			tos;
2298c2ecf20Sopenharmony_ci	__u8			min_ttl;
2308c2ecf20Sopenharmony_ci	__u8			mc_ttl;
2318c2ecf20Sopenharmony_ci	__u8			pmtudisc;
2328c2ecf20Sopenharmony_ci	__u8			recverr:1,
2338c2ecf20Sopenharmony_ci				is_icsk:1,
2348c2ecf20Sopenharmony_ci				freebind:1,
2358c2ecf20Sopenharmony_ci				hdrincl:1,
2368c2ecf20Sopenharmony_ci				mc_loop:1,
2378c2ecf20Sopenharmony_ci				transparent:1,
2388c2ecf20Sopenharmony_ci				mc_all:1,
2398c2ecf20Sopenharmony_ci				nodefrag:1;
2408c2ecf20Sopenharmony_ci	__u8			bind_address_no_port:1,
2418c2ecf20Sopenharmony_ci				recverr_rfc4884:1,
2428c2ecf20Sopenharmony_ci				defer_connect:1; /* Indicates that fastopen_connect is set
2438c2ecf20Sopenharmony_ci						  * and cookie exists so we defer connect
2448c2ecf20Sopenharmony_ci						  * until first data frame is written
2458c2ecf20Sopenharmony_ci						  */
2468c2ecf20Sopenharmony_ci	__u8			rcv_tos;
2478c2ecf20Sopenharmony_ci	__u8			convert_csum;
2488c2ecf20Sopenharmony_ci	int			uc_index;
2498c2ecf20Sopenharmony_ci	int			mc_index;
2508c2ecf20Sopenharmony_ci	__be32			mc_addr;
2518c2ecf20Sopenharmony_ci	struct ip_mc_socklist __rcu	*mc_list;
2528c2ecf20Sopenharmony_ci	struct inet_cork_full	cork;
2538c2ecf20Sopenharmony_ci};
2548c2ecf20Sopenharmony_ci
2558c2ecf20Sopenharmony_ci#define IPCORK_OPT	1	/* ip-options has been held in ipcork.opt */
2568c2ecf20Sopenharmony_ci#define IPCORK_ALLFRAG	2	/* always fragment (for ipv6 for now) */
2578c2ecf20Sopenharmony_ci
2588c2ecf20Sopenharmony_ci/* cmsg flags for inet */
2598c2ecf20Sopenharmony_ci#define IP_CMSG_PKTINFO		BIT(0)
2608c2ecf20Sopenharmony_ci#define IP_CMSG_TTL		BIT(1)
2618c2ecf20Sopenharmony_ci#define IP_CMSG_TOS		BIT(2)
2628c2ecf20Sopenharmony_ci#define IP_CMSG_RECVOPTS	BIT(3)
2638c2ecf20Sopenharmony_ci#define IP_CMSG_RETOPTS		BIT(4)
2648c2ecf20Sopenharmony_ci#define IP_CMSG_PASSSEC		BIT(5)
2658c2ecf20Sopenharmony_ci#define IP_CMSG_ORIGDSTADDR	BIT(6)
2668c2ecf20Sopenharmony_ci#define IP_CMSG_CHECKSUM	BIT(7)
2678c2ecf20Sopenharmony_ci#define IP_CMSG_RECVFRAGSIZE	BIT(8)
2688c2ecf20Sopenharmony_ci
2698c2ecf20Sopenharmony_ci/**
2708c2ecf20Sopenharmony_ci * sk_to_full_sk - Access to a full socket
2718c2ecf20Sopenharmony_ci * @sk: pointer to a socket
2728c2ecf20Sopenharmony_ci *
2738c2ecf20Sopenharmony_ci * SYNACK messages might be attached to request sockets.
2748c2ecf20Sopenharmony_ci * Some places want to reach the listener in this case.
2758c2ecf20Sopenharmony_ci */
2768c2ecf20Sopenharmony_cistatic inline struct sock *sk_to_full_sk(struct sock *sk)
2778c2ecf20Sopenharmony_ci{
2788c2ecf20Sopenharmony_ci#ifdef CONFIG_INET
2798c2ecf20Sopenharmony_ci	if (sk && sk->sk_state == TCP_NEW_SYN_RECV)
2808c2ecf20Sopenharmony_ci		sk = inet_reqsk(sk)->rsk_listener;
2818c2ecf20Sopenharmony_ci#endif
2828c2ecf20Sopenharmony_ci	return sk;
2838c2ecf20Sopenharmony_ci}
2848c2ecf20Sopenharmony_ci
2858c2ecf20Sopenharmony_ci/* sk_to_full_sk() variant with a const argument */
2868c2ecf20Sopenharmony_cistatic inline const struct sock *sk_const_to_full_sk(const struct sock *sk)
2878c2ecf20Sopenharmony_ci{
2888c2ecf20Sopenharmony_ci#ifdef CONFIG_INET
2898c2ecf20Sopenharmony_ci	if (sk && sk->sk_state == TCP_NEW_SYN_RECV)
2908c2ecf20Sopenharmony_ci		sk = ((const struct request_sock *)sk)->rsk_listener;
2918c2ecf20Sopenharmony_ci#endif
2928c2ecf20Sopenharmony_ci	return sk;
2938c2ecf20Sopenharmony_ci}
2948c2ecf20Sopenharmony_ci
2958c2ecf20Sopenharmony_cistatic inline struct sock *skb_to_full_sk(const struct sk_buff *skb)
2968c2ecf20Sopenharmony_ci{
2978c2ecf20Sopenharmony_ci	return sk_to_full_sk(skb->sk);
2988c2ecf20Sopenharmony_ci}
2998c2ecf20Sopenharmony_ci
3008c2ecf20Sopenharmony_cistatic inline struct inet_sock *inet_sk(const struct sock *sk)
3018c2ecf20Sopenharmony_ci{
3028c2ecf20Sopenharmony_ci	return (struct inet_sock *)sk;
3038c2ecf20Sopenharmony_ci}
3048c2ecf20Sopenharmony_ci
3058c2ecf20Sopenharmony_cistatic inline void __inet_sk_copy_descendant(struct sock *sk_to,
3068c2ecf20Sopenharmony_ci					     const struct sock *sk_from,
3078c2ecf20Sopenharmony_ci					     const int ancestor_size)
3088c2ecf20Sopenharmony_ci{
3098c2ecf20Sopenharmony_ci	memcpy(inet_sk(sk_to) + 1, inet_sk(sk_from) + 1,
3108c2ecf20Sopenharmony_ci	       sk_from->sk_prot->obj_size - ancestor_size);
3118c2ecf20Sopenharmony_ci}
3128c2ecf20Sopenharmony_ci
3138c2ecf20Sopenharmony_ciint inet_sk_rebuild_header(struct sock *sk);
3148c2ecf20Sopenharmony_ci
3158c2ecf20Sopenharmony_ci/**
3168c2ecf20Sopenharmony_ci * inet_sk_state_load - read sk->sk_state for lockless contexts
3178c2ecf20Sopenharmony_ci * @sk: socket pointer
3188c2ecf20Sopenharmony_ci *
3198c2ecf20Sopenharmony_ci * Paired with inet_sk_state_store(). Used in places we don't hold socket lock:
3208c2ecf20Sopenharmony_ci * tcp_diag_get_info(), tcp_get_info(), tcp_poll(), get_tcp4_sock() ...
3218c2ecf20Sopenharmony_ci */
3228c2ecf20Sopenharmony_cistatic inline int inet_sk_state_load(const struct sock *sk)
3238c2ecf20Sopenharmony_ci{
3248c2ecf20Sopenharmony_ci	/* state change might impact lockless readers. */
3258c2ecf20Sopenharmony_ci	return smp_load_acquire(&sk->sk_state);
3268c2ecf20Sopenharmony_ci}
3278c2ecf20Sopenharmony_ci
3288c2ecf20Sopenharmony_ci/**
3298c2ecf20Sopenharmony_ci * inet_sk_state_store - update sk->sk_state
3308c2ecf20Sopenharmony_ci * @sk: socket pointer
3318c2ecf20Sopenharmony_ci * @newstate: new state
3328c2ecf20Sopenharmony_ci *
3338c2ecf20Sopenharmony_ci * Paired with inet_sk_state_load(). Should be used in contexts where
3348c2ecf20Sopenharmony_ci * state change might impact lockless readers.
3358c2ecf20Sopenharmony_ci */
3368c2ecf20Sopenharmony_civoid inet_sk_state_store(struct sock *sk, int newstate);
3378c2ecf20Sopenharmony_ci
3388c2ecf20Sopenharmony_civoid inet_sk_set_state(struct sock *sk, int state);
3398c2ecf20Sopenharmony_ci
3408c2ecf20Sopenharmony_cistatic inline unsigned int __inet_ehashfn(const __be32 laddr,
3418c2ecf20Sopenharmony_ci					  const __u16 lport,
3428c2ecf20Sopenharmony_ci					  const __be32 faddr,
3438c2ecf20Sopenharmony_ci					  const __be16 fport,
3448c2ecf20Sopenharmony_ci					  u32 initval)
3458c2ecf20Sopenharmony_ci{
3468c2ecf20Sopenharmony_ci	return jhash_3words((__force __u32) laddr,
3478c2ecf20Sopenharmony_ci			    (__force __u32) faddr,
3488c2ecf20Sopenharmony_ci			    ((__u32) lport) << 16 | (__force __u32)fport,
3498c2ecf20Sopenharmony_ci			    initval);
3508c2ecf20Sopenharmony_ci}
3518c2ecf20Sopenharmony_ci
3528c2ecf20Sopenharmony_cistruct request_sock *inet_reqsk_alloc(const struct request_sock_ops *ops,
3538c2ecf20Sopenharmony_ci				      struct sock *sk_listener,
3548c2ecf20Sopenharmony_ci				      bool attach_listener);
3558c2ecf20Sopenharmony_ci
3568c2ecf20Sopenharmony_cistatic inline __u8 inet_sk_flowi_flags(const struct sock *sk)
3578c2ecf20Sopenharmony_ci{
3588c2ecf20Sopenharmony_ci	__u8 flags = 0;
3598c2ecf20Sopenharmony_ci
3608c2ecf20Sopenharmony_ci	if (inet_sk(sk)->transparent || inet_sk(sk)->hdrincl)
3618c2ecf20Sopenharmony_ci		flags |= FLOWI_FLAG_ANYSRC;
3628c2ecf20Sopenharmony_ci	return flags;
3638c2ecf20Sopenharmony_ci}
3648c2ecf20Sopenharmony_ci
3658c2ecf20Sopenharmony_cistatic inline void inet_inc_convert_csum(struct sock *sk)
3668c2ecf20Sopenharmony_ci{
3678c2ecf20Sopenharmony_ci	inet_sk(sk)->convert_csum++;
3688c2ecf20Sopenharmony_ci}
3698c2ecf20Sopenharmony_ci
3708c2ecf20Sopenharmony_cistatic inline void inet_dec_convert_csum(struct sock *sk)
3718c2ecf20Sopenharmony_ci{
3728c2ecf20Sopenharmony_ci	if (inet_sk(sk)->convert_csum > 0)
3738c2ecf20Sopenharmony_ci		inet_sk(sk)->convert_csum--;
3748c2ecf20Sopenharmony_ci}
3758c2ecf20Sopenharmony_ci
3768c2ecf20Sopenharmony_cistatic inline bool inet_get_convert_csum(struct sock *sk)
3778c2ecf20Sopenharmony_ci{
3788c2ecf20Sopenharmony_ci	return !!inet_sk(sk)->convert_csum;
3798c2ecf20Sopenharmony_ci}
3808c2ecf20Sopenharmony_ci
3818c2ecf20Sopenharmony_ci
3828c2ecf20Sopenharmony_cistatic inline bool inet_can_nonlocal_bind(struct net *net,
3838c2ecf20Sopenharmony_ci					  struct inet_sock *inet)
3848c2ecf20Sopenharmony_ci{
3858c2ecf20Sopenharmony_ci	return READ_ONCE(net->ipv4.sysctl_ip_nonlocal_bind) ||
3868c2ecf20Sopenharmony_ci		inet->freebind || inet->transparent;
3878c2ecf20Sopenharmony_ci}
3888c2ecf20Sopenharmony_ci
3898c2ecf20Sopenharmony_ci#endif	/* _INET_SOCK_H */
390