Commit Graph

316 Commits

Author SHA1 Message Date
Zebediah Figura
dfea1abbd8 vkd3d-shader/hlsl: Avoid shadowing "jump" in normalize_switch_cases(). 2023-12-07 21:57:33 +01:00
Zebediah Figura
46e135f6a7 vkd3d-shader/hlsl: Avoid shadowing "load" in lower_index_loads().
Found with -Wshadow.
2023-12-07 21:57:16 +01:00
Francisco Casas
736f3ae2df vkd3d-shader/hlsl: Use values at the time of the swizzle's load in copy-propagation.
This preempts us from replacing a swizzle incorrectly, as in the
following example:

    1: A.x = 1.0
    2: A
    3: A.x = 2.0
    4: @2.x

were @4 ends up being 2.0 instead of 1.0, because that's the value stored in
A.x at time 4, and we should be querying it at time 2.

This also helps us to avoid replacing a swizzle with itself in copy-prop
which can result in infinite loops, as with the included tests this commit.

Consider the following sequence of instructions:

    1 : A
    2 : B = @1
    3 : B
    4 : A = @3
    5 : @1.x

Current copy-prop would replace 5 so it points to @3 now:

    1 : A
    2 : B = @1
    3 : B
    4 : A = @3
    5 : @3.x

But in the next iteration it would make it point back to @1, keeping it
spinning infinitively.

The solution is to index the instructions and don't replace the swizzle
if the new load happens after the current load.
2023-11-29 22:53:24 +01:00
Francisco Casas
d877b877b3 vkd3d-shader/hlsl: Record trace of stored values in copy-propagation.
Instead of only storing the value that each variable's component has at
the moment of the instruction currently handled by copy-prop, we store
the trace of all the historic values with their timestamps, i.e. the
instruction index on which the value was stored.

This would allow us to query the value that the variable had at the time
of execution of previous instructions.
2023-11-29 22:53:21 +01:00
Francisco Casas
539294daea vkd3d-shader/hlsl: Move index_instructions() up. 2023-11-29 22:53:19 +01:00
Zebediah Figura
2d1825bb89 vkd3d-shader/hlsl: Remove an unnecessary local variable in copy_propagation_get_value().
Found with -Wshadow.
2023-11-28 00:09:53 +01:00
Jacek Caban
85f21f197c vkd3d-shader: Avoid implicit enum pointer casts in allocate_semantic_register. 2023-11-28 00:09:29 +01:00
Nikolay Sivov
88caf87789 vkd3d-shader/hlsl: Add a helper to check for a numeric type. 2023-11-15 21:48:49 +01:00
Nikolay Sivov
dd6a9135f4 vkd3d-shader/hlsl: Implement tex2Dproj().
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-11-10 20:23:41 +01:00
Zebediah Figura
b1c2852cd7 vkd3d-shader/hlsl: Store function overloads in a list.
The choice to store them in an rbtree was made early on. It does not seem likely
that HLSL programs would define many overloads for any of their functions, but I
suspect the idea was rather that intrinsics would be defined as plain
hlsl_ir_function_decl structures [cf. 447463e590]
and that some intrinsics that could operate on any type would therefore need
many overrides.

This is not how we deal with intrinsics, however. When the first intrinsics were
implemented I made the choice disregard this intended design, and instead match
and convert their types manually, in C. Nothing that has happened in the time
since has led me to question that choice, and in fact, the flexibility with
which we must accommodate functions has led me to believe that matching in this
way was definitely the right choice. The main other designs I see would have
been:

* define each intrinsic variant separately using existing HLSL types. Besides
  efficiency concerns (i.e. this would take more space in memory, and would take
  longer to generate each variant), the normal type-matching rules don't really
  apply to intrinsics.

  [For example: elementwise intrinsics like abs() return the same type as the
  input, including preserving the distinction between float and float1. It is
  legal to define separate HLSL overloads taking float and float1, but trying to
  invoke these functions yields an "ambiguous function call" error.]

* introduce new (semi-)generic types. This is far more code and ends up acting
  like our current scheme (with helpers) in a slightly more complex form.

So I think we can go ahead and rip out this vestige of the original design for
intrinsics.

As for why to change it: rbtrees are simply more complex to deal with, and it
seems unlikely to me that the difference is going to matter. I do not expect any
program to define large quantities of intrinsics; linked list search should be
good enough.
2023-11-09 21:15:11 +01:00
Nikolay Sivov
9a70ae5b6a vkd3d-shader: Add support for floor() on SM1-3.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-11-08 22:49:40 +01:00
Nikolay Sivov
aaef82e680 vkd3d-shader: Add support for ceil() on SM1-3.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-11-08 22:49:40 +01:00
Nikolay Sivov
76e42fbd21 vkd3d-shader/hlsl: Implement ternary operator for SM1.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-11-08 22:49:31 +01:00
Zebediah Figura
f0a6c7de1d vkd3d-shader/hlsl: Record partial allocations in allocate_range(). 2023-11-07 22:26:11 +01:00
Zebediah Figura
c683fc9402 vkd3d-shader/hlsl: Check that a partial register's mask is also available in is_range_available(). 2023-11-07 22:26:10 +01:00
Nikolay Sivov
31346e2cba vkd3d-shader/tpf: Fix used temp registers accounting for dcl_temps.
Otherwise we always output "dcl_temps 1" even when no temp registers were used.
2023-11-06 23:08:10 +01:00
Francisco Casas
eef2163375 vkd3d-shader/tpf: Declare indexable temps.
If var->indexable, then the variable is given a unique register number,
regardless of its lifetime.
2023-10-31 21:59:22 +01:00
Francisco Casas
83c313ecc6 vkd3d-shader/hlsl: Mark vars that require non-constant dereferences. 2023-10-31 21:59:21 +01:00
Francisco Casas
313df300ad vkd3d-shader/hlsl: Rename hlsl_deref.offset to hlsl_deref.rel_offset.
This field is now analogous to vkd3d_shader_register_index.rel_addr.

Also, it makes sense to rename it now because all the constant part of
the offset is now handled to hlsl_deref.const_offset. Consequently, it
may also be NULL now.
2023-10-31 21:59:19 +01:00
Francisco Casas
74767beaf6 vkd3d-shader/hlsl: Absorb hlsl_ir_constant deref offsets into const_offset. 2023-10-31 21:59:18 +01:00
Francisco Casas
1520f327e5 vkd3d-shader/hlsl: Express deref->offset in whole registers.
This is required to use SM4 relative addressing, because it is limited
to whole-register granularity.
2023-10-31 21:59:16 +01:00
Francisco Casas
61a17643a2 vkd3d-shader/hlsl: Split deref-offset into a node and a constant uint.
This uint will be used for the following:

- Since SM4's relative addressing (the capability of passing a register
  as an index to another register) only has whole-register granularity,
  we will need to make the offset node express the offset in
  whole-registers and specify the register component in this uint,
  otherwise we would have to add additional / and % operations in the
  output binary.

- If, after we apply constant folding and copy propagation, we determine
  that the offset is a single constant node, we can store all the offset
  in this uint constant, and remove the offset src.

  This allows DCE to remove a good bunch of the nodes previously required
  only for the offset constants, which makes the output more liteweight
  and readable, and simplifies the implementation of relative addressing
  when writing tpf in the following patches.

In dump_deref(), we use "c" to indicate components instead of whole
registers. Since now both the offset node and the offset uint are in
components a lowered deref would look like:

    var[@42c + 2c]

But, once we express the offset node in whole registers we will remove
the "c" from the node part:

    var[@22 + 3c]
2023-10-31 21:59:14 +01:00
Francisco Casas
81be47c00b vkd3d-shader/hlsl: Introduce hlsl_deref_is_lowered() helper.
Some functions work with dereferences and need to know if they are
lowered yet.

This can be known checking if deref->offset.node is NULL or
deref->data_type is NULL. I am using the latter since it keeps working
even after the following patches that split deref->offset into
constant and variable parts.
2023-10-31 21:59:12 +01:00
Francisco Casas
e93568f290 vkd3d-shader/hlsl: Clean-up instruction block for offset node creation. 2023-10-31 21:59:11 +01:00
Nikolay Sivov
68c14079a6 vkd3d-shader/hlsl: Add a pass to normalize switch cases blocks.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-31 21:59:04 +01:00
Nikolay Sivov
c84d4e3571 vkd3d-shader/hlsl: Add a pass to remove unreachable code.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-31 21:59:03 +01:00
Nikolay Sivov
a4fa323e6c vkd3d-shader/hlsl: Add copy propagation logic for switches.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-31 21:59:02 +01:00
Nikolay Sivov
ec8dfa467f vkd3d-shader/hlsl: Add initial support for parsing 'switch' statements.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-31 21:58:57 +01:00
Francisco Casas
7960836551 vkd3d-shader/hlsl: Remove enum hlsl_error_level (clangd).
It is only used once for calling hlsl_note(), and it expects an enum
vkd3d_shader_log_level values instead.
2023-10-12 23:27:22 +02:00
Nikolay Sivov
8479ceedfc vkd3d-shader/hlsl: Propagate structure fields modifiers when copying shader inputs.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-09 21:58:29 +02:00
Nikolay Sivov
7c378cc6f9 vkd3d-shader/hlsl: Remove conditional branching when condition is a compile time constant.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-10-05 16:16:09 +02:00
Francisco Casas
4ab6572be7 vkd3d-shader/hlsl: Replace hlsl_type_get_regset() uses with hlsl_deref_get_regset(). 2023-10-05 16:15:37 +02:00
Francisco Casas
a214b7374b vkd3d-shader/hlsl: Avoid hlsl_type_get_regset() in allocate_register_reservations(). 2023-10-05 16:15:34 +02:00
Francisco Casas
13f62e60e1 vkd3d-shader/tpf: Remove sm4_src_register.swizzle_type. 2023-10-03 21:27:47 +02:00
Zebediah Figura
fcda20a8c3 vkd3d-shader/hlsl: Use lower_ir() for lower_sqrt(). 2023-09-25 22:07:23 +02:00
Zebediah Figura
496a3a2093 vkd3d-shader/hlsl: Use lower_ir() for lower_division(). 2023-09-25 22:07:22 +02:00
Zebediah Figura
ecd781e809 vkd3d-shader/hlsl: Use lower_ir() for lower_int_abs(). 2023-09-25 22:07:21 +02:00
Zebediah Figura
7944ee9bed vkd3d-shader/hlsl: Use lower_ir() for lower_casts_to_bool(). 2023-09-25 22:07:20 +02:00
Zebediah Figura
65bf6e997c vkd3d-shader/hlsl: Use lower_ir() for more passes. 2023-09-25 22:07:18 +02:00
Nikolay Sivov
6d1ba83856 vkd3d-shader/hlsl: Use conditional moves for arithmetic operators instead of branching.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-09-22 11:06:22 +02:00
Francisco Casas
39563aa5b3 vkd3d-shader/hlsl: Lower matrix swizzles. 2023-09-13 23:10:38 +02:00
Nikolay Sivov
1002a6b357 vkd3d-shader/tpf: Use 'movc' to implement ternary operator.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com>
2023-09-07 19:15:25 +02:00
Zebediah Figura
63e056512d vkd3d-shader/hlsl: Introduce an hlsl_sprintf_alloc() helper. 2023-08-30 22:48:55 +02:00
Zebediah Figura
926575a6f3 vkd3d-shader/hlsl: Force sm1 inputs to be 4-component only for vertex shaders.
Pixel shaders still have an appropriate writemask.
2023-08-24 21:43:44 +02:00
Zebediah Figura
240b9424fb vkd3d-shader/hlsl: Pass an hlsl_block pointer to append_output_copy(). 2023-08-15 21:51:47 +02:00
Zebediah Figura
a04e3a51dd vkd3d-shader/hlsl: Pass an hlsl_block pointer to prepend_input_copy(). 2023-08-15 21:51:39 +02:00
Zebediah Figura
7a4ac1afb1 vkd3d-shader/hlsl: Pass an hlsl_block pointer to prepend_uniform_copy(). 2023-08-15 21:51:37 +02:00
Francisco Casas
d4a49d788a vkd3d-shader/hlsl: Simplify computation of allocation size. 2023-08-15 21:51:32 +02:00
Francisco Casas
37cfbe47d7 vkd3d-shader/hlsl: Sort synthetic separated samplers first for SM4. 2023-08-15 21:51:31 +02:00
Francisco Casas
81afe43569 vkd3d-shader/tpf: Put the actual bind count in the RDEF table. 2023-08-15 21:51:29 +02:00