• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2019 Google LLC
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #include "source/fuzz/transformation_add_constant_composite.h"
16 
17 #include "gtest/gtest.h"
18 #include "source/fuzz/fuzzer_util.h"
19 #include "test/fuzz/fuzz_test_util.h"
20 
21 namespace spvtools {
22 namespace fuzz {
23 namespace {
24 
TEST(TransformationAddConstantCompositeTest,BasicTest)25 TEST(TransformationAddConstantCompositeTest, BasicTest) {
26   std::string shader = R"(
27                OpCapability Shader
28           %1 = OpExtInstImport "GLSL.std.450"
29                OpMemoryModel Logical GLSL450
30                OpEntryPoint Fragment %4 "main"
31                OpExecutionMode %4 OriginUpperLeft
32                OpSource ESSL 310
33           %2 = OpTypeVoid
34           %3 = OpTypeFunction %2
35           %6 = OpTypeFloat 32
36           %7 = OpTypeVector %6 2
37           %8 = OpTypeMatrix %7 3
38          %11 = OpConstant %6 0
39          %12 = OpConstant %6 1
40          %14 = OpConstant %6 2
41          %15 = OpConstant %6 3
42          %17 = OpConstant %6 4
43          %18 = OpConstant %6 5
44          %21 = OpTypeInt 32 1
45          %22 = OpTypeInt 32 0
46          %23 = OpConstant %22 3
47          %24 = OpTypeArray %21 %23
48          %25 = OpTypeBool
49          %26 = OpTypeStruct %24 %25
50          %29 = OpConstant %21 1
51          %30 = OpConstant %21 2
52          %31 = OpConstant %21 3
53          %33 = OpConstantFalse %25
54          %35 = OpTypeVector %6 3
55          %38 = OpConstant %6 6
56          %39 = OpConstant %6 7
57          %40 = OpConstant %6 8
58           %4 = OpFunction %2 None %3
59           %5 = OpLabel
60                OpReturn
61                OpFunctionEnd
62   )";
63 
64   const auto env = SPV_ENV_UNIVERSAL_1_4;
65   const auto consumer = nullptr;
66   const auto context = BuildModule(env, consumer, shader, kFuzzAssembleOption);
67   spvtools::ValidatorOptions validator_options;
68   ASSERT_TRUE(fuzzerutil::IsValidAndWellFormed(context.get(), validator_options,
69                                                kConsoleMessageConsumer));
70   TransformationContext transformation_context(
71       MakeUnique<FactManager>(context.get()), validator_options);
72   // Too few ids
73   ASSERT_FALSE(TransformationAddConstantComposite(103, 8, {100, 101}, false)
74                    .IsApplicable(context.get(), transformation_context));
75   // Too many ids
76   ASSERT_FALSE(TransformationAddConstantComposite(101, 7, {14, 15, 14}, false)
77                    .IsApplicable(context.get(), transformation_context));
78   // Id already in use
79   ASSERT_FALSE(TransformationAddConstantComposite(40, 7, {11, 12}, false)
80                    .IsApplicable(context.get(), transformation_context));
81   // %39 is not a type
82   ASSERT_FALSE(TransformationAddConstantComposite(100, 39, {11, 12}, false)
83                    .IsApplicable(context.get(), transformation_context));
84 
85   TransformationAddConstantComposite transformations[] = {
86       // %100 = OpConstantComposite %7 %11 %12
87       TransformationAddConstantComposite(100, 7, {11, 12}, false),
88 
89       // %101 = OpConstantComposite %7 %14 %15
90       TransformationAddConstantComposite(101, 7, {14, 15}, false),
91 
92       // %102 = OpConstantComposite %7 %17 %18
93       TransformationAddConstantComposite(102, 7, {17, 18}, false),
94 
95       // %103 = OpConstantComposite %8 %100 %101 %102
96       TransformationAddConstantComposite(103, 8, {100, 101, 102}, false),
97 
98       // %104 = OpConstantComposite %24 %29 %30 %31
99       TransformationAddConstantComposite(104, 24, {29, 30, 31}, false),
100 
101       // %105 = OpConstantComposite %26 %104 %33
102       TransformationAddConstantComposite(105, 26, {104, 33}, false),
103 
104       // %106 = OpConstantComposite %35 %38 %39 %40
105       TransformationAddConstantComposite(106, 35, {38, 39, 40}, false),
106 
107       // Same constants but with an irrelevant fact applied.
108 
109       // %107 = OpConstantComposite %7 %11 %12
110       TransformationAddConstantComposite(107, 7, {11, 12}, true),
111 
112       // %108 = OpConstantComposite %7 %14 %15
113       TransformationAddConstantComposite(108, 7, {14, 15}, true),
114 
115       // %109 = OpConstantComposite %7 %17 %18
116       TransformationAddConstantComposite(109, 7, {17, 18}, true),
117 
118       // %110 = OpConstantComposite %8 %100 %101 %102
119       TransformationAddConstantComposite(110, 8, {100, 101, 102}, true),
120 
121       // %111 = OpConstantComposite %24 %29 %30 %31
122       TransformationAddConstantComposite(111, 24, {29, 30, 31}, true),
123 
124       // %112 = OpConstantComposite %26 %104 %33
125       TransformationAddConstantComposite(112, 26, {104, 33}, true),
126 
127       // %113 = OpConstantComposite %35 %38 %39 %40
128       TransformationAddConstantComposite(113, 35, {38, 39, 40}, true)};
129 
130   for (auto& transformation : transformations) {
131     ASSERT_TRUE(
132         transformation.IsApplicable(context.get(), transformation_context));
133     ApplyAndCheckFreshIds(transformation, context.get(),
134                           &transformation_context);
135   }
136   ASSERT_TRUE(fuzzerutil::IsValidAndWellFormed(context.get(), validator_options,
137                                                kConsoleMessageConsumer));
138 
139   for (uint32_t id = 100; id <= 106; ++id) {
140     ASSERT_FALSE(transformation_context.GetFactManager()->IdIsIrrelevant(id));
141   }
142 
143   for (uint32_t id = 107; id <= 113; ++id) {
144     ASSERT_TRUE(transformation_context.GetFactManager()->IdIsIrrelevant(id));
145   }
146 
147   std::string after_transformation = R"(
148                OpCapability Shader
149           %1 = OpExtInstImport "GLSL.std.450"
150                OpMemoryModel Logical GLSL450
151                OpEntryPoint Fragment %4 "main"
152                OpExecutionMode %4 OriginUpperLeft
153                OpSource ESSL 310
154           %2 = OpTypeVoid
155           %3 = OpTypeFunction %2
156           %6 = OpTypeFloat 32
157           %7 = OpTypeVector %6 2
158           %8 = OpTypeMatrix %7 3
159          %11 = OpConstant %6 0
160          %12 = OpConstant %6 1
161          %14 = OpConstant %6 2
162          %15 = OpConstant %6 3
163          %17 = OpConstant %6 4
164          %18 = OpConstant %6 5
165          %21 = OpTypeInt 32 1
166          %22 = OpTypeInt 32 0
167          %23 = OpConstant %22 3
168          %24 = OpTypeArray %21 %23
169          %25 = OpTypeBool
170          %26 = OpTypeStruct %24 %25
171          %29 = OpConstant %21 1
172          %30 = OpConstant %21 2
173          %31 = OpConstant %21 3
174          %33 = OpConstantFalse %25
175          %35 = OpTypeVector %6 3
176          %38 = OpConstant %6 6
177          %39 = OpConstant %6 7
178          %40 = OpConstant %6 8
179         %100 = OpConstantComposite %7 %11 %12
180         %101 = OpConstantComposite %7 %14 %15
181         %102 = OpConstantComposite %7 %17 %18
182         %103 = OpConstantComposite %8 %100 %101 %102
183         %104 = OpConstantComposite %24 %29 %30 %31
184         %105 = OpConstantComposite %26 %104 %33
185         %106 = OpConstantComposite %35 %38 %39 %40
186         %107 = OpConstantComposite %7 %11 %12
187         %108 = OpConstantComposite %7 %14 %15
188         %109 = OpConstantComposite %7 %17 %18
189         %110 = OpConstantComposite %8 %100 %101 %102
190         %111 = OpConstantComposite %24 %29 %30 %31
191         %112 = OpConstantComposite %26 %104 %33
192         %113 = OpConstantComposite %35 %38 %39 %40
193           %4 = OpFunction %2 None %3
194           %5 = OpLabel
195                OpReturn
196                OpFunctionEnd
197   )";
198   ASSERT_TRUE(IsEqual(env, after_transformation, context.get()));
199 }
200 
TEST(TransformationAddConstantCompositeTest,DisallowBufferBlockDecoration)201 TEST(TransformationAddConstantCompositeTest, DisallowBufferBlockDecoration) {
202   std::string shader = R"(
203                OpCapability Shader
204           %1 = OpExtInstImport "GLSL.std.450"
205                OpMemoryModel Logical GLSL450
206                OpEntryPoint GLCompute %4 "main"
207                OpExecutionMode %4 LocalSize 1 1 1
208                OpSource ESSL 320
209                OpName %4 "main"
210                OpName %7 "buf"
211                OpMemberName %7 0 "a"
212                OpMemberName %7 1 "b"
213                OpName %9 ""
214                OpMemberDecorate %7 0 Offset 0
215                OpMemberDecorate %7 1 Offset 4
216                OpDecorate %7 BufferBlock
217                OpDecorate %9 DescriptorSet 0
218                OpDecorate %9 Binding 0
219           %2 = OpTypeVoid
220           %3 = OpTypeFunction %2
221           %6 = OpTypeInt 32 1
222          %10 = OpConstant %6 42
223           %7 = OpTypeStruct %6 %6
224           %8 = OpTypePointer Uniform %7
225           %9 = OpVariable %8 Uniform
226           %4 = OpFunction %2 None %3
227           %5 = OpLabel
228                OpReturn
229                OpFunctionEnd
230   )";
231 
232   const auto env = SPV_ENV_UNIVERSAL_1_0;
233   const auto consumer = nullptr;
234   const auto context = BuildModule(env, consumer, shader, kFuzzAssembleOption);
235   spvtools::ValidatorOptions validator_options;
236   ASSERT_TRUE(fuzzerutil::IsValidAndWellFormed(context.get(), validator_options,
237                                                kConsoleMessageConsumer));
238   TransformationContext transformation_context(
239       MakeUnique<FactManager>(context.get()), validator_options);
240   ASSERT_FALSE(TransformationAddConstantComposite(100, 7, {10, 10}, false)
241                    .IsApplicable(context.get(), transformation_context));
242 }
243 
TEST(TransformationAddConstantCompositeTest,DisallowBlockDecoration)244 TEST(TransformationAddConstantCompositeTest, DisallowBlockDecoration) {
245   std::string shader = R"(
246                OpCapability Shader
247           %1 = OpExtInstImport "GLSL.std.450"
248                OpMemoryModel Logical GLSL450
249                OpEntryPoint GLCompute %4 "main" %9
250                OpExecutionMode %4 LocalSize 1 1 1
251                OpSource ESSL 320
252                OpName %4 "main"
253                OpName %7 "buf"
254                OpMemberName %7 0 "a"
255                OpMemberName %7 1 "b"
256                OpName %9 ""
257                OpMemberDecorate %7 0 Offset 0
258                OpMemberDecorate %7 1 Offset 4
259                OpDecorate %7 Block
260                OpDecorate %9 DescriptorSet 0
261                OpDecorate %9 Binding 0
262           %2 = OpTypeVoid
263           %3 = OpTypeFunction %2
264           %6 = OpTypeInt 32 1
265          %10 = OpConstant %6 42
266           %7 = OpTypeStruct %6 %6
267           %8 = OpTypePointer StorageBuffer %7
268           %9 = OpVariable %8 StorageBuffer
269           %4 = OpFunction %2 None %3
270           %5 = OpLabel
271                OpReturn
272                OpFunctionEnd
273   )";
274 
275   const auto env = SPV_ENV_UNIVERSAL_1_5;
276   const auto consumer = nullptr;
277   const auto context = BuildModule(env, consumer, shader, kFuzzAssembleOption);
278   spvtools::ValidatorOptions validator_options;
279   ASSERT_TRUE(fuzzerutil::IsValidAndWellFormed(context.get(), validator_options,
280                                                kConsoleMessageConsumer));
281   TransformationContext transformation_context(
282       MakeUnique<FactManager>(context.get()), validator_options);
283   ASSERT_FALSE(TransformationAddConstantComposite(100, 7, {10, 10}, false)
284                    .IsApplicable(context.get(), transformation_context));
285 }
286 
287 }  // namespace
288 }  // namespace fuzz
289 }  // namespace spvtools
290