From e8c6b2fd1bb75c6a3865745de30f26e235d3f12f Mon Sep 17 00:00:00 2001 From: Victor Stinner Date: Wed, 23 Mar 2016 09:25:01 +0100 Subject: Issue #26588: * _Py_HASHTABLE_ENTRY_DATA: change type from "char *" to "const void *" * Add _Py_HASHTABLE_ENTRY_WRITE_PKEY() macro * Rename _Py_HASHTABLE_ENTRY_WRITE_DATA() macro to _Py_HASHTABLE_ENTRY_WRITE_PDATA() * Add _Py_HASHTABLE_ENTRY_WRITE_DATA() macro --- Modules/_tracemalloc.c | 2 +- Modules/hashtable.c | 10 ++++------ Modules/hashtable.h | 27 +++++++++++++++++++++++---- Python/marshal.c | 2 +- 4 files changed, 29 insertions(+), 12 deletions(-) diff --git a/Modules/_tracemalloc.c b/Modules/_tracemalloc.c index 139b169..0bab540 100644 --- a/Modules/_tracemalloc.c +++ b/Modules/_tracemalloc.c @@ -1263,7 +1263,7 @@ tracemalloc_pyobject_decref_cb(_Py_hashtable_t *tracebacks, void *user_data) { PyObject *obj; - _Py_HASHTABLE_ENTRY_READ_DATA(tracebacks, entry, sizeof(obj), &obj); + _Py_HASHTABLE_ENTRY_READ_DATA(tracebacks, entry, obj); Py_DECREF(obj); return 0; } diff --git a/Modules/hashtable.c b/Modules/hashtable.c index bb20cce..d80acc6 100644 --- a/Modules/hashtable.c +++ b/Modules/hashtable.c @@ -287,7 +287,7 @@ _Py_hashtable_pop_entry(_Py_hashtable_t *ht, size_t key_size, const void *pkey, ht->entries--; if (data != NULL) - _Py_HASHTABLE_ENTRY_READ_DATA(ht, entry, data_size, data); + _Py_HASHTABLE_ENTRY_READ_PDATA(ht, entry, data_size, data); ht->alloc.free(entry); if ((float)ht->entries / (float)ht->num_buckets < HASHTABLE_LOW) @@ -325,10 +325,8 @@ _Py_hashtable_set(_Py_hashtable_t *ht, size_t key_size, const void *pkey, } entry->key_hash = key_hash; - memcpy((void *)_Py_HASHTABLE_ENTRY_KEY(entry), pkey, key_size); - - assert(data_size == ht->data_size); - memcpy(_Py_HASHTABLE_ENTRY_DATA(ht, entry), data, data_size); + _Py_HASHTABLE_ENTRY_WRITE_PKEY(key_size, entry, pkey); + _Py_HASHTABLE_ENTRY_WRITE_PDATA(ht, entry, data_size, data); _Py_slist_prepend(&ht->buckets[index], (_Py_slist_item_t*)entry); ht->entries++; @@ -350,7 +348,7 @@ _Py_hashtable_get(_Py_hashtable_t *ht, size_t key_size,const void *pkey, entry = _Py_hashtable_get_entry(ht, key_size, pkey); if (entry == NULL) return 0; - _Py_HASHTABLE_ENTRY_READ_DATA(ht, entry, data_size, data); + _Py_HASHTABLE_ENTRY_READ_PDATA(ht, entry, data_size, data); return 1; } diff --git a/Modules/hashtable.h b/Modules/hashtable.h index 4199aab..9c3fbdd 100644 --- a/Modules/hashtable.h +++ b/Modules/hashtable.h @@ -30,10 +30,13 @@ typedef struct { } _Py_hashtable_entry_t; #define _Py_HASHTABLE_ENTRY_KEY(ENTRY) \ - ((const void *)((char *)(ENTRY) + sizeof(_Py_hashtable_entry_t))) + ((const void *)((char *)(ENTRY) \ + + sizeof(_Py_hashtable_entry_t))) #define _Py_HASHTABLE_ENTRY_DATA(TABLE, ENTRY) \ - ((char *)(ENTRY) + sizeof(_Py_hashtable_entry_t) + (TABLE)->key_size) + ((const void *)((char *)(ENTRY) \ + + sizeof(_Py_hashtable_entry_t) \ + + (TABLE)->key_size)) /* Get a key value from pkey: use memcpy() rather than a pointer dereference to avoid memory alignment issues. */ @@ -49,10 +52,26 @@ typedef struct { memcpy(&(KEY), _Py_HASHTABLE_ENTRY_KEY(ENTRY), sizeof(KEY)); \ } while (0) -#define _Py_HASHTABLE_ENTRY_READ_DATA(TABLE, ENTRY, DATA_SIZE, DATA) \ +#define _Py_HASHTABLE_ENTRY_WRITE_PKEY(KEY_SIZE, ENTRY, PKEY) \ + do { \ + memcpy((void *)_Py_HASHTABLE_ENTRY_KEY(ENTRY), (PKEY), (KEY_SIZE)); \ + } while (0) + +#define _Py_HASHTABLE_ENTRY_READ_PDATA(TABLE, ENTRY, DATA_SIZE, PDATA) \ + do { \ + assert((DATA_SIZE) == (TABLE)->data_size); \ + memcpy((PDATA), _Py_HASHTABLE_ENTRY_DATA(TABLE, (ENTRY)), \ + (DATA_SIZE)); \ + } while (0) + +#define _Py_HASHTABLE_ENTRY_READ_DATA(TABLE, ENTRY, DATA) \ + _Py_HASHTABLE_ENTRY_READ_PDATA((TABLE), (ENTRY), sizeof(DATA), &(DATA)) + +#define _Py_HASHTABLE_ENTRY_WRITE_PDATA(TABLE, ENTRY, DATA_SIZE, PDATA) \ do { \ assert((DATA_SIZE) == (TABLE)->data_size); \ - memcpy(DATA, _Py_HASHTABLE_ENTRY_DATA(TABLE, ENTRY), DATA_SIZE); \ + memcpy((void *)_Py_HASHTABLE_ENTRY_DATA((TABLE), (ENTRY)), \ + (PDATA), (DATA_SIZE)); \ } while (0) diff --git a/Python/marshal.c b/Python/marshal.c index 83a1885..3be77a8 100644 --- a/Python/marshal.c +++ b/Python/marshal.c @@ -266,7 +266,7 @@ w_ref(PyObject *v, char *flag, WFILE *p) entry = _Py_HASHTABLE_GET_ENTRY(p->hashtable, v); if (entry != NULL) { /* write the reference index to the stream */ - _Py_HASHTABLE_ENTRY_READ_DATA(p->hashtable, entry, sizeof(w), &w); + _Py_HASHTABLE_ENTRY_READ_DATA(p->hashtable, entry, w); /* we don't store "long" indices in the dict */ assert(0 <= w && w <= 0x7fffffff); w_byte(TYPE_REF, p); -- cgit v0.12