src/http/modules/ngx_http_uwsgi_module.c:2038: error: Buffer Overrun L3
  Offset: [0, 535] (⇐ [0, 24] + [0, 511]) Size: [0, 4120] by call to `ngx_hash_init`.

src/http/modules/ngx_http_uwsgi_module.c:2032:5: Assignment
2030.     hash.hash = &params->hash;
2031.     hash.key = ngx_hash_key_lc;
2032.     hash.max_size = 512;
          ^
2033.     hash.bucket_size = 64;
2034.     hash.name = "uwsgi_params_hash";

src/http/modules/ngx_http_uwsgi_module.c:2038:12: Call
2036.     hash.temp_pool = NULL;
2037. 
2038.     return ngx_hash_init(&hash, headers_names.elts, headers_names.nelts);
                 ^
2039. }
2040. 

src/core/ngx_hash.c:251:1: <Offset trace>
249.     (sizeof(void *) + ngx_align((name)->key.len + 2, sizeof(void *)))
250. 
251. ngx_int_t
     ^
252. ngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)
253. {

src/core/ngx_hash.c:251:1: Parameter `hinit->max_size`
  249.     (sizeof(void *) + ngx_align((name)->key.len + 2, sizeof(void *)))
  250. 
  251. ngx_int_t
       ^
  252. ngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)
  253. {

src/core/ngx_hash.c:251:1: <Length trace>
249.     (sizeof(void *) + ngx_align((name)->key.len + 2, sizeof(void *)))
250. 
251. ngx_int_t
     ^
252. ngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)
253. {

src/core/ngx_hash.c:251:1: Parameter `hinit->max_size`
  249.     (sizeof(void *) + ngx_align((name)->key.len + 2, sizeof(void *)))
  250. 
  251. ngx_int_t
       ^
  252. ngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)
  253. {

src/core/ngx_hash.c:371:19: Call
  369. 
  370.     } else {
  371.         buckets = ngx_pcalloc(hinit->pool, size * sizeof(ngx_hash_elt_t *));
                         ^
  372.         if (buckets == NULL) {
  373.             ngx_free(test);

src/core/ngx_palloc.c:297:1: Parameter `size`
    295. 
    296. 
    297. void *
         ^
    298. ngx_pcalloc(ngx_pool_t *pool, size_t size)
    299. {

src/core/ngx_palloc.c:302:9: Call
    300.     void *p;
    301. 
    302.     p = ngx_palloc(pool, size);
                 ^
    303.     if (p) {
    304.         ngx_memzero(p, size);

src/core/ngx_palloc.c:127:16: Call
      125. #if !(NGX_DEBUG_PALLOC)
      126.     if (size <= pool->max) {
      127.         return ngx_palloc_small(pool, size, 1);
                          ^
      128.     }
      129. #endif

src/core/ngx_palloc.c:157:9: Assignment
        155. 
        156.     do {
        157.         m = p->d.last;
                     ^
        158. 
        159.         if (align) {

src/core/ngx_palloc.c:166:13: Assignment
        164.             p->d.last = m + size;
        165. 
        166.             return m;
                         ^
        167.         }
        168. 

src/core/ngx_palloc.c:127:9: Assignment
      125. #if !(NGX_DEBUG_PALLOC)
      126.     if (size <= pool->max) {
      127.         return ngx_palloc_small(pool, size, 1);
                   ^
      128.     }
      129. #endif

src/core/ngx_palloc.c:302:5: Assignment
    300.     void *p;
    301. 
    302.     p = ngx_palloc(pool, size);
             ^
    303.     if (p) {
    304.         ngx_memzero(p, size);

src/core/ngx_palloc.c:307:5: Assignment
    305.     }
    306. 
    307.     return p;
             ^
    308. }
    309. 

src/core/ngx_hash.c:371:9: Assignment
  369. 
  370.     } else {
  371.         buckets = ngx_pcalloc(hinit->pool, size * sizeof(ngx_hash_elt_t *));
               ^
  372.         if (buckets == NULL) {
  373.             ngx_free(test);

src/core/ngx_hash.c:391:9: Array access: Offset: [0, 535] (⇐ [0, 24] + [0, 511]) Size: [0, 4120] by call to `ngx_hash_init` 
  389.         }
  390. 
  391.         buckets[i] = (ngx_hash_elt_t *) elts;
               ^
  392.         elts += test[i];
  393.     }

ngx_int_t
ngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)
{
    u_char          *elts;
    size_t           len;
    u_short         *test;
    ngx_uint_t       i, n, key, size, start, bucket_size;
    ngx_hash_elt_t  *elt, **buckets;
    if (hinit->max_size == 0) {
        ngx_log_error(NGX_LOG_EMERG, hinit->pool->log, 0,
                      "could not build %s, you should "
                      "increase %s_max_size: %i",
                      hinit->name, hinit->name, hinit->max_size);
        return NGX_ERROR;
    }
    for (n = 0; n < nelts; n++) {
        if (hinit->bucket_size < NGX_HASH_ELT_SIZE(&names[n]) + sizeof(void *))
        {
            ngx_log_error(NGX_LOG_EMERG, hinit->pool->log, 0,
                          "could not build %s, you should "
                          "increase %s_bucket_size: %i",
                          hinit->name, hinit->name, hinit->bucket_size);
            return NGX_ERROR;
        }
    }
    test = ngx_alloc(hinit->max_size * sizeof(u_short), hinit->pool->log);
    if (test == NULL) {
        return NGX_ERROR;
    }
    bucket_size = hinit->bucket_size - sizeof(void *);
    start = nelts / (bucket_size / (2 * sizeof(void *)));
    start = start ? start : 1;
    if (hinit->max_size > 10000 && nelts && hinit->max_size / nelts < 100) {
        start = hinit->max_size - 1000;
    }
    for (size = start; size <= hinit->max_size; size++) {
        ngx_memzero(test, size * sizeof(u_short));
        for (n = 0; n < nelts; n++) {
            if (names[n].key.data == NULL) {
                continue;
            }
            key = names[n].key_hash % size;
            test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));
#if 0
            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,
                          "%ui: %ui %ui \"%V\"",
                          size, key, test[key], &names[n].key);
#endif
            if (test[key] > (u_short) bucket_size) {
                goto next;
            }
        }
        goto found;
    next:
        continue;
    }
    size = hinit->max_size;
    ngx_log_error(NGX_LOG_WARN, hinit->pool->log, 0,
                  "could not build optimal %s, you should increase "
                  "either %s_max_size: %i or %s_bucket_size: %i; "
                  "ignoring %s_bucket_size",
                  hinit->name, hinit->name, hinit->max_size,
                  hinit->name, hinit->bucket_size, hinit->name);
found:
    for (i = 0; i < size; i++) {
        test[i] = sizeof(void *);
    }
    for (n = 0; n < nelts; n++) {
        if (names[n].key.data == NULL) {
            continue;
        }
        key = names[n].key_hash % size;
        test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));
    }
    len = 0;
    for (i = 0; i < size; i++) {
        if (test[i] == sizeof(void *)) {
            continue;
        }
        test[i] = (u_short) (ngx_align(test[i], ngx_cacheline_size));
        len += test[i];
    }
    if (hinit->hash == NULL) {
        hinit->hash = ngx_pcalloc(hinit->pool, sizeof(ngx_hash_wildcard_t)
                                             + size * sizeof(ngx_hash_elt_t *));
        if (hinit->hash == NULL) {
            ngx_free(test);
            return NGX_ERROR;
        }
        buckets = (ngx_hash_elt_t **)
                      ((u_char *) hinit->hash + sizeof(ngx_hash_wildcard_t));
    } else {
        buckets = ngx_pcalloc(hinit->pool, size * sizeof(ngx_hash_elt_t *));
        if (buckets == NULL) {
            ngx_free(test);
            return NGX_ERROR;
        }
    }
    elts = ngx_palloc(hinit->pool, len + ngx_cacheline_size);
    if (elts == NULL) {
        ngx_free(test);
        return NGX_ERROR;
    }
    elts = ngx_align_ptr(elts, ngx_cacheline_size);
    for (i = 0; i < size; i++) {
        if (test[i] == sizeof(void *)) {
            continue;
        }
        buckets[i] = (ngx_hash_elt_t *) elts;
        elts += test[i];
    }
    for (i = 0; i < size; i++) {
        test[i] = 0;
    }
    for (n = 0; n < nelts; n++) {
        if (names[n].key.data == NULL) {
            continue;
        }
        key = names[n].key_hash % size;
        elt = (ngx_hash_elt_t *) ((u_char *) buckets[key] + test[key]);
        elt->value = names[n].value;
        elt->len = (u_short) names[n].key.len;
        ngx_strlow(elt->name, names[n].key.data, names[n].key.len);
        test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));
    }
    for (i = 0; i < size; i++) {
        if (buckets[i] == NULL) {
            continue;
        }
        elt = (ngx_hash_elt_t *) ((u_char *) buckets[i] + test[i]);
        elt->value = NULL;
    }
    ngx_free(test);
    hinit->hash->buckets = buckets;
    hinit->hash->size = size;
#if 0
    for (i = 0; i < size; i++) {
        ngx_str_t   val;
        ngx_uint_t  key;
        elt = buckets[i];
        if (elt == NULL) {
            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,
                          "%ui: NULL", i);
            continue;
        }
        while (elt->value) {
            val.len = elt->len;
            val.data = &elt->name[0];
            key = hinit->key(val.data, val.len);
            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,
                          "%ui: %p \"%V\" %ui", i, elt, &val, key);
            elt = (ngx_hash_elt_t *) ngx_align_ptr(&elt->name[0] + elt->len,
                                                   sizeof(void *));
        }
    }
#endif
    return NGX_OK;
}
['static ngx_int_t\nngx_http_uwsgi_init_params(ngx_conf_t *cf, ngx_http_uwsgi_loc_conf_t *conf,\n    ngx_http_uwsgi_params_t *params, ngx_keyval_t *default_params)\n{\n    u_char                       *p;\n    size_t                        size;\n    uintptr_t                    *code;\n    ngx_uint_t                    i, nsrc;\n    ngx_array_t                   headers_names, params_merged;\n    ngx_keyval_t                 *h;\n    ngx_hash_key_t               *hk;\n    ngx_hash_init_t               hash;\n    ngx_http_upstream_param_t    *src, *s;\n    ngx_http_script_compile_t     sc;\n    ngx_http_script_copy_code_t  *copy;\n    if (params->hash.buckets) {\n        return NGX_OK;\n    }\n    if (conf->params_source == NULL && default_params == NULL) {\n        params->hash.buckets = (void *) 1;\n        return NGX_OK;\n    }\n    params->lengths = ngx_array_create(cf->pool, 64, 1);\n    if (params->lengths == NULL) {\n        return NGX_ERROR;\n    }\n    params->values = ngx_array_create(cf->pool, 512, 1);\n    if (params->values == NULL) {\n        return NGX_ERROR;\n    }\n    if (ngx_array_init(&headers_names, cf->temp_pool, 4, sizeof(ngx_hash_key_t))\n        != NGX_OK)\n    {\n        return NGX_ERROR;\n    }\n    if (conf->params_source) {\n        src = conf->params_source->elts;\n        nsrc = conf->params_source->nelts;\n    } else {\n        src = NULL;\n        nsrc = 0;\n    }\n    if (default_params) {\n        if (ngx_array_init(&params_merged, cf->temp_pool, 4,\n                           sizeof(ngx_http_upstream_param_t))\n            != NGX_OK)\n        {\n            return NGX_ERROR;\n        }\n        for (i = 0; i < nsrc; i++) {\n            s = ngx_array_push(&params_merged);\n            if (s == NULL) {\n                return NGX_ERROR;\n            }\n            *s = src[i];\n        }\n        h = default_params;\n        while (h->key.len) {\n            src = params_merged.elts;\n            nsrc = params_merged.nelts;\n            for (i = 0; i < nsrc; i++) {\n                if (ngx_strcasecmp(h->key.data, src[i].key.data) == 0) {\n                    goto next;\n                }\n            }\n            s = ngx_array_push(&params_merged);\n            if (s == NULL) {\n                return NGX_ERROR;\n            }\n            s->key = h->key;\n            s->value = h->value;\n            s->skip_empty = 1;\n        next:\n            h++;\n        }\n        src = params_merged.elts;\n        nsrc = params_merged.nelts;\n    }\n    for (i = 0; i < nsrc; i++) {\n        if (src[i].key.len > sizeof("HTTP_") - 1\n            && ngx_strncmp(src[i].key.data, "HTTP_", sizeof("HTTP_") - 1) == 0)\n        {\n            hk = ngx_array_push(&headers_names);\n            if (hk == NULL) {\n                return NGX_ERROR;\n            }\n            hk->key.len = src[i].key.len - 5;\n            hk->key.data = src[i].key.data + 5;\n            hk->key_hash = ngx_hash_key_lc(hk->key.data, hk->key.len);\n            hk->value = (void *) 1;\n            if (src[i].value.len == 0) {\n                continue;\n            }\n        }\n        copy = ngx_array_push_n(params->lengths,\n                                sizeof(ngx_http_script_copy_code_t));\n        if (copy == NULL) {\n            return NGX_ERROR;\n        }\n        copy->code = (ngx_http_script_code_pt) ngx_http_script_copy_len_code;\n        copy->len = src[i].key.len;\n        copy = ngx_array_push_n(params->lengths,\n                                sizeof(ngx_http_script_copy_code_t));\n        if (copy == NULL) {\n            return NGX_ERROR;\n        }\n        copy->code = (ngx_http_script_code_pt) ngx_http_script_copy_len_code;\n        copy->len = src[i].skip_empty;\n        size = (sizeof(ngx_http_script_copy_code_t)\n                + src[i].key.len + sizeof(uintptr_t) - 1)\n               & ~(sizeof(uintptr_t) - 1);\n        copy = ngx_array_push_n(params->values, size);\n        if (copy == NULL) {\n            return NGX_ERROR;\n        }\n        copy->code = ngx_http_script_copy_code;\n        copy->len = src[i].key.len;\n        p = (u_char *) copy + sizeof(ngx_http_script_copy_code_t);\n        ngx_memcpy(p, src[i].key.data, src[i].key.len);\n        ngx_memzero(&sc, sizeof(ngx_http_script_compile_t));\n        sc.cf = cf;\n        sc.source = &src[i].value;\n        sc.flushes = &params->flushes;\n        sc.lengths = &params->lengths;\n        sc.values = &params->values;\n        if (ngx_http_script_compile(&sc) != NGX_OK) {\n            return NGX_ERROR;\n        }\n        code = ngx_array_push_n(params->lengths, sizeof(uintptr_t));\n        if (code == NULL) {\n            return NGX_ERROR;\n        }\n        *code = (uintptr_t) NULL;\n        code = ngx_array_push_n(params->values, sizeof(uintptr_t));\n        if (code == NULL) {\n            return NGX_ERROR;\n        }\n        *code = (uintptr_t) NULL;\n    }\n    code = ngx_array_push_n(params->lengths, sizeof(uintptr_t));\n    if (code == NULL) {\n        return NGX_ERROR;\n    }\n    *code = (uintptr_t) NULL;\n    params->number = headers_names.nelts;\n    hash.hash = &params->hash;\n    hash.key = ngx_hash_key_lc;\n    hash.max_size = 512;\n    hash.bucket_size = 64;\n    hash.name = "uwsgi_params_hash";\n    hash.pool = cf->pool;\n    hash.temp_pool = NULL;\n    return ngx_hash_init(&hash, headers_names.elts, headers_names.nelts);\n}', 'ngx_int_t\nngx_hash_init(ngx_hash_init_t *hinit, ngx_hash_key_t *names, ngx_uint_t nelts)\n{\n    u_char          *elts;\n    size_t           len;\n    u_short         *test;\n    ngx_uint_t       i, n, key, size, start, bucket_size;\n    ngx_hash_elt_t  *elt, **buckets;\n    if (hinit->max_size == 0) {\n        ngx_log_error(NGX_LOG_EMERG, hinit->pool->log, 0,\n                      "could not build %s, you should "\n                      "increase %s_max_size: %i",\n                      hinit->name, hinit->name, hinit->max_size);\n        return NGX_ERROR;\n    }\n    for (n = 0; n < nelts; n++) {\n        if (hinit->bucket_size < NGX_HASH_ELT_SIZE(&names[n]) + sizeof(void *))\n        {\n            ngx_log_error(NGX_LOG_EMERG, hinit->pool->log, 0,\n                          "could not build %s, you should "\n                          "increase %s_bucket_size: %i",\n                          hinit->name, hinit->name, hinit->bucket_size);\n            return NGX_ERROR;\n        }\n    }\n    test = ngx_alloc(hinit->max_size * sizeof(u_short), hinit->pool->log);\n    if (test == NULL) {\n        return NGX_ERROR;\n    }\n    bucket_size = hinit->bucket_size - sizeof(void *);\n    start = nelts / (bucket_size / (2 * sizeof(void *)));\n    start = start ? start : 1;\n    if (hinit->max_size > 10000 && nelts && hinit->max_size / nelts < 100) {\n        start = hinit->max_size - 1000;\n    }\n    for (size = start; size <= hinit->max_size; size++) {\n        ngx_memzero(test, size * sizeof(u_short));\n        for (n = 0; n < nelts; n++) {\n            if (names[n].key.data == NULL) {\n                continue;\n            }\n            key = names[n].key_hash % size;\n            test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));\n#if 0\n            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,\n                          "%ui: %ui %ui \\"%V\\"",\n                          size, key, test[key], &names[n].key);\n#endif\n            if (test[key] > (u_short) bucket_size) {\n                goto next;\n            }\n        }\n        goto found;\n    next:\n        continue;\n    }\n    size = hinit->max_size;\n    ngx_log_error(NGX_LOG_WARN, hinit->pool->log, 0,\n                  "could not build optimal %s, you should increase "\n                  "either %s_max_size: %i or %s_bucket_size: %i; "\n                  "ignoring %s_bucket_size",\n                  hinit->name, hinit->name, hinit->max_size,\n                  hinit->name, hinit->bucket_size, hinit->name);\nfound:\n    for (i = 0; i < size; i++) {\n        test[i] = sizeof(void *);\n    }\n    for (n = 0; n < nelts; n++) {\n        if (names[n].key.data == NULL) {\n            continue;\n        }\n        key = names[n].key_hash % size;\n        test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));\n    }\n    len = 0;\n    for (i = 0; i < size; i++) {\n        if (test[i] == sizeof(void *)) {\n            continue;\n        }\n        test[i] = (u_short) (ngx_align(test[i], ngx_cacheline_size));\n        len += test[i];\n    }\n    if (hinit->hash == NULL) {\n        hinit->hash = ngx_pcalloc(hinit->pool, sizeof(ngx_hash_wildcard_t)\n                                             + size * sizeof(ngx_hash_elt_t *));\n        if (hinit->hash == NULL) {\n            ngx_free(test);\n            return NGX_ERROR;\n        }\n        buckets = (ngx_hash_elt_t **)\n                      ((u_char *) hinit->hash + sizeof(ngx_hash_wildcard_t));\n    } else {\n        buckets = ngx_pcalloc(hinit->pool, size * sizeof(ngx_hash_elt_t *));\n        if (buckets == NULL) {\n            ngx_free(test);\n            return NGX_ERROR;\n        }\n    }\n    elts = ngx_palloc(hinit->pool, len + ngx_cacheline_size);\n    if (elts == NULL) {\n        ngx_free(test);\n        return NGX_ERROR;\n    }\n    elts = ngx_align_ptr(elts, ngx_cacheline_size);\n    for (i = 0; i < size; i++) {\n        if (test[i] == sizeof(void *)) {\n            continue;\n        }\n        buckets[i] = (ngx_hash_elt_t *) elts;\n        elts += test[i];\n    }\n    for (i = 0; i < size; i++) {\n        test[i] = 0;\n    }\n    for (n = 0; n < nelts; n++) {\n        if (names[n].key.data == NULL) {\n            continue;\n        }\n        key = names[n].key_hash % size;\n        elt = (ngx_hash_elt_t *) ((u_char *) buckets[key] + test[key]);\n        elt->value = names[n].value;\n        elt->len = (u_short) names[n].key.len;\n        ngx_strlow(elt->name, names[n].key.data, names[n].key.len);\n        test[key] = (u_short) (test[key] + NGX_HASH_ELT_SIZE(&names[n]));\n    }\n    for (i = 0; i < size; i++) {\n        if (buckets[i] == NULL) {\n            continue;\n        }\n        elt = (ngx_hash_elt_t *) ((u_char *) buckets[i] + test[i]);\n        elt->value = NULL;\n    }\n    ngx_free(test);\n    hinit->hash->buckets = buckets;\n    hinit->hash->size = size;\n#if 0\n    for (i = 0; i < size; i++) {\n        ngx_str_t   val;\n        ngx_uint_t  key;\n        elt = buckets[i];\n        if (elt == NULL) {\n            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,\n                          "%ui: NULL", i);\n            continue;\n        }\n        while (elt->value) {\n            val.len = elt->len;\n            val.data = &elt->name[0];\n            key = hinit->key(val.data, val.len);\n            ngx_log_error(NGX_LOG_ALERT, hinit->pool->log, 0,\n                          "%ui: %p \\"%V\\" %ui", i, elt, &val, key);\n            elt = (ngx_hash_elt_t *) ngx_align_ptr(&elt->name[0] + elt->len,\n                                                   sizeof(void *));\n        }\n    }\n#endif\n    return NGX_OK;\n}', 'void *\nngx_pcalloc(ngx_pool_t *pool, size_t size)\n{\n    void *p;\n    p = ngx_palloc(pool, size);\n    if (p) {\n        ngx_memzero(p, size);\n    }\n    return p;\n}', 'void *\nngx_palloc(ngx_pool_t *pool, size_t size)\n{\n#if !(NGX_DEBUG_PALLOC)\n    if (size <= pool->max) {\n        return ngx_palloc_small(pool, size, 1);\n    }\n#endif\n    return ngx_palloc_large(pool, size);\n}', 'static ngx_inline void *\nngx_palloc_small(ngx_pool_t *pool, size_t size, ngx_uint_t align)\n{\n    u_char      *m;\n    ngx_pool_t  *p;\n    p = pool->current;\n    do {\n        m = p->d.last;\n        if (align) {\n            m = ngx_align_ptr(m, NGX_ALIGNMENT);\n        }\n        if ((size_t) (p->d.end - m) >= size) {\n            p->d.last = m + size;\n            return m;\n        }\n        p = p->d.next;\n    } while (p);\n    return ngx_palloc_block(pool, size);\n}']