Expose path change count to destination in mpath info
Unified · Split
| @@ -1439,7 +1439,8 @@ enum mpath_info_flags { · 1438 unmodified lines | |||
| 1439 | MPATH_INFO_DISCOVERY_TIMEOUT = BIT(4), | 1439 | MPATH_INFO_DISCOVERY_TIMEOUT = BIT(4), |
| 1440 | MPATH_INFO_DISCOVERY_RETRIES = BIT(5), | 1440 | MPATH_INFO_DISCOVERY_RETRIES = BIT(5), |
| 1441 | MPATH_INFO_FLAGS = BIT(6), | 1441 | MPATH_INFO_FLAGS = BIT(6), |
| 1442 | MPATH_INFO_HOP_COUNT = BIT(7) | 1442 | MPATH_INFO_HOP_COUNT = BIT(7), |
| 1443 | MPATH_INFO_PATH_CHANGE = BIT(8), | ||
| 1443 | }; | 1444 | }; |
| 1444 | 1445 | ||
| 1445 | /** | 1446 | /** |
| @@ -1460,6 +1461,7 @@ enum mpath_info_flags { · 14 unmodified lines | |||
| 1460 | * changes, i.e. when a station is added or removed, so that | 1461 | * changes, i.e. when a station is added or removed, so that |
| 1461 | * userspace can tell whether it got a consistent snapshot. | 1462 | * userspace can tell whether it got a consistent snapshot. |
| 1462 | * @hop_count: hops to destination | 1463 | * @hop_count: hops to destination |
| 1464 | * @path_change_count: total number of path changes to destination | ||
| 1463 | */ | 1465 | */ |
| 1464 | struct mpath_info { | 1466 | struct mpath_info { |
| 1465 | u32 filled; | 1467 | u32 filled; |
| @@ -1471,6 +1473,7 @@ struct mpath_info { · 5 unmodified lines | |||
| 1471 | u8 discovery_retries; | 1473 | u8 discovery_retries; |
| 1472 | u8 flags; | 1474 | u8 flags; |
| 1473 | u8 hop_count; | 1475 | u8 hop_count; |
| 1476 | u32 path_change_count; | ||
| 1474 | 1477 | ||
| 1475 | int generation; | 1478 | int generation; |
| 1476 | }; | 1479 | }; |
| @@ -3288,8 +3288,9 @@ enum nl80211_mpath_flags { · 3287 unmodified lines | |||
| 3288 | * @NL80211_MPATH_INFO_DISCOVERY_TIMEOUT: total path discovery timeout, in msec | 3288 | * @NL80211_MPATH_INFO_DISCOVERY_TIMEOUT: total path discovery timeout, in msec |
| 3289 | * @NL80211_MPATH_INFO_DISCOVERY_RETRIES: mesh path discovery retries | 3289 | * @NL80211_MPATH_INFO_DISCOVERY_RETRIES: mesh path discovery retries |
| 3290 | * @NL80211_MPATH_INFO_HOP_COUNT: hop count to destination | 3290 | * @NL80211_MPATH_INFO_HOP_COUNT: hop count to destination |
| 3291 | * @NL80211_MPATH_INFO_PATH_CHANGE: total number of path changes to destination | ||
| 3291 | * @NL80211_MPATH_INFO_MAX: highest mesh path information attribute number | 3292 | * @NL80211_MPATH_INFO_MAX: highest mesh path information attribute number |
| 3292 | * currently defind | 3293 | * currently defined |
| 3293 | * @__NL80211_MPATH_INFO_AFTER_LAST: internal use | 3294 | * @__NL80211_MPATH_INFO_AFTER_LAST: internal use |
| 3294 | */ | 3295 | */ |
| 3295 | enum nl80211_mpath_info { | 3296 | enum nl80211_mpath_info { |
| @@ -3302,6 +3303,7 @@ enum nl80211_mpath_info { · 6 unmodified lines | |||
| 3302 | NL80211_MPATH_INFO_DISCOVERY_TIMEOUT, | 3303 | NL80211_MPATH_INFO_DISCOVERY_TIMEOUT, |
| 3303 | NL80211_MPATH_INFO_DISCOVERY_RETRIES, | 3304 | NL80211_MPATH_INFO_DISCOVERY_RETRIES, |
| 3304 | NL80211_MPATH_INFO_HOP_COUNT, | 3305 | NL80211_MPATH_INFO_HOP_COUNT, |
| 3306 | NL80211_MPATH_INFO_PATH_CHANGE, | ||
| 3305 | 3307 | ||
| 3306 | /* keep last */ | 3308 | /* keep last */ |
| 3307 | __NL80211_MPATH_INFO_AFTER_LAST, | 3309 | __NL80211_MPATH_INFO_AFTER_LAST, |
| @@ -1746,7 +1746,8 @@ static void mpath_set_pinfo(struct mesh_path *mpath, u8 *next_hop, · 1745 unmodified lines | |||
| 1746 | MPATH_INFO_DISCOVERY_TIMEOUT | | 1746 | MPATH_INFO_DISCOVERY_TIMEOUT | |
| 1747 | MPATH_INFO_DISCOVERY_RETRIES | | 1747 | MPATH_INFO_DISCOVERY_RETRIES | |
| 1748 | MPATH_INFO_FLAGS | | 1748 | MPATH_INFO_FLAGS | |
| 1749 | MPATH_INFO_HOP_COUNT; | 1749 | MPATH_INFO_HOP_COUNT | |
| 1750 | MPATH_INFO_PATH_CHANGE; | ||
| 1750 | 1751 | ||
| 1751 | pinfo->frame_qlen = mpath->frame_queue.qlen; | 1752 | pinfo->frame_qlen = mpath->frame_queue.qlen; |
| 1752 | pinfo->sn = mpath->sn; | 1753 | pinfo->sn = mpath->sn; |
| @@ -1767,6 +1768,7 @@ static void mpath_set_pinfo(struct mesh_path *mpath, u8 *next_hop, · 14 unmodified lines | |||
| 1767 | if (mpath->flags & MESH_PATH_RESOLVED) | 1768 | if (mpath->flags & MESH_PATH_RESOLVED) |
| 1768 | pinfo->flags |= NL80211_MPATH_FLAG_RESOLVED; | 1769 | pinfo->flags |= NL80211_MPATH_FLAG_RESOLVED; |
| 1769 | pinfo->hop_count = mpath->hop_count; | 1770 | pinfo->hop_count = mpath->hop_count; |
| 1771 | pinfo->path_change_count = mpath->path_change_count; | ||
| 1770 | } | 1772 | } |
| 1771 | 1773 | ||
| 1772 | static int ieee80211_get_mpath(struct wiphy *wiphy, struct net_device *dev, | 1774 | static int ieee80211_get_mpath(struct wiphy *wiphy, struct net_device *dev, |
| @@ -94,6 +94,7 @@ enum mesh_deferred_task_flags { · 93 unmodified lines | |||
| 94 | * @last_preq_to_root: Timestamp of last PREQ sent to root | 94 | * @last_preq_to_root: Timestamp of last PREQ sent to root |
| 95 | * @is_root: the destination station of this path is a root node | 95 | * @is_root: the destination station of this path is a root node |
| 96 | * @is_gate: the destination station of this path is a mesh gate | 96 | * @is_gate: the destination station of this path is a mesh gate |
| 97 | * @path_change_count: the number of path changes to destination | ||
| 97 | * | 98 | * |
| 98 | * | 99 | * |
| 99 | * The dst address is unique in the mesh path table. Since the mesh_path is | 100 | * The dst address is unique in the mesh path table. Since the mesh_path is |
| @@ -124,6 +125,7 @@ struct mesh_path { · 24 unmodified lines | |||
| 124 | unsigned long last_preq_to_root; | 125 | unsigned long last_preq_to_root; |
| 125 | bool is_root; | 126 | bool is_root; |
| 126 | bool is_gate; | 127 | bool is_gate; |
| 128 | u32 path_change_count; | ||
| 127 | }; | 129 | }; |
| 128 | 130 | ||
| 129 | /** | 131 | /** |
| @@ -479,6 +479,8 @@ static u32 hwmp_route_info_get(struct ieee80211_sub_if_data *sdata, · 478 unmodified lines | |||
| 479 | } | 479 | } |
| 480 | 480 | ||
| 481 | if (fresh_info) { | 481 | if (fresh_info) { |
| 482 | if (rcu_access_pointer(mpath->next_hop) != sta) | ||
| 483 | mpath->path_change_count++; | ||
| 482 | mesh_path_assign_nexthop(mpath, sta); | 484 | mesh_path_assign_nexthop(mpath, sta); |
| 483 | mpath->flags |= MESH_PATH_SN_VALID; | 485 | mpath->flags |= MESH_PATH_SN_VALID; |
| 484 | mpath->metric = new_metric; | 486 | mpath->metric = new_metric; |
| @@ -523,6 +525,8 @@ static u32 hwmp_route_info_get(struct ieee80211_sub_if_data *sdata, · 38 unmodified lines | |||
| 523 | } | 525 | } |
| 524 | 526 | ||
| 525 | if (fresh_info) { | 527 | if (fresh_info) { |
| 528 | if (rcu_access_pointer(mpath->next_hop) != sta) | ||
| 529 | mpath->path_change_count++; | ||
| 526 | mesh_path_assign_nexthop(mpath, sta); | 530 | mesh_path_assign_nexthop(mpath, sta); |
| 527 | mpath->metric = last_hop_metric; | 531 | mpath->metric = last_hop_metric; |
| 528 | mpath->exp_time = time_after(mpath->exp_time, exp_time) | 532 | mpath->exp_time = time_after(mpath->exp_time, exp_time) |
| @@ -5830,7 +5830,10 @@ static int nl80211_send_mpath(struct sk_buff *msg, u32 portid, u32 seq, · 5829 unmodified lines | |||
| 5830 | pinfo->discovery_retries)) || | 5830 | pinfo->discovery_retries)) || |
| 5831 | ((pinfo->filled & MPATH_INFO_HOP_COUNT) && | 5831 | ((pinfo->filled & MPATH_INFO_HOP_COUNT) && |
| 5832 | nla_put_u8(msg, NL80211_MPATH_INFO_HOP_COUNT, | 5832 | nla_put_u8(msg, NL80211_MPATH_INFO_HOP_COUNT, |
| 5833 | pinfo->hop_count))) | 5833 | pinfo->hop_count)) || |
| 5834 | ((pinfo->filled & MPATH_INFO_PATH_CHANGE) && | ||
| 5835 | nla_put_u32(msg, NL80211_MPATH_INFO_PATH_CHANGE, | ||
| 5836 | pinfo->path_change_count))) | ||
| 5834 | goto nla_put_failure; | 5837 | goto nla_put_failure; |
| 5835 | 5838 | ||
| 5836 | nla_nest_end(msg, pinfoattr); | 5839 | nla_nest_end(msg, pinfoattr); |