--- sys/netinet/tcp_stacks/rack_pcm.c.orig +++ sys/netinet/tcp_stacks/rack_pcm.c @@ -196,17 +196,22 @@ } else { /* Need to expand the array */ struct rack_pcm_stats *n; - uint16_t new_cnt; + size_t new_cnt; - new_cnt = rack->r_ctl.pcm_i.cnt_alloc * 2; - sz = (sizeof(struct rack_pcm_stats) * new_cnt); - n = malloc(sz,M_TCPPCM, M_NOWAIT); - if (n == NULL) { - /* We are dead, no memory */ + new_cnt = (size_t)rack->r_ctl.pcm_i.cnt_alloc * 2; + if (new_cnt > RACK_MAX_PCM_ARRAY) { + /* Too many entries required. */ +stop_measurement: rack->pcm_in_progress = 0; rack->r_ctl.pcm_i.cnt = 0; return; } + sz = (sizeof(struct rack_pcm_stats) * new_cnt); + n = malloc(sz, M_TCPPCM, M_NOWAIT); + if (n == NULL) { + /* We are dead, no memory. */ + goto stop_measurement; + } sz = (sizeof(struct rack_pcm_stats) * rack->r_ctl.pcm_i.cnt_alloc); memcpy(n, rack->r_ctl.pcm_s, sz); free(rack->r_ctl.pcm_s, M_TCPPCM); --- sys/netinet/tcp_stacks/tcp_rack.h.orig +++ sys/netinet/tcp_stacks/tcp_rack.h @@ -362,9 +362,11 @@ uint16_t cnt; /* Maximum acks present */ uint16_t cnt_alloc; +#define RACK_DEFAULT_PCM_ARRAY 16 +#define RACK_MAX_PCM_ARRAY 1024 }; - -#define RACK_DEFAULT_PCM_ARRAY 16 +_Static_assert(RACK_MAX_PCM_ARRAY <= UINT16_MAX, + "RACK_MAX_PCM_ARRAY must fit in 16 bits"); struct rack_pcm_stats { uint32_t sseq;