net/sched: transition act_pedit to rcu and percpu stats
[platform/kernel/linux-starfive.git] / include / net / tc_act / tc_pedit.h
index 3e02709..83fe399 100644 (file)
@@ -4,22 +4,29 @@
 
 #include <net/act_api.h>
 #include <linux/tc_act/tc_pedit.h>
+#include <linux/types.h>
 
 struct tcf_pedit_key_ex {
        enum pedit_header_type htype;
        enum pedit_cmd cmd;
 };
 
-struct tcf_pedit {
-       struct tc_action        common;
-       unsigned char           tcfp_nkeys;
-       unsigned char           tcfp_flags;
-       u32                     tcfp_off_max_hint;
+struct tcf_pedit_parms {
        struct tc_pedit_key     *tcfp_keys;
        struct tcf_pedit_key_ex *tcfp_keys_ex;
+       u32 tcfp_off_max_hint;
+       unsigned char tcfp_nkeys;
+       unsigned char tcfp_flags;
+       struct rcu_head rcu;
+};
+
+struct tcf_pedit {
+       struct tc_action common;
+       struct tcf_pedit_parms __rcu *parms;
 };
 
 #define to_pedit(a) ((struct tcf_pedit *)a)
+#define to_pedit_parms(a) (rcu_dereference(to_pedit(a)->parms))
 
 static inline bool is_tcf_pedit(const struct tc_action *a)
 {
@@ -32,37 +39,81 @@ static inline bool is_tcf_pedit(const struct tc_action *a)
 
 static inline int tcf_pedit_nkeys(const struct tc_action *a)
 {
-       return to_pedit(a)->tcfp_nkeys;
+       struct tcf_pedit_parms *parms;
+       int nkeys;
+
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       nkeys = parms->tcfp_nkeys;
+       rcu_read_unlock();
+
+       return nkeys;
 }
 
 static inline u32 tcf_pedit_htype(const struct tc_action *a, int index)
 {
-       if (to_pedit(a)->tcfp_keys_ex)
-               return to_pedit(a)->tcfp_keys_ex[index].htype;
+       u32 htype = TCA_PEDIT_KEY_EX_HDR_TYPE_NETWORK;
+       struct tcf_pedit_parms *parms;
+
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       if (parms->tcfp_keys_ex)
+               htype = parms->tcfp_keys_ex[index].htype;
+       rcu_read_unlock();
 
-       return TCA_PEDIT_KEY_EX_HDR_TYPE_NETWORK;
+       return htype;
 }
 
 static inline u32 tcf_pedit_cmd(const struct tc_action *a, int index)
 {
-       if (to_pedit(a)->tcfp_keys_ex)
-               return to_pedit(a)->tcfp_keys_ex[index].cmd;
+       struct tcf_pedit_parms *parms;
+       u32 cmd = __PEDIT_CMD_MAX;
 
-       return __PEDIT_CMD_MAX;
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       if (parms->tcfp_keys_ex)
+               cmd = parms->tcfp_keys_ex[index].cmd;
+       rcu_read_unlock();
+
+       return cmd;
 }
 
 static inline u32 tcf_pedit_mask(const struct tc_action *a, int index)
 {
-       return to_pedit(a)->tcfp_keys[index].mask;
+       struct tcf_pedit_parms *parms;
+       u32 mask;
+
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       mask = parms->tcfp_keys[index].mask;
+       rcu_read_unlock();
+
+       return mask;
 }
 
 static inline u32 tcf_pedit_val(const struct tc_action *a, int index)
 {
-       return to_pedit(a)->tcfp_keys[index].val;
+       struct tcf_pedit_parms *parms;
+       u32 val;
+
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       val = parms->tcfp_keys[index].val;
+       rcu_read_unlock();
+
+       return val;
 }
 
 static inline u32 tcf_pedit_offset(const struct tc_action *a, int index)
 {
-       return to_pedit(a)->tcfp_keys[index].off;
+       struct tcf_pedit_parms *parms;
+       u32 off;
+
+       rcu_read_lock();
+       parms = to_pedit_parms(a);
+       off = parms->tcfp_keys[index].off;
+       rcu_read_unlock();
+
+       return off;
 }
 #endif /* __NET_TC_PED_H */