SpecOp bool->uint/int and uint<->int conversion
Bool -> uint/int with OpSpecConstantOp OpSelect instruction.
uint <-> int conversion with OpSpecConstantOp OpIAdd instruction.
Note, implicit conversion: `const uint = an_int_spec_constant` is not
supported. Explicit type casting is required: `const uint =
uint(an_int_spec_constant)`
diff --git a/SPIRV/GlslangToSpv.cpp b/SPIRV/GlslangToSpv.cpp
index 9249574..0240d8d 100755
--- a/SPIRV/GlslangToSpv.cpp
+++ b/SPIRV/GlslangToSpv.cpp
@@ -1960,7 +1960,6 @@
glslang::TIntermTyped* specNode = arraySizes.getDimNode(dim);
if (specNode != nullptr) {
builder.clearAccessChain();
- // SpecConstantOpModeGuard set_to_spec_const_mode(&builder);
specNode->traverse(this);
return accessChainLoad(specNode->getAsTyped()->getType());
}
@@ -3307,7 +3306,27 @@
break;
case glslang::EOpConvUintToInt:
+ if (builder.isInSpecConstCodeGenMode()) {
+ // Build zero scalar or vector for OpIAdd to do the conversion when
+ // generating for OpSpecConstantOp instruction.
+ zero = builder.makeIntConstant(0);
+ zero = makeSmearedConstant(zero, vectorSize);
+ }
+ // Don't 'break' here as this case should be grouped together with
+ // EOpConvIntToUint when generating normal run-time conversion
+ // instruction.
case glslang::EOpConvIntToUint:
+ if (builder.isInSpecConstCodeGenMode()) {
+ // Build zero scalar or vector for OpIAdd.
+ if (zero == 0) {
+ zero = builder.makeUintConstant(0);
+ zero = makeSmearedConstant(zero, vectorSize);
+ }
+ // Use OpIAdd, instead of OpBitcast to do the conversion when
+ // generating for OpSpecConstantOp instruction.
+ return builder.createBinOp(spv::OpIAdd, destType, operand, zero);
+ }
+ // For normal run-time conversion instruction, use OpBitcast.
convOp = spv::OpBitcast;
break;
diff --git a/SPIRV/SpvBuilder.cpp b/SPIRV/SpvBuilder.cpp
index f69e7fe..df87e9c 100644
--- a/SPIRV/SpvBuilder.cpp
+++ b/SPIRV/SpvBuilder.cpp
@@ -1212,6 +1212,14 @@
Id Builder::createTriOp(Op opCode, Id typeId, Id op1, Id op2, Id op3)
{
+ // Generate code for spec constants if in spec constant operation
+ // generation mode.
+ if (generatingOpCodeForSpecConst) {
+ std::vector<Id> operands(3);
+ operands[0] = op1; operands[1] = op2; operands[2] = op3;
+ return createSpecConstantOp(
+ opCode, typeId, operands, std::vector<Id>());
+ }
Instruction* op = new Instruction(getUniqueId(), typeId, opCode);
op->addIdOperand(op1);
op->addIdOperand(op2);
diff --git a/Test/baseResults/spv.specConstantOperations.vert.out b/Test/baseResults/spv.specConstantOperations.vert.out
index 76853d6..7544b32 100644
--- a/Test/baseResults/spv.specConstantOperations.vert.out
+++ b/Test/baseResults/spv.specConstantOperations.vert.out
@@ -7,7 +7,7 @@
// Module Version 10000
// Generated by (magic number): 80001
-// Id's are bound by 101
+// Id's are bound by 134
Capability Shader
1: ExtInstImport "GLSL.std.450"
@@ -16,109 +16,152 @@
Source GLSL 450
Name 4 "main"
Name 8 "non_const_array_size_from_spec_const("
- Name 15 "array"
- Decorate 10 SpecId 201
- Decorate 24 SpecId 200
- Decorate 26 SpecId 202
- Decorate 27 SpecId 203
+ Name 11 "i"
+ Name 27 "array"
+ Decorate 19 SpecId 201
+ Decorate 40 SpecId 200
+ Decorate 42 SpecId 202
+ Decorate 43 SpecId 203
2: TypeVoid
3: TypeFunction 2
6: TypeInt 32 1
7: TypeFunction 6(int)
- 10: 6(int) SpecConstant 10
- 11: 6(int) Constant 2
- 12: 6(int) SpecConstantOp 128 10 11
- 13: TypeArray 6(int) 12
- 14: TypePointer Function 13
- 16: 6(int) Constant 1
- 17: 6(int) SpecConstantOp 128 10 16
- 18: TypePointer Function 6(int)
- 23: TypeFloat 32
- 24: 23(float) SpecConstant 1078530010
- 25: TypeInt 32 0
- 26: 25(int) SpecConstant 100
- 27: 6(int) SpecConstant 4294967286
- 28: 6(int) SpecConstantOp 126 10
- 29: 6(int) SpecConstantOp 200 10
- 30: 6(int) SpecConstantOp 128 10 11
- 31: 6(int) SpecConstantOp 128 10 11
- 32: 6(int) Constant 3
- 33: 6(int) SpecConstantOp 130 31 32
- 34: 6(int) Constant 4
- 35: 6(int) SpecConstantOp 130 30 34
- 36: 6(int) SpecConstantOp 132 27 11
- 37: 25(int) Constant 2
- 38: 25(int) SpecConstantOp 132 26 37
- 39: 6(int) Constant 5
- 40: 6(int) SpecConstantOp 135 36 39
- 41: 25(int) Constant 5
- 42: 25(int) SpecConstantOp 134 38 41
- 43: 6(int) SpecConstantOp 139 27 34
- 44: 25(int) Constant 4
- 45: 25(int) SpecConstantOp 137 26 44
- 46: 6(int) SpecConstantOp 132 27 32
- 47: 6(int) SpecConstantOp 135 46 39
- 48: 6(int) Constant 10
- 49: 6(int) SpecConstantOp 195 27 48
- 50: 6(int) Constant 20
- 51: 25(int) SpecConstantOp 194 26 50
- 52: 6(int) SpecConstantOp 196 27 16
- 53: 25(int) SpecConstantOp 196 26 11
- 54: 6(int) Constant 256
- 55: 6(int) SpecConstantOp 197 27 54
- 56: 25(int) Constant 512
- 57: 25(int) SpecConstantOp 198 26 56
- 58: TypeBool
- 59: 58(bool) SpecConstantOp 177 10 27
- 60: 58(bool) SpecConstantOp 170 26 26
- 61: 58(bool) SpecConstantOp 173 10 27
- 62: TypeVector 6(int) 4
- 63: 6(int) Constant 30
- 64: 62(ivec4) SpecConstantComposite 50 63 10 10
- 65: TypeVector 25(int) 4
- 66: 25(int) Constant 4294967295
- 67: 25(int) Constant 4294967294
- 68: 65(ivec4) SpecConstantComposite 26 26 66 67
- 69: TypeVector 23(float) 4
- 70: 23(float) Constant 1067450368
- 71: 69(fvec4) SpecConstantComposite 24 70 24 70
- 72: 62(ivec4) SpecConstantOp 200 64
- 73: 62(ivec4) SpecConstantOp 126 64
- 74: 62(ivec4) ConstantComposite 11 11 11 11
- 75: 62(ivec4) SpecConstantOp 128 64 74
- 76: 62(ivec4) SpecConstantOp 128 64 74
- 77: 62(ivec4) ConstantComposite 32 32 32 32
- 78: 62(ivec4) SpecConstantOp 130 76 77
- 79: 62(ivec4) ConstantComposite 34 34 34 34
- 80: 62(ivec4) SpecConstantOp 130 78 79
- 81: 62(ivec4) SpecConstantOp 132 64 74
- 82: 62(ivec4) ConstantComposite 39 39 39 39
- 83: 62(ivec4) SpecConstantOp 135 81 82
- 84: 62(ivec4) SpecConstantOp 139 64 79
- 85: 62(ivec4) ConstantComposite 48 48 48 48
- 86: 62(ivec4) SpecConstantOp 195 64 85
- 87: 62(ivec4) SpecConstantOp 196 64 74
- 88: 6(int) Constant 1024
- 89: 62(ivec4) ConstantComposite 88 88 88 88
- 90: 62(ivec4) SpecConstantOp 197 64 89
- 91: 25(int) Constant 2048
- 92: 65(ivec4) ConstantComposite 91 91 91 91
- 93: 65(ivec4) SpecConstantOp 198 68 92
- 94: 25(int) Constant 0
- 95: 6(int) SpecConstantOp 81 64 0
- 96: TypeVector 6(int) 2
- 97: 96(ivec2) SpecConstantOp 79 64 64 1(GLSL.std.450) 0
- 98: TypeVector 6(int) 3
- 99: 98(ivec3) SpecConstantOp 79 64 64 2 1(GLSL.std.450) 0
- 100: 62(ivec4) SpecConstantOp 79 64 64 1(GLSL.std.450) 2 0 3
+ 10: TypePointer Function 6(int)
+ 12: 6(int) Constant 0
+ 19: 6(int) SpecConstant 10
+ 20: 6(int) Constant 2
+ 21: 6(int) SpecConstantOp 128 19 20
+ 22: TypeBool
+ 24: 6(int) SpecConstantOp 128 19 20
+ 25: TypeArray 6(int) 24
+ 26: TypePointer Function 25
+ 29: 6(int) Constant 1023
+ 32: 6(int) Constant 1
+ 34: 6(int) SpecConstantOp 128 19 32
+ 39: TypeFloat 32
+ 40: 39(float) SpecConstant 1078530010
+ 41: TypeInt 32 0
+ 42: 41(int) SpecConstant 100
+ 43: 6(int) SpecConstant 4294967286
+ 44: 41(int) Constant 0
+ 45: 22(bool) SpecConstantOp 171 19 44
+ 46: 22(bool) SpecConstantOp 171 42 44
+ 47: 6(int) SpecConstantOp 169 45 32 12
+ 48: 41(int) Constant 1
+ 49: 41(int) SpecConstantOp 169 45 48 44
+ 50: 41(int) SpecConstantOp 128 43 44
+ 51: 6(int) SpecConstantOp 128 42 12
+ 52: 6(int) SpecConstantOp 126 19
+ 53: 6(int) SpecConstantOp 200 19
+ 54: 6(int) SpecConstantOp 128 19 20
+ 55: 6(int) SpecConstantOp 128 19 20
+ 56: 6(int) Constant 3
+ 57: 6(int) SpecConstantOp 130 55 56
+ 58: 6(int) Constant 4
+ 59: 6(int) SpecConstantOp 130 54 58
+ 60: 6(int) SpecConstantOp 132 43 20
+ 61: 41(int) Constant 2
+ 62: 41(int) SpecConstantOp 132 42 61
+ 63: 6(int) Constant 5
+ 64: 6(int) SpecConstantOp 135 60 63
+ 65: 41(int) Constant 5
+ 66: 41(int) SpecConstantOp 134 62 65
+ 67: 6(int) SpecConstantOp 139 43 58
+ 68: 41(int) Constant 4
+ 69: 41(int) SpecConstantOp 137 42 68
+ 70: 6(int) SpecConstantOp 132 43 56
+ 71: 6(int) SpecConstantOp 135 70 63
+ 72: 6(int) Constant 10
+ 73: 6(int) SpecConstantOp 195 43 72
+ 74: 6(int) Constant 20
+ 75: 41(int) SpecConstantOp 194 42 74
+ 76: 6(int) SpecConstantOp 196 43 32
+ 77: 41(int) SpecConstantOp 196 42 20
+ 78: 6(int) Constant 256
+ 79: 6(int) SpecConstantOp 197 43 78
+ 80: 41(int) Constant 512
+ 81: 41(int) SpecConstantOp 198 42 80
+ 82: 22(bool) SpecConstantOp 177 19 43
+ 83: 22(bool) SpecConstantOp 170 42 42
+ 84: 22(bool) SpecConstantOp 173 19 43
+ 85: TypeVector 6(int) 4
+ 86: 6(int) Constant 30
+ 87: 85(ivec4) SpecConstantComposite 74 86 19 19
+ 88: TypeVector 41(int) 4
+ 89: 41(int) Constant 4294967295
+ 90: 41(int) Constant 4294967294
+ 91: 88(ivec4) SpecConstantComposite 42 42 89 90
+ 92: TypeVector 39(float) 4
+ 93: 39(float) Constant 1067450368
+ 94: 92(fvec4) SpecConstantComposite 40 93 40 93
+ 95: TypeVector 22(bool) 4
+ 96: 88(ivec4) ConstantComposite 44 44 44 44
+ 97: 95(bvec4) SpecConstantOp 171 87 96
+ 98: 95(bvec4) SpecConstantOp 171 91 96
+ 99: 85(ivec4) ConstantComposite 12 12 12 12
+ 100: 85(ivec4) ConstantComposite 32 32 32 32
+ 101: 85(ivec4) SpecConstantOp 169 97 100 99
+ 102: 88(ivec4) ConstantComposite 48 48 48 48
+ 103: 88(ivec4) SpecConstantOp 169 97 102 96
+ 104: 88(ivec4) SpecConstantOp 128 87 96
+ 105: 85(ivec4) SpecConstantOp 128 91 99
+ 106: 85(ivec4) SpecConstantOp 200 87
+ 107: 85(ivec4) SpecConstantOp 126 87
+ 108: 85(ivec4) ConstantComposite 20 20 20 20
+ 109: 85(ivec4) SpecConstantOp 128 87 108
+ 110: 85(ivec4) SpecConstantOp 128 87 108
+ 111: 85(ivec4) ConstantComposite 56 56 56 56
+ 112: 85(ivec4) SpecConstantOp 130 110 111
+ 113: 85(ivec4) ConstantComposite 58 58 58 58
+ 114: 85(ivec4) SpecConstantOp 130 112 113
+ 115: 85(ivec4) SpecConstantOp 132 87 108
+ 116: 85(ivec4) ConstantComposite 63 63 63 63
+ 117: 85(ivec4) SpecConstantOp 135 115 116
+ 118: 85(ivec4) SpecConstantOp 139 87 113
+ 119: 85(ivec4) ConstantComposite 72 72 72 72
+ 120: 85(ivec4) SpecConstantOp 195 87 119
+ 121: 85(ivec4) SpecConstantOp 196 87 108
+ 122: 6(int) Constant 1024
+ 123: 85(ivec4) ConstantComposite 122 122 122 122
+ 124: 85(ivec4) SpecConstantOp 197 87 123
+ 125: 41(int) Constant 2048
+ 126: 88(ivec4) ConstantComposite 125 125 125 125
+ 127: 88(ivec4) SpecConstantOp 198 91 126
+ 128: 6(int) SpecConstantOp 81 87 0
+ 129: TypeVector 6(int) 2
+ 130: 129(ivec2) SpecConstantOp 79 87 87 1(GLSL.std.450) 0
+ 131: TypeVector 6(int) 3
+ 132: 131(ivec3) SpecConstantOp 79 87 87 2 1(GLSL.std.450) 0
+ 133: 85(ivec4) SpecConstantOp 79 87 87 1(GLSL.std.450) 2 0 3
4(main): 2 Function None 3
5: Label
Return
FunctionEnd
8(non_const_array_size_from_spec_const(): 6(int) Function None 7
9: Label
- 15(array): 14(ptr) Variable Function
- 19: 18(ptr) AccessChain 15(array) 17
- 20: 6(int) Load 19
- ReturnValue 20
+ 11(i): 10(ptr) Variable Function
+ 27(array): 26(ptr) Variable Function
+ Store 11(i) 12
+ Branch 13
+ 13: Label
+ LoopMerge 15 16 None
+ Branch 17
+ 17: Label
+ 18: 6(int) Load 11(i)
+ 23: 22(bool) SLessThan 18 21
+ BranchConditional 23 14 15
+ 14: Label
+ 28: 6(int) Load 11(i)
+ 30: 10(ptr) AccessChain 27(array) 28
+ Store 30 29
+ Branch 16
+ 16: Label
+ 31: 6(int) Load 11(i)
+ 33: 6(int) IAdd 31 32
+ Store 11(i) 33
+ Branch 13
+ 15: Label
+ 35: 10(ptr) AccessChain 27(array) 34
+ 36: 6(int) Load 35
+ ReturnValue 36
FunctionEnd
diff --git a/Test/spv.specConstantOperations.vert b/Test/spv.specConstantOperations.vert
index 91920cf..f2d57bf 100644
--- a/Test/spv.specConstantOperations.vert
+++ b/Test/spv.specConstantOperations.vert
@@ -10,9 +10,15 @@
// Scalars
//
-// Size convert
-//const double float_to_double = double(sp_float);
-//const float double_to_float = float(float_to_double);
+// uint/int <-> bool conversion
+const bool bool_from_int = bool(sp_int);
+const bool bool_from_uint = bool(sp_uint);
+const int int_from_bool = int(bool_from_int);
+const uint uint_from_bool = uint(bool_from_int);
+
+// uint <-> int
+const uint sp_uint_from_sint = uint(sp_sint);
+const int sp_sint_from_uint = int(sp_uint);
// Negate and Not
const int negate_int = -sp_int;
@@ -54,9 +60,15 @@
const uvec4 uv = uvec4(sp_uint, sp_uint, -1, -2);
const vec4 fv = vec4(sp_float, 1.25, sp_float, 1.25);
-// Size convert
-//const dvec4 fv_to_dv = dvec4(fv);
-//const vec4 dv_to_fv = vec4(fv_to_dv);
+// uint/int <-> bool conversion
+const bvec4 bv_from_iv = bvec4(iv);
+const bvec4 bv_from_uv = bvec4(uv);
+const ivec4 iv_from_bv = ivec4(bv_from_iv);
+const uvec4 uv_from_bv = uvec4(bv_from_iv);
+
+// uint <-> int
+const uvec4 uv_from_iv = uvec4(iv);
+const ivec4 iv_from_uv = ivec4(uv);
// Negate and Not
const ivec4 not_iv = ~iv;
@@ -88,6 +100,9 @@
int non_const_array_size_from_spec_const() {
int array[sp_int + 2];
+ for (int i = 0; i < sp_int + 2; i++) {
+ array[i] = 1023;
+ }
return array[sp_int + 1];
}