1
0
Fork 0
mirror of https://github.com/warmcat/libwebsockets.git synced 2025-03-30 00:00:16 +01:00

lws-dsh: fix alignment and boost size add per kind totaling

This commit is contained in:
Andy Green 2021-02-01 21:16:25 +00:00
parent 611e6477fd
commit 9f1bd0a5c8
2 changed files with 20 additions and 6 deletions

View file

@ -1,7 +1,7 @@
/* /*
* libwebsockets - small server side websockets and web server implementation * libwebsockets - small server side websockets and web server implementation
* *
* Copyright (C) 2010 - 2019 Andy Green <andy@warmcat.com> * Copyright (C) 2010 - 2021 Andy Green <andy@warmcat.com>
* *
* Permission is hereby granted, free of charge, to any person obtaining a copy * Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to * of this software and associated documentation files (the "Software"), to
@ -60,6 +60,7 @@ lws_dsh_create(lws_dll2_owner_t *owner, size_t buf_len, int count_kinds)
assert(buf_len); assert(buf_len);
assert(count_kinds > 1); assert(count_kinds > 1);
assert(buf_len > sizeof(lws_dsh_t) + oha_len); assert(buf_len > sizeof(lws_dsh_t) + oha_len);
buf_len += 64;
dsh = lws_malloc(sizeof(lws_dsh_t) + buf_len + oha_len, __func__); dsh = lws_malloc(sizeof(lws_dsh_t) + buf_len + oha_len, __func__);
if (!dsh) if (!dsh)
@ -76,8 +77,10 @@ lws_dsh_create(lws_dll2_owner_t *owner, size_t buf_len, int count_kinds)
/* clear down the obj heads array */ /* clear down the obj heads array */
memset(dsh->oha, 0, oha_len); memset(dsh->oha, 0, oha_len);
for (n = 0; n < count_kinds; n++) for (n = 0; n < count_kinds; n++) {
dsh->oha[n].kind = n; dsh->oha[n].kind = n;
dsh->oha[n].total_size = 0;
}
/* initially the whole buffer is on the free kind (0) list */ /* initially the whole buffer is on the free kind (0) list */
@ -296,6 +299,7 @@ _lws_dsh_alloc_tail(lws_dsh_t *dsh, int kind, const void *src1, size_t size1,
*/ */
lws_dll2_remove(&s.best->list); lws_dll2_remove(&s.best->list);
s.best->dsh = s.dsh; s.best->dsh = s.dsh;
s.best->kind = kind;
s.best->size = size1 + size2; s.best->size = size1 + size2;
memcpy(&s.best[1], src1, size1); memcpy(&s.best[1], src1, size1);
if (src2) if (src2)
@ -310,12 +314,15 @@ _lws_dsh_alloc_tail(lws_dsh_t *dsh, int kind, const void *src1, size_t size1,
if (replace->next) if (replace->next)
replace->next->prev = &s.best->list; replace->next->prev = &s.best->list;
} else } else
if (dsh) if (dsh) {
assert(!(((unsigned long)(intptr_t)(s.best)) & (sizeof(int *) - 1)));
lws_dll2_add_tail(&s.best->list, &dsh->oha[kind].owner); lws_dll2_add_tail(&s.best->list, &dsh->oha[kind].owner);
}
assert(s.dsh->locally_free >= s.best->asize); assert(s.dsh->locally_free >= s.best->asize);
s.dsh->locally_free -= s.best->asize; s.dsh->locally_free -= s.best->asize;
s.dsh->locally_in_use += s.best->asize; s.dsh->locally_in_use += s.best->asize;
dsh->oha[kind].total_size += s.best->asize;
assert(s.dsh->locally_in_use <= s.dsh->buffer_size); assert(s.dsh->locally_in_use <= s.dsh->buffer_size);
} else { } else {
lws_dsh_obj_t *obj; lws_dsh_obj_t *obj;
@ -334,10 +341,11 @@ _lws_dsh_alloc_tail(lws_dsh_t *dsh, int kind, const void *src1, size_t size1,
/* latter part becomes new object */ /* latter part becomes new object */
obj = (lws_dsh_obj_t *)(((uint8_t *)s.best) + s.best->asize); obj = (lws_dsh_obj_t *)(((uint8_t *)s.best) + lws_dsh_align(s.best->asize));
lws_dll2_clear(&obj->list); lws_dll2_clear(&obj->list);
obj->dsh = s.dsh; obj->dsh = s.dsh;
obj->kind = kind;
obj->size = size1 + size2; obj->size = size1 + size2;
obj->asize = asize; obj->asize = asize;
@ -354,12 +362,15 @@ _lws_dsh_alloc_tail(lws_dsh_t *dsh, int kind, const void *src1, size_t size1,
if (replace->next) if (replace->next)
replace->next->prev = &s.best->list; replace->next->prev = &s.best->list;
} else } else
if (dsh) if (dsh) {
assert(!(((unsigned long)(intptr_t)(obj)) & (sizeof(int *) - 1)));
lws_dll2_add_tail(&obj->list, &dsh->oha[kind].owner); lws_dll2_add_tail(&obj->list, &dsh->oha[kind].owner);
}
assert(s.dsh->locally_free >= asize); assert(s.dsh->locally_free >= asize);
s.dsh->locally_free -= asize; s.dsh->locally_free -= asize;
s.dsh->locally_in_use += asize; s.dsh->locally_in_use += asize;
dsh->oha[kind].total_size += asize;
assert(s.dsh->locally_in_use <= s.dsh->buffer_size); assert(s.dsh->locally_in_use <= s.dsh->buffer_size);
} }
@ -402,6 +413,7 @@ lws_dsh_free(void **pobj)
assert(dsh->locally_in_use >= _o->asize); assert(dsh->locally_in_use >= _o->asize);
dsh->locally_free += _o->asize; dsh->locally_free += _o->asize;
dsh->locally_in_use -= _o->asize; dsh->locally_in_use -= _o->asize;
dsh->oha[_o->kind].total_size -= _o->asize; /* account for usage by kind */
assert(dsh->locally_in_use <= dsh->buffer_size); assert(dsh->locally_in_use <= dsh->buffer_size);
/* /*
@ -469,7 +481,7 @@ lws_dsh_get_head(lws_dsh_t *dsh, int kind, void **obj, size_t *size)
*size = _obj->size; *size = _obj->size;
/* anything coming out of here must be aligned */ /* anything coming out of here must be aligned */
assert(!(((unsigned long)(*obj)) & (sizeof(int *) - 1))); assert(!(((unsigned long)(intptr_t)(*obj)) & (sizeof(int *) - 1)));
return 0; /* we returned the head */ return 0; /* we returned the head */
} }

View file

@ -270,6 +270,7 @@ struct lws_timed_vh_protocol {
typedef struct lws_dsh_obj_head { typedef struct lws_dsh_obj_head {
lws_dll2_owner_t owner; lws_dll2_owner_t owner;
size_t total_size; /* for this kind in dsh */
int kind; int kind;
} lws_dsh_obj_head_t; } lws_dsh_obj_head_t;
@ -278,6 +279,7 @@ typedef struct lws_dsh_obj {
struct lws_dsh *dsh; /* invalid when on free list */ struct lws_dsh *dsh; /* invalid when on free list */
size_t size; /* invalid when on free list */ size_t size; /* invalid when on free list */
size_t asize; size_t asize;
int kind; /* so we can account at free */
} lws_dsh_obj_t; } lws_dsh_obj_t;
typedef struct lws_dsh { typedef struct lws_dsh {