Type: fix
When a covering entry is removed from the table, the covered entries first see it 'updated' and then 'removed'.
the crash occurs because the covered prefixes share (simple pointer copy) the covereds hash table of path extensions. During the cervers deletion this hash table has been removed and the update of the covered crashes when recaluationg forwarding becuase it uses the free'd hash.
Fix is to refetch the shared hash table (which is NULL) when the covered is updated.
Signed-off-by: Neale Ranns <neale@graphiant.com>
Change-Id: Icefca9d7b21da975111d0e974d75f663fc0cc00c
}
static inline mfib_path_ext_t *
}
static inline mfib_path_ext_t *
-mfib_entry_path_ext_find (mfib_path_ext_t *exts,
+mfib_entry_path_ext_find (uword *exts,
fib_node_index_t path_index)
{
uword *p;
fib_node_index_t path_index)
{
uword *p;
/**
* Hash table of path extensions
*/
/**
* Hash table of path extensions
*/
- mfib_path_ext_t *mfes_exts;
/**
* Covering entry (if needed)
/**
* Covering entry (if needed)
#include <vnet/fib/fib_path_list.h>
static void
#include <vnet/fib/fib_path_list.h>
static void
-mfib_entry_src_rr_deactiviate (mfib_entry_t *mfib_entry,
- mfib_entry_src_t *msrc)
+mfib_entry_src_rr_deactivate (mfib_entry_t *mfib_entry,
+ mfib_entry_src_t *msrc)
-mfib_entry_src_rr_activiate (mfib_entry_t *mfib_entry,
- mfib_entry_src_t *msrc)
+mfib_entry_src_rr_activate (mfib_entry_t *mfib_entry,
+ mfib_entry_src_t *msrc)
{
mfib_entry_src_t *csrc;
mfib_entry_t *cover;
{
mfib_entry_src_t *csrc;
mfib_entry_t *cover;
mfib_entry_src_rr_cover_change (mfib_entry_t *mfib_entry,
mfib_entry_src_t *msrc)
{
mfib_entry_src_rr_cover_change (mfib_entry_t *mfib_entry,
mfib_entry_src_t *msrc)
{
- mfib_entry_src_rr_deactiviate(mfib_entry, msrc);
- mfib_entry_src_rr_activiate(mfib_entry, msrc);
+ mfib_entry_src_rr_deactivate(mfib_entry, msrc);
+ mfib_entry_src_rr_activate(mfib_entry, msrc);
return (MFIB_SRC_REEVALUATE);
}
return (MFIB_SRC_REEVALUATE);
}
* so there's no need to check for a new one. but we do need to
* copy down any new flags and input interfaces
*/
* so there's no need to check for a new one. but we do need to
* copy down any new flags and input interfaces
*/
+ mfib_entry_src_t *csrc;
mfib_entry_t *cover;
cover = mfib_entry_get(msrc->mfes_cover);
mfib_entry_t *cover;
cover = mfib_entry_get(msrc->mfes_cover);
msrc->mfes_itfs = cover->mfe_itfs;
msrc->mfes_rpf_id = cover->mfe_rpf_id;
msrc->mfes_itfs = cover->mfe_itfs;
msrc->mfes_rpf_id = cover->mfe_rpf_id;
+ /* The update to the cover could have removed the extensions.
+ * When a cover is removed from the table, the covereds see it first
+ * updated (to have no forwarding) and then changed
+ */
+ csrc = mfib_entry_get_best_src(cover);
+ msrc->mfes_exts = (csrc ? csrc->mfes_exts : NULL);
+
return (MFIB_SRC_REEVALUATE);
}
return (MFIB_SRC_REEVALUATE);
}
mfib_entry_src_rr_module_init (void)
{
mfib_entry_src_vft mvft = {
mfib_entry_src_rr_module_init (void)
{
mfib_entry_src_vft mvft = {
- .mev_activate = mfib_entry_src_rr_activiate,
- .mev_deactivate = mfib_entry_src_rr_deactiviate,
+ .mev_activate = mfib_entry_src_rr_activate,
+ .mev_deactivate = mfib_entry_src_rr_deactivate,
.mev_cover_change = mfib_entry_src_rr_cover_change,
.mev_cover_update = mfib_entry_src_rr_cover_update,
};
.mev_cover_change = mfib_entry_src_rr_cover_change,
.mev_cover_update = mfib_entry_src_rr_cover_update,
};