2 * Copyright (C) 2020 Collabora Ltd.
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 * Authors (Collabora):
24 * Alyssa Rosenzweig <alyssa.rosenzweig@collabora.com>
31 panfrost_sysval_for_ssbo(nir_intrinsic_instr
*instr
)
33 nir_src index
= instr
->src
[0];
34 assert(nir_src_is_const(index
));
35 uint32_t uindex
= nir_src_as_uint(index
);
37 return PAN_SYSVAL(SSBO
, uindex
);
41 panfrost_sysval_for_sampler(nir_intrinsic_instr
*instr
)
43 /* TODO: indirect samplers !!! */
44 nir_src index
= instr
->src
[0];
45 assert(nir_src_is_const(index
));
46 uint32_t uindex
= nir_src_as_uint(index
);
48 return PAN_SYSVAL(SAMPLER
, uindex
);
52 panfrost_nir_sysval_for_intrinsic(nir_intrinsic_instr
*instr
)
54 switch (instr
->intrinsic
) {
55 case nir_intrinsic_load_viewport_scale
:
56 return PAN_SYSVAL_VIEWPORT_SCALE
;
57 case nir_intrinsic_load_viewport_offset
:
58 return PAN_SYSVAL_VIEWPORT_OFFSET
;
59 case nir_intrinsic_load_num_work_groups
:
60 return PAN_SYSVAL_NUM_WORK_GROUPS
;
61 case nir_intrinsic_load_ssbo_address
:
62 case nir_intrinsic_get_buffer_size
:
63 return panfrost_sysval_for_ssbo(instr
);
64 case nir_intrinsic_load_sampler_lod_parameters_pan
:
65 return panfrost_sysval_for_sampler(instr
);
72 panfrost_sysval_for_instr(nir_instr
*instr
, nir_dest
*dest
)
74 nir_intrinsic_instr
*intr
;
79 switch (instr
->type
) {
80 case nir_instr_type_intrinsic
:
81 intr
= nir_instr_as_intrinsic(instr
);
82 sysval
= panfrost_nir_sysval_for_intrinsic(intr
);
85 case nir_instr_type_tex
:
86 tex
= nir_instr_as_tex(instr
);
87 if (tex
->op
!= nir_texop_txs
)
90 sysval
= PAN_SYSVAL(TEXTURE_SIZE
,
91 PAN_TXS_SYSVAL_ID(tex
->texture_index
,
92 nir_tex_instr_dest_size(tex
) -
93 (tex
->is_array
? 1 : 0),
108 panfrost_nir_assign_sysval_body(struct panfrost_sysvals
*ctx
, nir_instr
*instr
)
110 int sysval
= panfrost_sysval_for_instr(instr
, NULL
);
114 /* We have a sysval load; check if it's already been assigned */
116 if (_mesa_hash_table_u64_search(ctx
->sysval_to_id
, sysval
))
119 /* It hasn't -- so assign it now! */
121 unsigned id
= ctx
->sysval_count
++;
122 _mesa_hash_table_u64_insert(ctx
->sysval_to_id
, sysval
, (void *) ((uintptr_t) id
+ 1));
123 ctx
->sysvals
[id
] = sysval
;
127 panfrost_nir_assign_sysvals(struct panfrost_sysvals
*ctx
, void *memctx
, nir_shader
*shader
)
129 ctx
->sysval_count
= 0;
130 ctx
->sysval_to_id
= _mesa_hash_table_u64_create(memctx
);
132 nir_foreach_function(function
, shader
) {
133 if (!function
->impl
) continue;
135 nir_foreach_block(block
, function
->impl
) {
136 nir_foreach_instr_safe(instr
, block
) {
137 panfrost_nir_assign_sysval_body(ctx
, instr
);