Commit adae216f authored by Jakub Kicinski's avatar Jakub Kicinski
Browse files

Merge branch 'refactor-duplicate-codes-in-the-tc-cls-walk-function'

Zhengchao Shao says:

====================
refactor duplicate codes in the tc cls walk function

The walk implementation of most tc cls modules is basically the same.
That is, the values of count and skip are checked first. If count is
greater than or equal to skip, the registered fn function is executed.
Otherwise, increase the value of count. So the code can be refactored.
Then use helper function to replace the code of each cls module in
alphabetical order.

The walk function is invoked during dump. Therefore, test cases related
 to the tdc filter need to be added.
====================

Link: https://lore.kernel.org/r/20220916020251.190097-1-shaozhengchao@huawei.com


Signed-off-by: default avatarJakub Kicinski <kuba@kernel.org>
parents e93a766d 972e8861
Loading
Loading
Loading
Loading
+13 −0
Original line number Diff line number Diff line
@@ -81,6 +81,19 @@ int tcf_classify(struct sk_buff *skb,
		 const struct tcf_proto *tp, struct tcf_result *res,
		 bool compat_mode);

static inline bool tc_cls_stats_dump(struct tcf_proto *tp,
				     struct tcf_walker *arg,
				     void *filter)
{
	if (arg->count >= arg->skip && arg->fn(tp, filter, arg) < 0) {
		arg->stop = 1;
		return false;
	}

	arg->count++;
	return true;
}

#else
static inline bool tcf_block_shared(struct tcf_block *block)
{
+1 −8
Original line number Diff line number Diff line
@@ -251,16 +251,9 @@ static void basic_walk(struct tcf_proto *tp, struct tcf_walker *arg,
	struct basic_filter *f;

	list_for_each_entry(f, &head->flist, link) {
		if (arg->count < arg->skip)
			goto skip;

		if (arg->fn(tp, f, arg) < 0) {
			arg->stop = 1;
		if (!tc_cls_stats_dump(tp, arg, f))
			break;
	}
skip:
		arg->count++;
	}
}

static void basic_bind_class(void *fh, u32 classid, unsigned long cl, void *q,
+1 −7
Original line number Diff line number Diff line
@@ -650,15 +650,9 @@ static void cls_bpf_walk(struct tcf_proto *tp, struct tcf_walker *arg,
	struct cls_bpf_prog *prog;

	list_for_each_entry(prog, &head->plist, link) {
		if (arg->count < arg->skip)
			goto skip;
		if (arg->fn(tp, prog, arg) < 0) {
			arg->stop = 1;
		if (!tc_cls_stats_dump(tp, arg, prog))
			break;
	}
skip:
		arg->count++;
	}
}

static int cls_bpf_reoffload(struct tcf_proto *tp, bool add, flow_setup_cb_t *cb,
+1 −7
Original line number Diff line number Diff line
@@ -683,15 +683,9 @@ static void flow_walk(struct tcf_proto *tp, struct tcf_walker *arg,
	struct flow_filter *f;

	list_for_each_entry(f, &head->filters, list) {
		if (arg->count < arg->skip)
			goto skip;
		if (arg->fn(tp, f, arg) < 0) {
			arg->stop = 1;
		if (!tc_cls_stats_dump(tp, arg, f))
			break;
	}
skip:
		arg->count++;
	}
}

static struct tcf_proto_ops cls_flow_ops __read_mostly = {
+1 −8
Original line number Diff line number Diff line
@@ -358,16 +358,9 @@ static void fw_walk(struct tcf_proto *tp, struct tcf_walker *arg,

		for (f = rtnl_dereference(head->ht[h]); f;
		     f = rtnl_dereference(f->next)) {
			if (arg->count < arg->skip) {
				arg->count++;
				continue;
			}
			if (arg->fn(tp, f, arg) < 0) {
				arg->stop = 1;
			if (!tc_cls_stats_dump(tp, arg, f))
				return;
		}
			arg->count++;
		}
	}
}

Loading