cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

inet_sock.h (9946B)


      1/* SPDX-License-Identifier: GPL-2.0-or-later */
      2/*
      3 * INET		An implementation of the TCP/IP protocol suite for the LINUX
      4 *		operating system.  INET is implemented using the  BSD Socket
      5 *		interface as the means of communication with the user level.
      6 *
      7 *		Definitions for inet_sock
      8 *
      9 * Authors:	Many, reorganised here by
     10 * 		Arnaldo Carvalho de Melo <acme@mandriva.com>
     11 */
     12#ifndef _INET_SOCK_H
     13#define _INET_SOCK_H
     14
     15#include <linux/bitops.h>
     16#include <linux/string.h>
     17#include <linux/types.h>
     18#include <linux/jhash.h>
     19#include <linux/netdevice.h>
     20
     21#include <net/flow.h>
     22#include <net/sock.h>
     23#include <net/request_sock.h>
     24#include <net/netns/hash.h>
     25#include <net/tcp_states.h>
     26#include <net/l3mdev.h>
     27
     28/** struct ip_options - IP Options
     29 *
     30 * @faddr - Saved first hop address
     31 * @nexthop - Saved nexthop address in LSRR and SSRR
     32 * @is_strictroute - Strict source route
     33 * @srr_is_hit - Packet destination addr was our one
     34 * @is_changed - IP checksum more not valid
     35 * @rr_needaddr - Need to record addr of outgoing dev
     36 * @ts_needtime - Need to record timestamp
     37 * @ts_needaddr - Need to record addr of outgoing dev
     38 */
     39struct ip_options {
     40	__be32		faddr;
     41	__be32		nexthop;
     42	unsigned char	optlen;
     43	unsigned char	srr;
     44	unsigned char	rr;
     45	unsigned char	ts;
     46	unsigned char	is_strictroute:1,
     47			srr_is_hit:1,
     48			is_changed:1,
     49			rr_needaddr:1,
     50			ts_needtime:1,
     51			ts_needaddr:1;
     52	unsigned char	router_alert;
     53	unsigned char	cipso;
     54	unsigned char	__pad2;
     55	unsigned char	__data[];
     56};
     57
     58struct ip_options_rcu {
     59	struct rcu_head rcu;
     60	struct ip_options opt;
     61};
     62
     63struct ip_options_data {
     64	struct ip_options_rcu	opt;
     65	char			data[40];
     66};
     67
     68struct inet_request_sock {
     69	struct request_sock	req;
     70#define ir_loc_addr		req.__req_common.skc_rcv_saddr
     71#define ir_rmt_addr		req.__req_common.skc_daddr
     72#define ir_num			req.__req_common.skc_num
     73#define ir_rmt_port		req.__req_common.skc_dport
     74#define ir_v6_rmt_addr		req.__req_common.skc_v6_daddr
     75#define ir_v6_loc_addr		req.__req_common.skc_v6_rcv_saddr
     76#define ir_iif			req.__req_common.skc_bound_dev_if
     77#define ir_cookie		req.__req_common.skc_cookie
     78#define ireq_net		req.__req_common.skc_net
     79#define ireq_state		req.__req_common.skc_state
     80#define ireq_family		req.__req_common.skc_family
     81
     82	u16			snd_wscale : 4,
     83				rcv_wscale : 4,
     84				tstamp_ok  : 1,
     85				sack_ok	   : 1,
     86				wscale_ok  : 1,
     87				ecn_ok	   : 1,
     88				acked	   : 1,
     89				no_srccheck: 1,
     90				smc_ok	   : 1;
     91	u32                     ir_mark;
     92	union {
     93		struct ip_options_rcu __rcu	*ireq_opt;
     94#if IS_ENABLED(CONFIG_IPV6)
     95		struct {
     96			struct ipv6_txoptions	*ipv6_opt;
     97			struct sk_buff		*pktopts;
     98		};
     99#endif
    100	};
    101};
    102
    103static inline struct inet_request_sock *inet_rsk(const struct request_sock *sk)
    104{
    105	return (struct inet_request_sock *)sk;
    106}
    107
    108static inline u32 inet_request_mark(const struct sock *sk, struct sk_buff *skb)
    109{
    110	if (!sk->sk_mark && sock_net(sk)->ipv4.sysctl_tcp_fwmark_accept)
    111		return skb->mark;
    112
    113	return sk->sk_mark;
    114}
    115
    116static inline int inet_request_bound_dev_if(const struct sock *sk,
    117					    struct sk_buff *skb)
    118{
    119	int bound_dev_if = READ_ONCE(sk->sk_bound_dev_if);
    120#ifdef CONFIG_NET_L3_MASTER_DEV
    121	struct net *net = sock_net(sk);
    122
    123	if (!bound_dev_if && net->ipv4.sysctl_tcp_l3mdev_accept)
    124		return l3mdev_master_ifindex_by_index(net, skb->skb_iif);
    125#endif
    126
    127	return bound_dev_if;
    128}
    129
    130static inline int inet_sk_bound_l3mdev(const struct sock *sk)
    131{
    132#ifdef CONFIG_NET_L3_MASTER_DEV
    133	struct net *net = sock_net(sk);
    134
    135	if (!net->ipv4.sysctl_tcp_l3mdev_accept)
    136		return l3mdev_master_ifindex_by_index(net,
    137						      sk->sk_bound_dev_if);
    138#endif
    139
    140	return 0;
    141}
    142
    143static inline bool inet_bound_dev_eq(bool l3mdev_accept, int bound_dev_if,
    144				     int dif, int sdif)
    145{
    146	if (!bound_dev_if)
    147		return !sdif || l3mdev_accept;
    148	return bound_dev_if == dif || bound_dev_if == sdif;
    149}
    150
    151struct inet_cork {
    152	unsigned int		flags;
    153	__be32			addr;
    154	struct ip_options	*opt;
    155	unsigned int		fragsize;
    156	int			length; /* Total length of all frames */
    157	struct dst_entry	*dst;
    158	u8			tx_flags;
    159	__u8			ttl;
    160	__s16			tos;
    161	char			priority;
    162	__u16			gso_size;
    163	u64			transmit_time;
    164	u32			mark;
    165};
    166
    167struct inet_cork_full {
    168	struct inet_cork	base;
    169	struct flowi		fl;
    170};
    171
    172struct ip_mc_socklist;
    173struct ipv6_pinfo;
    174struct rtable;
    175
    176/** struct inet_sock - representation of INET sockets
    177 *
    178 * @sk - ancestor class
    179 * @pinet6 - pointer to IPv6 control block
    180 * @inet_daddr - Foreign IPv4 addr
    181 * @inet_rcv_saddr - Bound local IPv4 addr
    182 * @inet_dport - Destination port
    183 * @inet_num - Local port
    184 * @inet_saddr - Sending source
    185 * @uc_ttl - Unicast TTL
    186 * @inet_sport - Source port
    187 * @inet_id - ID counter for DF pkts
    188 * @tos - TOS
    189 * @mc_ttl - Multicasting TTL
    190 * @is_icsk - is this an inet_connection_sock?
    191 * @uc_index - Unicast outgoing device index
    192 * @mc_index - Multicast device index
    193 * @mc_list - Group array
    194 * @cork - info to build ip hdr on each ip frag while socket is corked
    195 */
    196struct inet_sock {
    197	/* sk and pinet6 has to be the first two members of inet_sock */
    198	struct sock		sk;
    199#if IS_ENABLED(CONFIG_IPV6)
    200	struct ipv6_pinfo	*pinet6;
    201#endif
    202	/* Socket demultiplex comparisons on incoming packets. */
    203#define inet_daddr		sk.__sk_common.skc_daddr
    204#define inet_rcv_saddr		sk.__sk_common.skc_rcv_saddr
    205#define inet_dport		sk.__sk_common.skc_dport
    206#define inet_num		sk.__sk_common.skc_num
    207
    208	__be32			inet_saddr;
    209	__s16			uc_ttl;
    210	__u16			cmsg_flags;
    211	struct ip_options_rcu __rcu	*inet_opt;
    212	__be16			inet_sport;
    213	__u16			inet_id;
    214
    215	__u8			tos;
    216	__u8			min_ttl;
    217	__u8			mc_ttl;
    218	__u8			pmtudisc;
    219	__u8			recverr:1,
    220				is_icsk:1,
    221				freebind:1,
    222				hdrincl:1,
    223				mc_loop:1,
    224				transparent:1,
    225				mc_all:1,
    226				nodefrag:1;
    227	__u8			bind_address_no_port:1,
    228				recverr_rfc4884:1,
    229				defer_connect:1; /* Indicates that fastopen_connect is set
    230						  * and cookie exists so we defer connect
    231						  * until first data frame is written
    232						  */
    233	__u8			rcv_tos;
    234	__u8			convert_csum;
    235	int			uc_index;
    236	int			mc_index;
    237	__be32			mc_addr;
    238	struct ip_mc_socklist __rcu	*mc_list;
    239	struct inet_cork_full	cork;
    240};
    241
    242#define IPCORK_OPT	1	/* ip-options has been held in ipcork.opt */
    243#define IPCORK_ALLFRAG	2	/* always fragment (for ipv6 for now) */
    244
    245/* cmsg flags for inet */
    246#define IP_CMSG_PKTINFO		BIT(0)
    247#define IP_CMSG_TTL		BIT(1)
    248#define IP_CMSG_TOS		BIT(2)
    249#define IP_CMSG_RECVOPTS	BIT(3)
    250#define IP_CMSG_RETOPTS		BIT(4)
    251#define IP_CMSG_PASSSEC		BIT(5)
    252#define IP_CMSG_ORIGDSTADDR	BIT(6)
    253#define IP_CMSG_CHECKSUM	BIT(7)
    254#define IP_CMSG_RECVFRAGSIZE	BIT(8)
    255
    256static inline bool sk_is_inet(struct sock *sk)
    257{
    258	return sk->sk_family == AF_INET || sk->sk_family == AF_INET6;
    259}
    260
    261/**
    262 * sk_to_full_sk - Access to a full socket
    263 * @sk: pointer to a socket
    264 *
    265 * SYNACK messages might be attached to request sockets.
    266 * Some places want to reach the listener in this case.
    267 */
    268static inline struct sock *sk_to_full_sk(struct sock *sk)
    269{
    270#ifdef CONFIG_INET
    271	if (sk && sk->sk_state == TCP_NEW_SYN_RECV)
    272		sk = inet_reqsk(sk)->rsk_listener;
    273#endif
    274	return sk;
    275}
    276
    277/* sk_to_full_sk() variant with a const argument */
    278static inline const struct sock *sk_const_to_full_sk(const struct sock *sk)
    279{
    280#ifdef CONFIG_INET
    281	if (sk && sk->sk_state == TCP_NEW_SYN_RECV)
    282		sk = ((const struct request_sock *)sk)->rsk_listener;
    283#endif
    284	return sk;
    285}
    286
    287static inline struct sock *skb_to_full_sk(const struct sk_buff *skb)
    288{
    289	return sk_to_full_sk(skb->sk);
    290}
    291
    292static inline struct inet_sock *inet_sk(const struct sock *sk)
    293{
    294	return (struct inet_sock *)sk;
    295}
    296
    297static inline void __inet_sk_copy_descendant(struct sock *sk_to,
    298					     const struct sock *sk_from,
    299					     const int ancestor_size)
    300{
    301	memcpy(inet_sk(sk_to) + 1, inet_sk(sk_from) + 1,
    302	       sk_from->sk_prot->obj_size - ancestor_size);
    303}
    304
    305int inet_sk_rebuild_header(struct sock *sk);
    306
    307/**
    308 * inet_sk_state_load - read sk->sk_state for lockless contexts
    309 * @sk: socket pointer
    310 *
    311 * Paired with inet_sk_state_store(). Used in places we don't hold socket lock:
    312 * tcp_diag_get_info(), tcp_get_info(), tcp_poll(), get_tcp4_sock() ...
    313 */
    314static inline int inet_sk_state_load(const struct sock *sk)
    315{
    316	/* state change might impact lockless readers. */
    317	return smp_load_acquire(&sk->sk_state);
    318}
    319
    320/**
    321 * inet_sk_state_store - update sk->sk_state
    322 * @sk: socket pointer
    323 * @newstate: new state
    324 *
    325 * Paired with inet_sk_state_load(). Should be used in contexts where
    326 * state change might impact lockless readers.
    327 */
    328void inet_sk_state_store(struct sock *sk, int newstate);
    329
    330void inet_sk_set_state(struct sock *sk, int state);
    331
    332static inline unsigned int __inet_ehashfn(const __be32 laddr,
    333					  const __u16 lport,
    334					  const __be32 faddr,
    335					  const __be16 fport,
    336					  u32 initval)
    337{
    338	return jhash_3words((__force __u32) laddr,
    339			    (__force __u32) faddr,
    340			    ((__u32) lport) << 16 | (__force __u32)fport,
    341			    initval);
    342}
    343
    344struct request_sock *inet_reqsk_alloc(const struct request_sock_ops *ops,
    345				      struct sock *sk_listener,
    346				      bool attach_listener);
    347
    348static inline __u8 inet_sk_flowi_flags(const struct sock *sk)
    349{
    350	__u8 flags = 0;
    351
    352	if (inet_sk(sk)->transparent || inet_sk(sk)->hdrincl)
    353		flags |= FLOWI_FLAG_ANYSRC;
    354	return flags;
    355}
    356
    357static inline void inet_inc_convert_csum(struct sock *sk)
    358{
    359	inet_sk(sk)->convert_csum++;
    360}
    361
    362static inline void inet_dec_convert_csum(struct sock *sk)
    363{
    364	if (inet_sk(sk)->convert_csum > 0)
    365		inet_sk(sk)->convert_csum--;
    366}
    367
    368static inline bool inet_get_convert_csum(struct sock *sk)
    369{
    370	return !!inet_sk(sk)->convert_csum;
    371}
    372
    373
    374static inline bool inet_can_nonlocal_bind(struct net *net,
    375					  struct inet_sock *inet)
    376{
    377	return net->ipv4.sysctl_ip_nonlocal_bind ||
    378		inet->freebind || inet->transparent;
    379}
    380
    381static inline bool inet_addr_valid_or_nonlocal(struct net *net,
    382					       struct inet_sock *inet,
    383					       __be32 addr,
    384					       int addr_type)
    385{
    386	return inet_can_nonlocal_bind(net, inet) ||
    387		addr == htonl(INADDR_ANY) ||
    388		addr_type == RTN_LOCAL ||
    389		addr_type == RTN_MULTICAST ||
    390		addr_type == RTN_BROADCAST;
    391}
    392
    393#endif	/* _INET_SOCK_H */