summaryrefslogtreecommitdiffstats
path: root/pimd/pim_mroute.c
diff options
context:
space:
mode:
Diffstat (limited to 'pimd/pim_mroute.c')
-rw-r--r--pimd/pim_mroute.c33
1 files changed, 32 insertions, 1 deletions
diff --git a/pimd/pim_mroute.c b/pimd/pim_mroute.c
index 6fa95d4b6..a2e6aabcf 100644
--- a/pimd/pim_mroute.c
+++ b/pimd/pim_mroute.c
@@ -1015,12 +1015,39 @@ static int pim_upstream_mroute_update(struct channel_oil *c_oil,
return pim_mroute_add(c_oil, name);
}
+/* IIF associated with SGrpt entries are re-evaluated when the parent
+ * (*,G) entries IIF changes
+ */
+static void pim_upstream_all_sources_iif_update(struct pim_upstream *up)
+{
+ struct listnode *listnode;
+ struct pim_upstream *child;
+
+ for (ALL_LIST_ELEMENTS_RO(up->sources, listnode,
+ child)) {
+ if (PIM_UPSTREAM_FLAG_TEST_USE_RPT(child->flags))
+ pim_upstream_mroute_iif_update(child->channel_oil,
+ __func__);
+ }
+}
+
/* In the case of "PIM state machine" added mroutes an upstream entry
* must be present to decide on the SPT-forwarding vs. RPT-forwarding.
*/
int pim_upstream_mroute_add(struct channel_oil *c_oil, const char *name)
{
- c_oil->oil.mfcc_parent = pim_upstream_get_mroute_iif(c_oil, name);
+ vifi_t iif;
+
+ iif = pim_upstream_get_mroute_iif(c_oil, name);
+
+ if (c_oil->oil.mfcc_parent != iif) {
+ c_oil->oil.mfcc_parent = iif;
+ if (c_oil->oil.mfcc_origin.s_addr == INADDR_ANY &&
+ c_oil->up)
+ pim_upstream_all_sources_iif_update(c_oil->up);
+ } else {
+ c_oil->oil.mfcc_parent = iif;
+ }
return pim_upstream_mroute_update(c_oil, name);
}
@@ -1040,6 +1067,10 @@ int pim_upstream_mroute_iif_update(struct channel_oil *c_oil, const char *name)
}
c_oil->oil.mfcc_parent = iif;
+ if (c_oil->oil.mfcc_origin.s_addr == INADDR_ANY &&
+ c_oil->up)
+ pim_upstream_all_sources_iif_update(c_oil->up);
+
if (PIM_DEBUG_MROUTE_DETAIL)
zlog_debug("%s(%s) %s mroute iif update %d",
__func__, name,