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
|
#ifndef __NET_INET_FRAG_WRAPPER_H
#define __NET_INET_FRAG_WRAPPER_H 1
#include <linux/version.h>
#include_next <net/inet_frag.h>
#ifdef HAVE_INET_FRAGS_LAST_IN
#define q_flags(q) (q->last_in)
#define qp_flags(qp) (qp->q.last_in)
#else
#define q_flags(q) (q->flags)
#define qp_flags(qp) (qp->q.flags)
#endif
#ifndef HAVE_INET_FRAG_EVICTING
static inline bool inet_frag_evicting(struct inet_frag_queue *q)
{
#ifdef HAVE_INET_FRAG_QUEUE_WITH_LIST_EVICTOR
return !hlist_unhashed(&q->list_evictor);
#else
return (q_flags(q) & INET_FRAG_FIRST_IN) && q->fragments != NULL;
#endif /* HAVE_INET_FRAG_QUEUE_WITH_LIST_EVICTOR */
}
#endif /* HAVE_INET_FRAG_EVICTING */
/* Upstream commit 3fd588eb90bf ("inet: frag: remove lru list") dropped this
* function, but we call it from our compat code. Provide a noop version. */
#ifndef HAVE_INET_FRAG_LRU_MOVE
#define inet_frag_lru_move(q)
#endif
#ifndef HAVE_CORRECT_MRU_HANDLING
static inline void rpl_sub_frag_mem_limit(struct netns_frags *nf, int i)
{
__percpu_counter_add(&nf->mem, -i, frag_percpu_counter_batch);
}
#define sub_frag_mem_limit rpl_sub_frag_mem_limit
static inline void rpl_add_frag_mem_limit(struct netns_frags *nf, int i)
{
__percpu_counter_add(&nf->mem, i, frag_percpu_counter_batch);
}
#define add_frag_mem_limit rpl_add_frag_mem_limit
static inline int rpl_inet_frags_init(struct inet_frags *frags)
{
inet_frags_init(frags);
return 0;
}
#define inet_frags_init rpl_inet_frags_init
/* We reuse the upstream inet_fragment.c common code for managing fragment
* stores, However we actually store the fragments within our own 'inet_frags'
* structures (in {ip_fragment,nf_conntrack_reasm}.c). When unloading the OVS
* kernel module, we need to flush all of the remaining fragments from these
* caches, or else we will panic with the following sequence of events:
*
* 1) A fragment for a packet arrives and is cached in inet_frags. This
* starts a timer to ensure the fragment does not hang around forever.
* 2) openvswitch module is unloaded.
* 3) The timer for the fragment fires, calling into backported OVS code
* to free the fragment.
* 4) BUG: unable to handle kernel paging request at ffffffffc03c01e0
*/
void rpl_inet_frags_exit_net(struct netns_frags *nf, struct inet_frags *f);
#define inet_frags_exit_net rpl_inet_frags_exit_net
#endif /* !HAVE_CORRECT_MRU_HANDLING */
#endif /* inet_frag.h */
|