GH-95245: Store object values and dict pointers in single tagged pointer.#95278
Conversation
…tion to correct header.
|
Is there any documentation about this? It's pretty intricate. |
|
I was going to document this once I'd done the second part of #95245 |
| static inline void | ||
| _PyDictOrValues_SetValues(PyDictOrValues *ptr, PyDictValues *values) | ||
| { | ||
| ptr->values = ((char *)values) - 1; |
There was a problem hiding this comment.
I'm curious why this one is a -1? Naively, I would have expected something like (|1), ie setting the lowest bit. Which would be equivalent to +1.
I assume there's something that goes horribly wrong with that native approach that I am missing, though?
(As far as I can tell, subtracting one should also work. Not sure what C does with null pointers in this context, though.)
There was a problem hiding this comment.
_PyDictOrValues_SetValues mutates the pointer; _PyDictOrValues_GetValues restores the pointer. Think of it as +1, as you suggest, we'd have to undo that using -1 iso. +1. AFAICS, either way is fine.
There was a problem hiding this comment.
Thanks for explaining!
I am working on a prototype with a tagged pointer elsewhere in the code, I so I was looking for exiting examples to learn from.
Thanks for confirming that either way is fine.
I was just wrecking my brain about whether there's something more going on that I was missing. (And something that I would thus be bound to get horriby wrong in my code, where I want to store either a pointer directly, or an odd integer, in the same memory location.)
This is the first part of #95245. Part two will move the weakrefs pointer into the object pre-header.
I have chosen to tag the values pointer, rather than the dict pointer, because it allows
_PyObject_GetDictPtr(PyObject *obj)to continue to return a valid pointer.