mirror of
https://gitlab.winehq.org/wine/vkd3d.git
synced 2025-12-15 08:03:30 -08:00
vkd3d-shader/ir: Move the source and destination operand allocators to struct vsir_program.
This commit is contained in:
committed by
Henri Verbeet
parent
6ed78a0211
commit
d2d22c7af6
Notes:
Henri Verbeet
2025-09-17 12:56:43 +02:00
Approved-by: Giovanni Mascellani (@giomasce) Approved-by: Henri Verbeet (@hverbeet) Merge-Request: https://gitlab.winehq.org/wine/vkd3d/-/merge_requests/1725
@@ -513,11 +513,10 @@ bool vsir_program_add_icb(struct vsir_program *program, struct vkd3d_shader_imme
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
|
static struct vkd3d_shader_src_param *vsir_program_clone_src_params(
|
||||||
struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_src_param *params, size_t count);
|
struct vsir_program *program, const struct vkd3d_shader_src_param *params, size_t count);
|
||||||
|
|
||||||
static bool shader_register_clone_relative_addresses(struct vkd3d_shader_register *reg,
|
static bool shader_register_clone_relative_addresses(struct vkd3d_shader_register *reg, struct vsir_program *program)
|
||||||
struct vkd3d_shader_instruction_array *array)
|
|
||||||
{
|
{
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
@@ -526,45 +525,45 @@ static bool shader_register_clone_relative_addresses(struct vkd3d_shader_registe
|
|||||||
if (!reg->idx[i].rel_addr)
|
if (!reg->idx[i].rel_addr)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (!(reg->idx[i].rel_addr = shader_instruction_array_clone_src_params(array, reg->idx[i].rel_addr, 1)))
|
if (!(reg->idx[i].rel_addr = vsir_program_clone_src_params(program, reg->idx[i].rel_addr, 1)))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct vkd3d_shader_dst_param *shader_instruction_array_clone_dst_params(
|
static struct vkd3d_shader_dst_param *vsir_program_clone_dst_params(
|
||||||
struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_dst_param *params, size_t count)
|
struct vsir_program *program, const struct vkd3d_shader_dst_param *params, size_t count)
|
||||||
{
|
{
|
||||||
struct vkd3d_shader_dst_param *dst_params;
|
struct vkd3d_shader_dst_param *dst_params;
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
if (!(dst_params = shader_dst_param_allocator_get(&array->dst_params, count)))
|
if (!(dst_params = vsir_program_get_dst_params(program, count)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
memcpy(dst_params, params, count * sizeof(*params));
|
memcpy(dst_params, params, count * sizeof(*params));
|
||||||
for (i = 0; i < count; ++i)
|
for (i = 0; i < count; ++i)
|
||||||
{
|
{
|
||||||
if (!shader_register_clone_relative_addresses(&dst_params[i].reg, array))
|
if (!shader_register_clone_relative_addresses(&dst_params[i].reg, program))
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
return dst_params;
|
return dst_params;
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
|
static struct vkd3d_shader_src_param *vsir_program_clone_src_params(
|
||||||
struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_src_param *params, size_t count)
|
struct vsir_program *program, const struct vkd3d_shader_src_param *params, size_t count)
|
||||||
{
|
{
|
||||||
struct vkd3d_shader_src_param *src_params;
|
struct vkd3d_shader_src_param *src_params;
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
if (!(src_params = shader_src_param_allocator_get(&array->src_params, count)))
|
if (!(src_params = vsir_program_get_src_params(program, count)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
memcpy(src_params, params, count * sizeof(*params));
|
memcpy(src_params, params, count * sizeof(*params));
|
||||||
for (i = 0; i < count; ++i)
|
for (i = 0; i < count; ++i)
|
||||||
{
|
{
|
||||||
if (!shader_register_clone_relative_addresses(&src_params[i].reg, array))
|
if (!shader_register_clone_relative_addresses(&src_params[i].reg, program))
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -574,17 +573,11 @@ static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
|
|||||||
static void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *array)
|
static void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *array)
|
||||||
{
|
{
|
||||||
vkd3d_free(array->elements);
|
vkd3d_free(array->elements);
|
||||||
shader_param_allocator_destroy(&array->dst_params);
|
|
||||||
shader_param_allocator_destroy(&array->src_params);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *array, size_t reserve)
|
static bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *array, size_t reserve)
|
||||||
{
|
{
|
||||||
memset(array, 0, sizeof(*array));
|
memset(array, 0, sizeof(*array));
|
||||||
/* Size the parameter initial allocations so they are large enough for most shaders. The
|
|
||||||
* code path for chained allocations will be tested if a few shaders need to use it. */
|
|
||||||
shader_param_allocator_init(&array->dst_params, reserve - reserve / 8u, sizeof(struct vkd3d_shader_dst_param));
|
|
||||||
shader_param_allocator_init(&array->src_params, reserve * 2u, sizeof(struct vkd3d_shader_src_param));
|
|
||||||
|
|
||||||
return shader_instruction_array_reserve(array, reserve);
|
return shader_instruction_array_reserve(array, reserve);
|
||||||
}
|
}
|
||||||
@@ -660,6 +653,11 @@ bool vsir_program_init(struct vsir_program *program, const struct vkd3d_shader_c
|
|||||||
program->shader_version = *version;
|
program->shader_version = *version;
|
||||||
program->cf_type = cf_type;
|
program->cf_type = cf_type;
|
||||||
program->normalisation_level = normalisation_level;
|
program->normalisation_level = normalisation_level;
|
||||||
|
|
||||||
|
/* Size the parameter initial allocations so they are large enough for most shaders. The
|
||||||
|
* code path for chained allocations will be tested if a few shaders need to use it. */
|
||||||
|
shader_param_allocator_init(&program->dst_params, reserve - reserve / 8u, sizeof(struct vkd3d_shader_dst_param));
|
||||||
|
shader_param_allocator_init(&program->src_params, reserve * 2u, sizeof(struct vkd3d_shader_src_param));
|
||||||
if (!shader_instruction_array_init(&program->instructions, reserve))
|
if (!shader_instruction_array_init(&program->instructions, reserve))
|
||||||
{
|
{
|
||||||
if (program->free_parameters)
|
if (program->free_parameters)
|
||||||
@@ -687,6 +685,8 @@ void vsir_program_cleanup(struct vsir_program *program)
|
|||||||
shader_signature_cleanup(&program->output_signature);
|
shader_signature_cleanup(&program->output_signature);
|
||||||
shader_signature_cleanup(&program->patch_constant_signature);
|
shader_signature_cleanup(&program->patch_constant_signature);
|
||||||
vkd3d_shader_free_scan_descriptor_info1(&program->descriptors);
|
vkd3d_shader_free_scan_descriptor_info1(&program->descriptors);
|
||||||
|
shader_param_allocator_destroy(&program->src_params);
|
||||||
|
shader_param_allocator_destroy(&program->dst_params);
|
||||||
for (i = 0; i < program->icb_count; ++i)
|
for (i = 0; i < program->icb_count; ++i)
|
||||||
{
|
{
|
||||||
vkd3d_free(program->icbs[i]);
|
vkd3d_free(program->icbs[i]);
|
||||||
@@ -1087,19 +1087,17 @@ static void vkd3d_shader_instruction_make_nop(struct vkd3d_shader_instruction *i
|
|||||||
|
|
||||||
/* NOTE: Immediate constant buffers are not cloned, so the source must not be destroyed while the
|
/* NOTE: Immediate constant buffers are not cloned, so the source must not be destroyed while the
|
||||||
* destination is in use. This seems like a reasonable requirement given how this is currently used. */
|
* destination is in use. This seems like a reasonable requirement given how this is currently used. */
|
||||||
static bool vsir_program_iterator_clone_instruction(struct vsir_program_iterator *dst_it,
|
static bool vsir_program_iterator_clone_instruction(struct vsir_program *program,
|
||||||
const struct vkd3d_shader_instruction *src)
|
struct vsir_program_iterator *dst_it, const struct vkd3d_shader_instruction *src)
|
||||||
{
|
{
|
||||||
struct vkd3d_shader_instruction *dst = vsir_program_iterator_current(dst_it);
|
struct vkd3d_shader_instruction *dst = vsir_program_iterator_current(dst_it);
|
||||||
|
|
||||||
*dst = *src;
|
*dst = *src;
|
||||||
|
|
||||||
if (dst->dst_count && !(dst->dst = shader_instruction_array_clone_dst_params(dst_it->array,
|
if (dst->dst_count && !(dst->dst = vsir_program_clone_dst_params(program, dst->dst, dst->dst_count)))
|
||||||
dst->dst, dst->dst_count)))
|
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return !dst->src_count || !!(dst->src = shader_instruction_array_clone_src_params(dst_it->array,
|
return !dst->src_count || (dst->src = vsir_program_clone_src_params(program, dst->src, dst->src_count));
|
||||||
dst->src, dst->src_count));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool get_opcode_from_rel_op(enum vkd3d_shader_rel_op rel_op,
|
static bool get_opcode_from_rel_op(enum vkd3d_shader_rel_op rel_op,
|
||||||
@@ -1660,7 +1658,7 @@ static enum vkd3d_result vsir_program_lower_texld_sm1(struct vsir_program *progr
|
|||||||
return VKD3D_ERROR_NOT_IMPLEMENTED;
|
return VKD3D_ERROR_NOT_IMPLEMENTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 3)))
|
if (!(srcs = vsir_program_get_src_params(program, 3)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
/* Note we run before I/O normalization. */
|
/* Note we run before I/O normalization. */
|
||||||
@@ -1736,7 +1734,7 @@ static enum vkd3d_result vsir_program_lower_texld(struct vsir_program *program,
|
|||||||
VKD3D_ASSERT(tex->src[1].reg.idx_count == 1);
|
VKD3D_ASSERT(tex->src[1].reg.idx_count == 1);
|
||||||
VKD3D_ASSERT(!tex->src[1].reg.idx[0].rel_addr);
|
VKD3D_ASSERT(!tex->src[1].reg.idx[0].rel_addr);
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 4)))
|
if (!(srcs = vsir_program_get_src_params(program, 4)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
srcs[0] = tex->src[0];
|
srcs[0] = tex->src[0];
|
||||||
@@ -1779,7 +1777,7 @@ static enum vkd3d_result vsir_program_lower_texldd(struct vsir_program *program,
|
|||||||
VKD3D_ASSERT(texldd->src[1].reg.idx_count == 1);
|
VKD3D_ASSERT(texldd->src[1].reg.idx_count == 1);
|
||||||
VKD3D_ASSERT(!texldd->src[1].reg.idx[0].rel_addr);
|
VKD3D_ASSERT(!texldd->src[1].reg.idx[0].rel_addr);
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 5)))
|
if (!(srcs = vsir_program_get_src_params(program, 5)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
srcs[0] = texldd->src[0];
|
srcs[0] = texldd->src[0];
|
||||||
@@ -1805,7 +1803,7 @@ static enum vkd3d_result vsir_program_lower_texldl(struct vsir_program *program,
|
|||||||
VKD3D_ASSERT(texldl->src[1].reg.idx_count == 1);
|
VKD3D_ASSERT(texldl->src[1].reg.idx_count == 1);
|
||||||
VKD3D_ASSERT(!texldl->src[1].reg.idx[0].rel_addr);
|
VKD3D_ASSERT(!texldl->src[1].reg.idx[0].rel_addr);
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 4)))
|
if (!(srcs = vsir_program_get_src_params(program, 4)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
srcs[0] = texldl->src[0];
|
srcs[0] = texldl->src[0];
|
||||||
@@ -1834,7 +1832,7 @@ static enum vkd3d_result vsir_program_lower_tex(struct vsir_program *program, st
|
|||||||
/* We run before I/O normalization. */
|
/* We run before I/O normalization. */
|
||||||
VKD3D_ASSERT(program->normalisation_level < VSIR_NORMALISED_SM6);
|
VKD3D_ASSERT(program->normalisation_level < VSIR_NORMALISED_SM6);
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 3)))
|
if (!(srcs = vsir_program_get_src_params(program, 3)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
vsir_src_param_init(&srcs[0], VKD3DSPR_TEXTURE, VSIR_DATA_F32, 1);
|
vsir_src_param_init(&srcs[0], VKD3DSPR_TEXTURE, VSIR_DATA_F32, 1);
|
||||||
@@ -1864,7 +1862,7 @@ static enum vkd3d_result vsir_program_lower_texcoord(struct vsir_program *progra
|
|||||||
/* We run before I/O normalization. */
|
/* We run before I/O normalization. */
|
||||||
VKD3D_ASSERT(program->normalisation_level < VSIR_NORMALISED_SM6);
|
VKD3D_ASSERT(program->normalisation_level < VSIR_NORMALISED_SM6);
|
||||||
|
|
||||||
if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 1)))
|
if (!(srcs = vsir_program_get_src_params(program, 1)))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
vsir_src_param_init(&srcs[0], VKD3DSPR_TEXTURE, VSIR_DATA_F32, 1);
|
vsir_src_param_init(&srcs[0], VKD3DSPR_TEXTURE, VSIR_DATA_F32, 1);
|
||||||
@@ -2631,7 +2629,7 @@ static enum vkd3d_result flattener_replicate_location(struct hull_flattener *nor
|
|||||||
struct vsir_program_iterator *it, size_t instance_count, size_t instruction_count)
|
struct vsir_program_iterator *it, size_t instance_count, size_t instruction_count)
|
||||||
{
|
{
|
||||||
struct vsir_program_iterator dst_it, src_it, first_it;
|
struct vsir_program_iterator dst_it, src_it, first_it;
|
||||||
struct vkd3d_shader_instruction *ins;
|
struct vkd3d_shader_instruction *ins, *src_ins;
|
||||||
unsigned int i, j;
|
unsigned int i, j;
|
||||||
size_t count;
|
size_t count;
|
||||||
|
|
||||||
@@ -2647,7 +2645,8 @@ static enum vkd3d_result flattener_replicate_location(struct hull_flattener *nor
|
|||||||
src_it = *it;
|
src_it = *it;
|
||||||
for (j = 0; j < instruction_count; ++j)
|
for (j = 0; j < instruction_count; ++j)
|
||||||
{
|
{
|
||||||
if (!vsir_program_iterator_clone_instruction(&dst_it, vsir_program_iterator_current(&src_it)))
|
src_ins = vsir_program_iterator_current(&src_it);
|
||||||
|
if (!vsir_program_iterator_clone_instruction(normaliser->program, &dst_it, src_ins))
|
||||||
return VKD3D_ERROR_OUT_OF_MEMORY;
|
return VKD3D_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
vsir_program_iterator_next(&dst_it);
|
vsir_program_iterator_next(&dst_it);
|
||||||
@@ -2781,10 +2780,9 @@ static bool control_point_normaliser_is_in_control_point_phase(const struct cont
|
|||||||
|
|
||||||
struct vkd3d_shader_src_param *vsir_program_create_outpointid_param(struct vsir_program *program)
|
struct vkd3d_shader_src_param *vsir_program_create_outpointid_param(struct vsir_program *program)
|
||||||
{
|
{
|
||||||
struct vkd3d_shader_instruction_array *instructions = &program->instructions;
|
|
||||||
struct vkd3d_shader_src_param *rel_addr;
|
struct vkd3d_shader_src_param *rel_addr;
|
||||||
|
|
||||||
if (!(rel_addr = shader_src_param_allocator_get(&instructions->src_params, 1)))
|
if (!(rel_addr = vsir_program_get_src_params(program, 1)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
vsir_register_init(&rel_addr->reg, VKD3DSPR_OUTPOINTID, VSIR_DATA_U32, 0);
|
vsir_register_init(&rel_addr->reg, VKD3DSPR_OUTPOINTID, VSIR_DATA_U32, 0);
|
||||||
|
|||||||
@@ -1421,28 +1421,11 @@ struct vkd3d_shader_param_allocator
|
|||||||
|
|
||||||
void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count);
|
void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count);
|
||||||
|
|
||||||
static inline struct vkd3d_shader_src_param *shader_src_param_allocator_get(
|
|
||||||
struct vkd3d_shader_param_allocator *allocator, size_t count)
|
|
||||||
{
|
|
||||||
VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_src_param));
|
|
||||||
return shader_param_allocator_get(allocator, count);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline struct vkd3d_shader_dst_param *shader_dst_param_allocator_get(
|
|
||||||
struct vkd3d_shader_param_allocator *allocator, size_t count)
|
|
||||||
{
|
|
||||||
VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_dst_param));
|
|
||||||
return shader_param_allocator_get(allocator, count);
|
|
||||||
}
|
|
||||||
|
|
||||||
struct vkd3d_shader_instruction_array
|
struct vkd3d_shader_instruction_array
|
||||||
{
|
{
|
||||||
struct vkd3d_shader_instruction *elements;
|
struct vkd3d_shader_instruction *elements;
|
||||||
size_t capacity;
|
size_t capacity;
|
||||||
size_t count;
|
size_t count;
|
||||||
|
|
||||||
struct vkd3d_shader_param_allocator src_params;
|
|
||||||
struct vkd3d_shader_param_allocator dst_params;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve);
|
bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve);
|
||||||
@@ -1635,6 +1618,9 @@ struct vsir_program
|
|||||||
struct vkd3d_shader_immediate_constant_buffer **icbs;
|
struct vkd3d_shader_immediate_constant_buffer **icbs;
|
||||||
size_t icb_capacity;
|
size_t icb_capacity;
|
||||||
size_t icb_count;
|
size_t icb_count;
|
||||||
|
|
||||||
|
struct vkd3d_shader_param_allocator src_params;
|
||||||
|
struct vkd3d_shader_param_allocator dst_params;
|
||||||
};
|
};
|
||||||
|
|
||||||
enum vkd3d_result vsir_allocate_temp_registers(struct vsir_program *program,
|
enum vkd3d_result vsir_allocate_temp_registers(struct vsir_program *program,
|
||||||
@@ -1676,13 +1662,21 @@ static inline struct vkd3d_shader_instruction *vsir_program_append(struct vsir_p
|
|||||||
static inline struct vkd3d_shader_dst_param *vsir_program_get_dst_params(
|
static inline struct vkd3d_shader_dst_param *vsir_program_get_dst_params(
|
||||||
struct vsir_program *program, unsigned int count)
|
struct vsir_program *program, unsigned int count)
|
||||||
{
|
{
|
||||||
return shader_dst_param_allocator_get(&program->instructions.dst_params, count);
|
struct vkd3d_shader_param_allocator *allocator = &program->dst_params;
|
||||||
|
|
||||||
|
VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_dst_param));
|
||||||
|
|
||||||
|
return shader_param_allocator_get(allocator, count);
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline struct vkd3d_shader_src_param *vsir_program_get_src_params(
|
static inline struct vkd3d_shader_src_param *vsir_program_get_src_params(
|
||||||
struct vsir_program *program, unsigned int count)
|
struct vsir_program *program, unsigned int count)
|
||||||
{
|
{
|
||||||
return shader_src_param_allocator_get(&program->instructions.src_params, count);
|
struct vkd3d_shader_param_allocator *allocator = &program->src_params;
|
||||||
|
|
||||||
|
VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_src_param));
|
||||||
|
|
||||||
|
return shader_param_allocator_get(allocator, count);
|
||||||
}
|
}
|
||||||
|
|
||||||
struct vkd3d_shader_parser
|
struct vkd3d_shader_parser
|
||||||
|
|||||||
Reference in New Issue
Block a user