summaryrefslogtreecommitdiffstats
path: root/src/vnet/dpo/replicate_dpo.c
diff options
context:
space:
mode:
authorBenoît Ganne <bganne@cisco.com>2023-02-21 16:09:47 +0100
committerDave Wallace <dwallacelf@gmail.com>2023-05-19 21:14:52 +0000
commite211ac4886d0ae51c08f77c76ed37b76f01f7629 (patch)
tree040d3e41b1cbc4e3cf31fbfec9e3308786eb07cc /src/vnet/dpo/replicate_dpo.c
parent168bb1d55efeba716bd3004a1f3d19cf25c15191 (diff)
fib: fix load-balance and replicate dpos buckets overflow
load-balance and replicate dpos both store their number of buckets as u16, which can overflow if too many paths are configured. For load-balance it can happens quite quickly because of weights normalization. Type: fix Change-Id: I0c78c39fc3d40626dfc58b49e7d99d71f9852b50 Signed-off-by: Benoît Ganne <bganne@cisco.com>
Diffstat (limited to 'src/vnet/dpo/replicate_dpo.c')
-rw-r--r--src/vnet/dpo/replicate_dpo.c16
1 files changed, 15 insertions, 1 deletions
diff --git a/src/vnet/dpo/replicate_dpo.c b/src/vnet/dpo/replicate_dpo.c
index 5f88f12b910..0474fd82984 100644
--- a/src/vnet/dpo/replicate_dpo.c
+++ b/src/vnet/dpo/replicate_dpo.c
@@ -172,6 +172,8 @@ replicate_create_i (u32 num_buckets,
{
replicate_t *rep;
+ ASSERT (num_buckets <= REP_MAX_BUCKETS);
+
rep = replicate_alloc_i();
rep->rep_n_buckets = num_buckets;
rep->rep_proto = rep_proto;
@@ -311,7 +313,8 @@ static inline void
replicate_set_n_buckets (replicate_t *rep,
u32 n_buckets)
{
- rep->rep_n_buckets = n_buckets;
+ ASSERT (n_buckets <= REP_MAX_BUCKETS);
+ rep->rep_n_buckets = n_buckets;
}
void
@@ -331,6 +334,17 @@ replicate_multipath_update (const dpo_id_t *dpo,
rep->rep_proto);
n_buckets = vec_len(nhs);
+ if (n_buckets > REP_MAX_BUCKETS)
+ {
+ vlib_log_err (replicate_logger,
+ "Too many paths for replicate, truncating %d -> %d",
+ n_buckets, REP_MAX_BUCKETS);
+ for (int i = REP_MAX_BUCKETS; i < n_buckets; i++)
+ dpo_reset (&vec_elt (nhs, i).path_dpo);
+ vec_set_len (nhs, REP_MAX_BUCKETS);
+ n_buckets = REP_MAX_BUCKETS;
+ }
+
if (0 == rep->rep_n_buckets)
{
/*