hc
2024-03-22 f63cd4c03ea42695d5f9b0e1798edd196923aae6
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
/* SPDX-License-Identifier: GPL-2.0-or-later */
/*
 * INET        An implementation of the TCP/IP protocol suite for the LINUX
 *        operating system.  INET is implemented using the  BSD Socket
 *        interface as the means of communication with the user level.
 *
 *        Definitions for the protocol dispatcher.
 *
 * Version:    @(#)protocol.h    1.0.2    05/07/93
 *
 * Author:    Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
 *
 *    Changes:
 *        Alan Cox    :    Added a name field and a frag handler
 *                    field for later.
 *        Alan Cox    :    Cleaned up, and sorted types.
 *        Pedro Roque    :    inet6 protocols
 */
 
#ifndef _PROTOCOL_H
#define _PROTOCOL_H
 
#include <linux/in6.h>
#include <linux/skbuff.h>
#if IS_ENABLED(CONFIG_IPV6)
#include <linux/ipv6.h>
#endif
#include <linux/netdevice.h>
 
/* This is one larger than the largest protocol value that can be
 * found in an ipv4 or ipv6 header.  Since in both cases the protocol
 * value is presented in a __u8, this is defined to be 256.
 */
#define MAX_INET_PROTOS        256
 
/* This is used to register protocols. */
struct net_protocol {
   int            (*handler)(struct sk_buff *skb);
 
   /* This returns an error if we weren't able to handle the error. */
   int            (*err_handler)(struct sk_buff *skb, u32 info);
 
   unsigned int        no_policy:1,
               netns_ok:1,
               /* does the protocol do more stringent
                * icmp tag validation than simple
                * socket lookup?
                */
               icmp_strict_tag_validation:1;
};
 
#if IS_ENABLED(CONFIG_IPV6)
struct inet6_protocol {
   int    (*handler)(struct sk_buff *skb);
 
   /* This returns an error if we weren't able to handle the error. */
   int    (*err_handler)(struct sk_buff *skb,
                  struct inet6_skb_parm *opt,
                  u8 type, u8 code, int offset,
                  __be32 info);
 
   unsigned int    flags;    /* INET6_PROTO_xxx */
};
 
#define INET6_PROTO_NOPOLICY    0x1
#define INET6_PROTO_FINAL    0x2
#endif
 
struct net_offload {
   struct offload_callbacks callbacks;
   unsigned int         flags;    /* Flags used by IPv6 for now */
};
/* This should be set for any extension header which is compatible with GSO. */
#define INET6_PROTO_GSO_EXTHDR    0x1
 
/* This is used to register socket interfaces for IP protocols.  */
struct inet_protosw {
   struct list_head list;
 
        /* These two fields form the lookup key.  */
   unsigned short     type;       /* This is the 2nd argument to socket(2). */
   unsigned short     protocol; /* This is the L4 protocol number.  */
 
   struct proto     *prot;
   const struct proto_ops *ops;
  
   unsigned char     flags;      /* See INET_PROTOSW_* below.  */
};
#define INET_PROTOSW_REUSE 0x01         /* Are ports automatically reusable? */
#define INET_PROTOSW_PERMANENT 0x02  /* Permanent protocols are unremovable. */
#define INET_PROTOSW_ICSK      0x04  /* Is this an inet_connection_sock? */
 
extern struct net_protocol __rcu *inet_protos[MAX_INET_PROTOS];
extern const struct net_offload __rcu *inet_offloads[MAX_INET_PROTOS];
extern const struct net_offload __rcu *inet6_offloads[MAX_INET_PROTOS];
 
#if IS_ENABLED(CONFIG_IPV6)
extern struct inet6_protocol __rcu *inet6_protos[MAX_INET_PROTOS];
#endif
 
int inet_add_protocol(const struct net_protocol *prot, unsigned char num);
int inet_del_protocol(const struct net_protocol *prot, unsigned char num);
int inet_add_offload(const struct net_offload *prot, unsigned char num);
int inet_del_offload(const struct net_offload *prot, unsigned char num);
void inet_register_protosw(struct inet_protosw *p);
void inet_unregister_protosw(struct inet_protosw *p);
 
#if IS_ENABLED(CONFIG_IPV6)
int inet6_add_protocol(const struct inet6_protocol *prot, unsigned char num);
int inet6_del_protocol(const struct inet6_protocol *prot, unsigned char num);
int inet6_register_protosw(struct inet_protosw *p);
void inet6_unregister_protosw(struct inet_protosw *p);
#endif
int inet6_add_offload(const struct net_offload *prot, unsigned char num);
int inet6_del_offload(const struct net_offload *prot, unsigned char num);
 
#endif    /* _PROTOCOL_H */