Commit 96a85625 authored by Petr Machata's avatar Petr Machata Committed by David S. Miller

nexthop: __nh_notifier_single_info_init(): Make nh_info an argument

The cited function currently uses rtnl_dereference() to get nh_info from a
handed-in nexthop. However, under the resilient hashing scheme, this
function will not always be called under RTNL, sometimes the mutual
exclusion will be achieved differently. Therefore move the nh_info
extraction from the function to its callers to make it possible to use a
different synchronization guarantee.
Signed-off-by: default avatarPetr Machata <petrm@nvidia.com>
Reviewed-by: default avatarIdo Schimmel <idosch@nvidia.com>
Reviewed-by: default avatarDavid Ahern <dsahern@kernel.org>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 597f48e4
...@@ -52,10 +52,8 @@ static bool nexthop_notifiers_is_empty(struct net *net) ...@@ -52,10 +52,8 @@ static bool nexthop_notifiers_is_empty(struct net *net)
static void static void
__nh_notifier_single_info_init(struct nh_notifier_single_info *nh_info, __nh_notifier_single_info_init(struct nh_notifier_single_info *nh_info,
const struct nexthop *nh) const struct nh_info *nhi)
{ {
struct nh_info *nhi = rtnl_dereference(nh->nh_info);
nh_info->dev = nhi->fib_nhc.nhc_dev; nh_info->dev = nhi->fib_nhc.nhc_dev;
nh_info->gw_family = nhi->fib_nhc.nhc_gw_family; nh_info->gw_family = nhi->fib_nhc.nhc_gw_family;
if (nh_info->gw_family == AF_INET) if (nh_info->gw_family == AF_INET)
...@@ -71,12 +69,14 @@ __nh_notifier_single_info_init(struct nh_notifier_single_info *nh_info, ...@@ -71,12 +69,14 @@ __nh_notifier_single_info_init(struct nh_notifier_single_info *nh_info,
static int nh_notifier_single_info_init(struct nh_notifier_info *info, static int nh_notifier_single_info_init(struct nh_notifier_info *info,
const struct nexthop *nh) const struct nexthop *nh)
{ {
struct nh_info *nhi = rtnl_dereference(nh->nh_info);
info->type = NH_NOTIFIER_INFO_TYPE_SINGLE; info->type = NH_NOTIFIER_INFO_TYPE_SINGLE;
info->nh = kzalloc(sizeof(*info->nh), GFP_KERNEL); info->nh = kzalloc(sizeof(*info->nh), GFP_KERNEL);
if (!info->nh) if (!info->nh)
return -ENOMEM; return -ENOMEM;
__nh_notifier_single_info_init(info->nh, nh); __nh_notifier_single_info_init(info->nh, nhi);
return 0; return 0;
} }
...@@ -103,11 +103,13 @@ static int nh_notifier_mp_info_init(struct nh_notifier_info *info, ...@@ -103,11 +103,13 @@ static int nh_notifier_mp_info_init(struct nh_notifier_info *info,
for (i = 0; i < num_nh; i++) { for (i = 0; i < num_nh; i++) {
struct nh_grp_entry *nhge = &nhg->nh_entries[i]; struct nh_grp_entry *nhge = &nhg->nh_entries[i];
struct nh_info *nhi;
nhi = rtnl_dereference(nhge->nh->nh_info);
info->nh_grp->nh_entries[i].id = nhge->nh->id; info->nh_grp->nh_entries[i].id = nhge->nh->id;
info->nh_grp->nh_entries[i].weight = nhge->weight; info->nh_grp->nh_entries[i].weight = nhge->weight;
__nh_notifier_single_info_init(&info->nh_grp->nh_entries[i].nh, __nh_notifier_single_info_init(&info->nh_grp->nh_entries[i].nh,
nhge->nh); nhi);
} }
return 0; return 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment