diff options
| author | Tim Foley <tfoleyNV@users.noreply.github.com> | 2020-06-12 13:30:32 -0700 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2020-06-12 13:30:32 -0700 |
| commit | 36a06f1289c9a68a261920ef5d34f075f2a43219 (patch) | |
| tree | dd11eba962d87da0d437a752b818ddc68f5b6603 /tests | |
| parent | 2359921bb7aba569b36ce3c1904b2dccbde5ffec (diff) | |
Diagnose circularly-defined constants (#1384)
* Diagnose circularly-defined constants
Work on #1374
This change diagnoses cases like the following:
```hlsl
static const int kCircular = kCircular;
static const int kInfinite = kInfinite + 1;
static const int kHere = kThere;
static const int kThere = kHere;
```
By diagnosing these as errors in the front-end we protect against infinite recursion leading to stack overflow crashes.
The basic approach is to have front-end constant folding track variables that are in use when folding a sub-expression, and then diagnosing an error if the same variable is encountered again while it is in use. In order to make sure the error occurs whether or not the constant is referenced, we invoke constant folding on all `static const` integer variables.
Limitations:
* This only works for integers, since that is all front-end constant folding applies to. A future change can/should catch circularity in constants at the IR level (and handle more types).
* This only works for constants. Circular references in the definition of a global variable are harder to diagnose, but at least shouldn't result in compiler crashes.
* This doesn't work across modules, or through generic specialization: anything that requires global knowledge won't be checked
* fixup: missing files
* fixup: review feedback
Diffstat (limited to 'tests')
| -rw-r--r-- | tests/diagnostics/gh-1374.slang | 21 | ||||
| -rw-r--r-- | tests/diagnostics/gh-1374.slang.expected | 8 |
2 files changed, 29 insertions, 0 deletions
diff --git a/tests/diagnostics/gh-1374.slang b/tests/diagnostics/gh-1374.slang new file mode 100644 index 000000000..b1bb04253 --- /dev/null +++ b/tests/diagnostics/gh-1374.slang @@ -0,0 +1,21 @@ +// gh-1374.slang + +// Test a `static` variable wwith a definition that refers to itself + +//DIAGNOSTIC_TEST:REFLECTION:-stage compute -entry main -target hlsl + +struct S +{ + static const int kVal = kVal; + + static const int kInf = kInf + 1; + + static const int kA = kB; + static const int kB = kA; +} + +[numthreads(1, 1, 1)] +void main( + uint3 dispatchThreadID : SV_DispatchThreadID) +{ +}
\ No newline at end of file diff --git a/tests/diagnostics/gh-1374.slang.expected b/tests/diagnostics/gh-1374.slang.expected new file mode 100644 index 000000000..7f4e0d8f0 --- /dev/null +++ b/tests/diagnostics/gh-1374.slang.expected @@ -0,0 +1,8 @@ +result code = 1 +standard error = { +tests/diagnostics/gh-1374.slang(9): error 39999: the initial-value expression for variable 'kVal' depends on the value of the variable itself +tests/diagnostics/gh-1374.slang(11): error 39999: the initial-value expression for variable 'kInf' depends on the value of the variable itself +tests/diagnostics/gh-1374.slang(14): error 39999: the initial-value expression for variable 'kB' depends on the value of the variable itself +} +standard output = { +} |
