On Thu, Apr 8, 2021 at 12:50 AM Vlad Buslov [off-list ref] wrote:
On Thu 08 Apr 2021 at 02:50, Cong Wang [off-list ref] wrote:
quoted
In my last comments, I actually meant whether we can avoid this
'init_res[]' array. Since here you want to check whether an action
returned by tcf_action_init_1() is a new one or an existing one, how
about checking its refcnt? Something like:
act = tcf_action_init_1(...);
if (IS_ERR(act)) {
err = PTR_ERR(act);
goto err;
}
if (refcount_read(&act->tcfa_refcnt) == 1) {
// we know this is a newly allocated one
}
Thanks.
Hmm, I don't think this would work in general case. Consider following
cases:
1. Action existed during init as filter action(refcnt=1), init overwrote
it setting refcnt=2, by the time we got to checking tcfa_refcnt filter
has been deleted (refcnt=1) so code will incorrectly assume that it has
created the action.
2. We need this check in tcf_action_add() to release the refcnt in case
of overwriting existing actions, but by that time actions are already
accessible though idr, so even in case when new action has been created
(refcnt=1) it could already been referenced by concurrently created
filter (refcnt=2).
Hmm, I nearly forgot RTNL is lifted for some cases along TC filter
and action control paths... It seems we have no better way to work
around this.
Thanks.