static DEFINE_SPINLOCK(ptype_lock);
struct list_head ptype_base[PTYPE_HASH_SIZE] ;
struct list_head ptype_all ; /* Taps */
struct packet_type {
__be16 type; /* This is really htons(ether_type). */
struct net_device *dev; /* NULL is wildcarded here */
int (*func) (struct sk_buff *,
struct net_device *,
struct packet_type *,
struct net_device *);
bool (*id_match)(struct packet_type *ptype,
struct sock *sk);
void *af_packet_priv;
struct list_head list;
};
void dev_add_pack(struct packet_type *pt)
{
struct list_head *head = ptype_head(pt);
spin_lock(&ptype_lock);
list_add_rcu(&pt->list, head);
spin_unlock(&ptype_lock);
}
EXPORT_SYMBOL(dev_add_pack);
void __dev_remove_pack(struct packet_type *pt)
{
struct list_head *head = ptype_head(pt);
struct packet_type *pt1;
spin_lock(&ptype_lock);
list_for_each_entry(pt1, head, list) {
if (pt == pt1) {
list_del_rcu(&pt->list);
goto out;
}
}
pr_warn("dev_remove_pack: %p not found\n", pt);
out:
spin_unlock(&ptype_lock);
}
EXPORT_SYMBOL(__dev_remove_pack);
void dev_remove_pack(struct packet_type *pt)
{
__dev_remove_pack(pt);
synchronize_net();
}
EXPORT_SYMBOL(dev_remove_pack);
static struct packet_type ip_packet_type = {
.type = cpu_to_be16(ETH_P_IP),
.func = ip_rcv,
};static struct packet_type ipv6_packet_type = {
.type = cpu_to_be16(ETH_P_IPV6),
.func = ipv6_rcv,
};static struct packet_type can_packet __read_mostly = {
.type = cpu_to_be16(ETH_P_CAN),
.func = can_rcv,
};
static struct packet_type canfd_packet __read_mostly = {
.type = cpu_to_be16(ETH_P_CANFD),
.func = canfd_rcv,
};static struct packet_type rarp_packet_type = {
.type = cpu_to_be16(ETH_P_RARP),
.func = ic_rarp_recv,
};
static struct packet_type llc_packet_type __read_mostly = {
.type = cpu_to_be16(ETH_P_802_2),
.func = llc_rcv,
};
static struct packet_type llc_tr_packet_type __read_mostly = {
.type = cpu_to_be16(ETH_P_TR_802_2),
.func = llc_rcv,
};
标签:协议,head,struct,list,网络层,ptype,packet,注册,type
From: https://blog.51cto.com/u_11860992/6392695