mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-05 03:08:05 +02:00
nir: Use a tagged pointer for nir_src parents
This allows us to pack the is_if boolean into the bottom bit of the parent pointer, eliminating the boolean and hence shrinking the nir_src by 8 bytes (due to the extra 63 bits of padding incurred in the old layout). Because all access is forced through helpers now, this is a local change. Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io> Reviewed-by: Rhys Perry <pendingchaos02@gmail.com> Acked-by: Faith Ekstrand <faith.ekstrand@collabora.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/24671>
This commit is contained in:
parent
316af8c965
commit
335cf5f22f
1 changed files with 34 additions and 15 deletions
|
|
@ -997,56 +997,75 @@ struct nir_src;
|
|||
struct nir_if;
|
||||
|
||||
typedef struct nir_src {
|
||||
union {
|
||||
/** Instruction that consumes this value as a source. */
|
||||
nir_instr *renamed_parent_instr;
|
||||
struct nir_if *parent_if;
|
||||
};
|
||||
/* Instruction or if-statement that consumes this value as a source. This
|
||||
* should only be accessed through nir_src_* helpers.
|
||||
*
|
||||
* Internally, it is a tagged pointer to a nir_instr or nir_if.
|
||||
*/
|
||||
uintptr_t _parent;
|
||||
|
||||
struct list_head use_link;
|
||||
nir_def *ssa;
|
||||
|
||||
bool is_if;
|
||||
} nir_src;
|
||||
|
||||
/* Layout of the _parent pointer. Bottom bit is set for nir_if parents (clear
|
||||
* for nir_instr parents). Remaining bits are the pointer.
|
||||
*/
|
||||
#define NIR_SRC_PARENT_IS_IF (0x1)
|
||||
#define NIR_SRC_PARENT_MASK (~((uintptr_t) NIR_SRC_PARENT_IS_IF))
|
||||
|
||||
static inline bool
|
||||
nir_src_is_if(const nir_src *src)
|
||||
{
|
||||
return src->is_if;
|
||||
return src->_parent & NIR_SRC_PARENT_IS_IF;
|
||||
}
|
||||
|
||||
static inline nir_instr *
|
||||
nir_src_parent_instr(const nir_src *src)
|
||||
{
|
||||
assert(!nir_src_is_if(src));
|
||||
return src->renamed_parent_instr;
|
||||
|
||||
/* Because it is not an if, the tag is 0, therefore we do not need to mask */
|
||||
return (nir_instr *)(src->_parent);
|
||||
}
|
||||
|
||||
static inline struct nir_if *
|
||||
nir_src_parent_if(const nir_src *src)
|
||||
{
|
||||
assert(nir_src_is_if(src));
|
||||
return src->parent_if;
|
||||
|
||||
/* Because it is an if, the tag is 1, so we need to mask */
|
||||
return (struct nir_if *)(src->_parent & NIR_SRC_PARENT_MASK);
|
||||
}
|
||||
|
||||
static inline void
|
||||
_nir_src_set_parent(nir_src *src, void *parent, bool is_if)
|
||||
{
|
||||
uintptr_t ptr = (uintptr_t) parent;
|
||||
assert((ptr & ~NIR_SRC_PARENT_MASK) == 0 && "pointer must be aligned");
|
||||
|
||||
if (is_if)
|
||||
ptr |= NIR_SRC_PARENT_IS_IF;
|
||||
|
||||
src->_parent = ptr;
|
||||
}
|
||||
|
||||
static inline void
|
||||
nir_src_set_parent_instr(nir_src *src, nir_instr *parent_instr)
|
||||
{
|
||||
src->is_if = false;
|
||||
src->renamed_parent_instr = parent_instr;
|
||||
_nir_src_set_parent(src, parent_instr, false);
|
||||
}
|
||||
|
||||
static inline void
|
||||
nir_src_set_parent_if(nir_src *src, struct nir_if *parent_if)
|
||||
{
|
||||
src->is_if = true;
|
||||
src->parent_if = parent_if;
|
||||
_nir_src_set_parent(src, parent_if, true);
|
||||
}
|
||||
|
||||
static inline nir_src
|
||||
nir_src_init(void)
|
||||
{
|
||||
nir_src src = { { NULL } };
|
||||
nir_src src = { 0 };
|
||||
return src;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue