[v5,5/7] malloc: mangle tcache entries pointers
Checks
Context |
Check |
Description |
redhat-pt-bot/TryBot-apply_patch |
success
|
Patch applied to master at the time it was sent
|
linaro-tcwg-bot/tcwg_glibc_build--master-arm |
success
|
Build passed
|
linaro-tcwg-bot/tcwg_glibc_build--master-aarch64 |
success
|
Build passed
|
linaro-tcwg-bot/tcwg_glibc_check--master-aarch64 |
fail
|
Test failed
|
linaro-tcwg-bot/tcwg_glibc_check--master-arm |
success
|
Test passed
|
Commit Message
tcache entries are store in mangled linked lists of chunks.
However the initial pointer stored in tcache->entries[index] is stored
unmangled.
Due to this difference, tcache_get_n contains 2 extra conditions to
disambiguate between the original pointer from tcache entries, or the
next pointer within the content of the chunk.
This patch slightly improves tcache_get_n by removing the condition
related to refering to the first pointer by also mangling the pointers
stored in tcache->entries.
The mangling of the entries should also happen on tcache_init as NULL
pointers are also mangled.
---
malloc/malloc.c | 27 +++++++++++----------------
1 file changed, 11 insertions(+), 16 deletions(-)
@@ -3164,8 +3164,8 @@ tcache_put (mchunkptr chunk, size_t tc_idx)
detect a double free. */
e->key = tcache_key;
- e->next = PROTECT_PTR (&e->next, tcache->entries[tc_idx]);
- tcache->entries[tc_idx] = e;
+ e->next = PROTECT_PTR (&e->next, REVEAL_PTR (tcache->entries[tc_idx]));
+ tcache->entries[tc_idx] = PROTECT_PTR (&(tcache->entries[tc_idx]), e);
++(tcache->counts[tc_idx]);
}
@@ -3175,19 +3175,12 @@ tcache_put (mchunkptr chunk, size_t tc_idx)
static __always_inline void *
tcache_get_n (size_t tc_idx, tcache_entry **ep)
{
- tcache_entry *e;
- if (ep == &(tcache->entries[tc_idx]))
- e = *ep;
- else
- e = REVEAL_PTR (*ep);
+ tcache_entry *e = REVEAL_PTR (*ep);
if (__glibc_unlikely (!aligned_OK (e)))
malloc_printerr ("malloc(): unaligned tcache chunk detected");
- if (ep == &(tcache->entries[tc_idx]))
- *ep = REVEAL_PTR (e->next);
- else
- *ep = PROTECT_PTR (ep, REVEAL_PTR (e->next));
+ *ep = PROTECT_PTR (ep, REVEAL_PTR (e->next));
--(tcache->counts[tc_idx]);
e->key = 0;
@@ -3228,7 +3221,7 @@ tcache_double_free_verify (tcache_entry *e, size_t tc_idx)
tcache_entry *tmp;
size_t cnt = 0;
LIBC_PROBE (memory_tcache_double_free, 2, e, tc_idx);
- for (tmp = tcache->entries[tc_idx];
+ for (tmp = REVEAL_PTR (tcache->entries[tc_idx]);
tmp;
tmp = REVEAL_PTR (tmp->next), ++cnt)
{
@@ -3290,13 +3283,13 @@ tcache_thread_shutdown (void)
heap for coalescing. */
for (i = 0; i < TCACHE_MAX_BINS; ++i)
{
- while (tcache_tmp->entries[i])
+ while (REVEAL_PTR (tcache_tmp->entries[i]))
{
- tcache_entry *e = tcache_tmp->entries[i];
+ tcache_entry *e = REVEAL_PTR (tcache_tmp->entries[i]);
if (__glibc_unlikely (!aligned_OK (e)))
malloc_printerr ("tcache_thread_shutdown(): "
"unaligned tcache chunk detected");
- tcache_tmp->entries[i] = REVEAL_PTR (e->next);
+ tcache_tmp->entries[i] = PROTECT_PTR (&(tcache_tmp->entries[i]), REVEAL_PTR (e->next));
__libc_free (e);
}
}
@@ -3337,6 +3330,8 @@ tcache_init(void)
memset (tcache, 0, sizeof (tcache_perthread_struct));
}
+ for (int i = 0; i < mp_.tcache_bins; i++)
+ tcache->entries[i] = PROTECT_PTR (&(tcache->entries[i]), NULL);
}
# define MAYBE_INIT_TCACHE() \
@@ -3699,7 +3694,7 @@ _mid_memalign (size_t alignment, size_t bytes, void *address)
{
/* The tcache itself isn't encoded, but the chain is. */
tcache_entry **tep = & tcache->entries[tc_idx];
- tcache_entry *te = *tep;
+ tcache_entry *te = REVEAL_PTR (*tep);
while (te != NULL && !PTR_IS_ALIGNED (te, alignment))
{
tep = & (te->next);