Fixed integer overflow with hashtables when calculating their capacity
This commit is contained in:
1 parent
1254e657c5
commit
976965bcfa
6 files changed
+37
-1
No files matched your search
@@ -233,6 +233,10 @@ static const size_t cmc_hashtable_primes[] = {53, 97, 191, 383, 769, 1531,
|
||||
if (capacity == 0 || load <= 0 || load >= 1) \
|
||||
return NULL; \
|
||||
\
|
||||
/* Prevent integer overflow */ \
|
||||
if (capacity >= UINTMAX_MAX * load) \
|
||||
return NULL; \
|
||||
\
|
||||
size_t real_capacity = PFX##_impl_calculate_size(capacity / load); \
|
||||
\
|
||||
SNAME *_map_ = malloc(sizeof(SNAME)); \
|
||||
|
||||
@@ -225,6 +225,10 @@ static const size_t cmc_hashtable_primes[] = {53, 97, 191, 383, 769, 1531,
|
||||
if (capacity == 0 || load <= 0 || load >= 1) \
|
||||
return NULL; \
|
||||
\
|
||||
/* Prevent integer overflow */ \
|
||||
if (capacity >= UINTMAX_MAX * load) \
|
||||
return NULL; \
|
||||
\
|
||||
size_t real_capacity = PFX##_impl_calculate_size(capacity / load); \
|
||||
\
|
||||
SNAME *_set_ = malloc(sizeof(SNAME)); \
|
||||
|
||||
@@ -248,6 +248,10 @@ static const size_t cmc_hashtable_primes[] = {53, 97, 191, 383, 769, 1531,
|
||||
if (capacity == 0 || load <= 0) \
|
||||
return NULL; \
|
||||
\
|
||||
/* Prevent integer overflow */ \
|
||||
if (capacity >= UINTMAX_MAX * load) \
|
||||
return NULL; \
|
||||
\
|
||||
size_t real_capacity = PFX##_impl_calculate_size(capacity / load); \
|
||||
\
|
||||
SNAME *_map_ = malloc(sizeof(SNAME)); \
|
||||
|
||||
@@ -45,6 +45,7 @@ bool hm_contains(hashmap *_map_, size_t key);
|
||||
bool hm_empty(hashmap *_map_);
|
||||
size_t hm_count(hashmap *_map_);
|
||||
size_t hm_capacity(hashmap *_map_);
|
||||
cmc_string hm_to_string(hashmap *_map_);
|
||||
hashmap_iter *hm_iter_new(hashmap *target);
|
||||
void hm_iter_free(hashmap_iter *iter);
|
||||
void hm_iter_init(hashmap_iter *iter, hashmap *target);
|
||||
@@ -79,6 +80,8 @@ hashmap *hm_new(size_t capacity, double load, int (*compare)(size_t, size_t), si
|
||||
{
|
||||
if (capacity == 0 || load <= 0 || load >= 1)
|
||||
return NULL;
|
||||
if (capacity >= UINTMAX_MAX * load)
|
||||
return NULL;
|
||||
size_t real_capacity = hm_impl_calculate_size(capacity / load);
|
||||
hashmap *_map_ = malloc(sizeof(hashmap));
|
||||
if (!_map_)
|
||||
@@ -249,6 +252,14 @@ bool hm_contains(hashmap *_map_, size_t key) { return hm_impl_get_entry(_map_, k
|
||||
bool hm_empty(hashmap *_map_) { return _map_->count == 0; }
|
||||
size_t hm_count(hashmap *_map_) { return _map_->count; }
|
||||
size_t hm_capacity(hashmap *_map_) { return _map_->capacity; }
|
||||
cmc_string hm_to_string(hashmap *_map_)
|
||||
{
|
||||
cmc_string str;
|
||||
hashmap *m_ = _map_;
|
||||
const char *name = "hashmap";
|
||||
snprintf(str.s, cmc_string_len, cmc_string_fmt_hashmap, name, m_, m_->buffer, m_->capacity, m_->count, m_->load, m_->cmp, m_->hash);
|
||||
return str;
|
||||
}
|
||||
hashmap_iter *hm_iter_new(hashmap *target)
|
||||
{
|
||||
hashmap_iter *iter = malloc(sizeof(hashmap_iter));
|
||||
|
||||
@@ -42,6 +42,7 @@ bool hs_contains(hashset *_set_, size_t element);
|
||||
bool hs_empty(hashset *_set_);
|
||||
size_t hs_count(hashset *_set_);
|
||||
size_t hs_capacity(hashset *_set_);
|
||||
cmc_string hs_to_string(hashset *_set_);
|
||||
hashset *hs_union(hashset *_set1_, hashset *_set2_);
|
||||
hashset *hs_intersection(hashset *_set1_, hashset *_set2_);
|
||||
hashset *hs_difference(hashset *_set1_, hashset *_set2_);
|
||||
@@ -77,6 +78,8 @@ hashset *hs_new(size_t capacity, double load, int (*compare)(size_t, size_t), si
|
||||
{
|
||||
if (capacity == 0 || load <= 0 || load >= 1)
|
||||
return NULL;
|
||||
if (capacity >= UINTMAX_MAX * load)
|
||||
return NULL;
|
||||
size_t real_capacity = hs_impl_calculate_size(capacity / load);
|
||||
hashset *_set_ = malloc(sizeof(hashset));
|
||||
if (!_set_)
|
||||
@@ -212,6 +215,14 @@ bool hs_contains(hashset *_set_, size_t element) { return hs_impl_get_entry(_set
|
||||
bool hs_empty(hashset *_set_) { return _set_->count == 0; }
|
||||
size_t hs_count(hashset *_set_) { return _set_->count; }
|
||||
size_t hs_capacity(hashset *_set_) { return _set_->capacity; }
|
||||
cmc_string hs_to_string(hashset *_set_)
|
||||
{
|
||||
cmc_string str;
|
||||
hashset *s_ = _set_;
|
||||
const char *name = "hashset";
|
||||
snprintf(str.s, cmc_string_len, cmc_string_fmt_hashset, name, s_, s_->buffer, s_->capacity, s_->count, s_->load, s_->cmp, s_->hash);
|
||||
return str;
|
||||
}
|
||||
hashset *hs_union(hashset *_set1_, hashset *_set2_)
|
||||
{
|
||||
hashset *_set_r_ = hs_new(_set1_->capacity, _set1_->load, _set1_->cmp, _set1_->hash);
|
||||
|
||||
@@ -31,7 +31,7 @@ typedef struct multimap_iter_s
|
||||
bool start;
|
||||
bool end;
|
||||
} multimap_iter, *multimap_iter_ptr;
|
||||
multimap *mm_new(size_t size, double load, int (*compare)(size_t, size_t), size_t (*hash)(size_t));
|
||||
multimap *mm_new(size_t capacity, double load, int (*compare)(size_t, size_t), size_t (*hash)(size_t));
|
||||
void mm_clear(multimap *_map_);
|
||||
void mm_free(multimap *_map_);
|
||||
bool mm_insert(multimap *_map_, size_t key, size_t value);
|
||||
@@ -82,6 +82,8 @@ multimap *mm_new(size_t capacity, double load, int (*compare)(size_t, size_t), s
|
||||
{
|
||||
if (capacity == 0 || load <= 0)
|
||||
return NULL;
|
||||
if (capacity >= UINTMAX_MAX * load)
|
||||
return NULL;
|
||||
size_t real_capacity = mm_impl_calculate_size(capacity / load);
|
||||
multimap *_map_ = malloc(sizeof(multimap));
|
||||
if (!_map_)
|
||||
|
||||
Reference in new issue
Block a user