xref: /llvm-project/mlir/test/Conversion/ConvertToSPIRV/vector.mlir (revision 25ae1a266d50f24a8fffc57152d7f3c3fcb65517)
1// RUN: mlir-opt -test-convert-to-spirv="run-signature-conversion=false run-vector-unrolling=false" -split-input-file %s | FileCheck %s
2
3// CHECK-LABEL: @extract
4//  CHECK-SAME: %[[ARG:.+]]: vector<2xf32>
5//       CHECK:   spirv.CompositeExtract %[[ARG]][0 : i32] : vector<2xf32>
6//       CHECK:   spirv.CompositeExtract %[[ARG]][1 : i32] : vector<2xf32>
7func.func @extract(%arg0 : vector<2xf32>) -> (vector<1xf32>, f32) {
8  %0 = "vector.extract"(%arg0) <{static_position = array<i64: 0>}> : (vector<2xf32>) -> vector<1xf32>
9  %1 = "vector.extract"(%arg0) <{static_position = array<i64: 1>}> : (vector<2xf32>) -> f32
10  return %0, %1: vector<1xf32>, f32
11}
12
13// -----
14
15// CHECK-LABEL: @extract_size1_vector
16//  CHECK-SAME: %[[ARG0:.+]]: f32
17//       CHECK:   spirv.ReturnValue %[[ARG0]] : f32
18func.func @extract_size1_vector(%arg0 : vector<1xf32>) -> f32 {
19  %0 = vector.extract %arg0[0] : f32 from vector<1xf32>
20  return %0: f32
21}
22
23// -----
24
25// CHECK-LABEL: @insert
26//  CHECK-SAME: %[[V:.*]]: vector<4xf32>, %[[S:.*]]: f32
27//       CHECK:   spirv.CompositeInsert %[[S]], %[[V]][2 : i32] : f32 into vector<4xf32>
28func.func @insert(%arg0 : vector<4xf32>, %arg1: f32) -> vector<4xf32> {
29  %1 = vector.insert %arg1, %arg0[2] : f32 into vector<4xf32>
30  return %1: vector<4xf32>
31}
32
33// -----
34
35// CHECK-LABEL: @insert_index_vector
36//       CHECK:   spirv.CompositeInsert %{{.+}}, %{{.+}}[2 : i32] : i32 into vector<4xi32>
37func.func @insert_index_vector(%arg0 : vector<4xindex>, %arg1: index) -> vector<4xindex> {
38  %1 = vector.insert %arg1, %arg0[2] : index into vector<4xindex>
39  return %1: vector<4xindex>
40}
41
42// -----
43
44// CHECK-LABEL: @insert_size1_vector
45//  CHECK-SAME: %[[V:.*]]: f32, %[[S:.*]]: f32
46//       CHECK:   spirv.ReturnValue %[[S]] : f32
47func.func @insert_size1_vector(%arg0 : vector<1xf32>, %arg1: f32) -> vector<1xf32> {
48  %1 = vector.insert %arg1, %arg0[0] : f32 into vector<1xf32>
49  return %1 : vector<1xf32>
50}
51
52// -----
53
54// CHECK-LABEL: @extract_element
55//  CHECK-SAME: %[[V:.*]]: vector<4xf32>, %[[ID:.*]]: i32
56//       CHECK:   spirv.VectorExtractDynamic %[[V]][%[[ID]]] : vector<4xf32>, i32
57func.func @extract_element(%arg0 : vector<4xf32>, %id : i32) -> f32 {
58  %0 = vector.extractelement %arg0[%id : i32] : vector<4xf32>
59  return %0: f32
60}
61
62// -----
63
64// CHECK-LABEL: @extract_element_cst
65//  CHECK-SAME: %[[V:.*]]: vector<4xf32>
66//       CHECK:   spirv.CompositeExtract %[[V]][1 : i32] : vector<4xf32>
67func.func @extract_element_cst(%arg0 : vector<4xf32>) -> f32 {
68  %idx = arith.constant 1 : i32
69  %0 = vector.extractelement %arg0[%idx : i32] : vector<4xf32>
70  return %0: f32
71}
72
73// -----
74
75// CHECK-LABEL: @extract_element_index
76func.func @extract_element_index(%arg0 : vector<4xf32>, %id : index) -> f32 {
77  // CHECK: spirv.VectorExtractDynamic
78  %0 = vector.extractelement %arg0[%id : index] : vector<4xf32>
79  return %0: f32
80}
81
82// -----
83
84// CHECK-LABEL: @extract_element_size1_vector
85//  CHECK-SAME:(%[[S:.+]]: f32,
86func.func @extract_element_size1_vector(%arg0 : f32, %i: index) -> f32 {
87  %bcast = vector.broadcast %arg0 : f32 to vector<1xf32>
88  %0 = vector.extractelement %bcast[%i : index] : vector<1xf32>
89  // CHECK: spirv.ReturnValue %[[S]]
90  return %0: f32
91}
92
93// -----
94
95// CHECK-LABEL: @extract_element_0d_vector
96//  CHECK-SAME: (%[[S:.+]]: f32)
97func.func @extract_element_0d_vector(%arg0 : f32) -> f32 {
98  %bcast = vector.broadcast %arg0 : f32 to vector<f32>
99  %0 = vector.extractelement %bcast[] : vector<f32>
100  // CHECK: spirv.ReturnValue %[[S]]
101  return %0: f32
102}
103
104// -----
105
106// CHECK-LABEL: @insert_element
107//  CHECK-SAME: %[[VAL:.*]]: f32, %[[V:.*]]: vector<4xf32>, %[[ID:.*]]: i32
108//       CHECK:   spirv.VectorInsertDynamic %[[VAL]], %[[V]][%[[ID]]] : vector<4xf32>, i32
109func.func @insert_element(%val: f32, %arg0 : vector<4xf32>, %id : i32) -> vector<4xf32> {
110  %0 = vector.insertelement %val, %arg0[%id : i32] : vector<4xf32>
111  return %0: vector<4xf32>
112}
113
114// -----
115
116// CHECK-LABEL: @insert_element_cst
117//  CHECK-SAME: %[[VAL:.*]]: f32, %[[V:.*]]: vector<4xf32>
118//       CHECK:   spirv.CompositeInsert %[[VAL]], %[[V]][2 : i32] : f32 into vector<4xf32>
119func.func @insert_element_cst(%val: f32, %arg0 : vector<4xf32>) -> vector<4xf32> {
120  %idx = arith.constant 2 : i32
121  %0 = vector.insertelement %val, %arg0[%idx : i32] : vector<4xf32>
122  return %0: vector<4xf32>
123}
124
125// -----
126
127// CHECK-LABEL: @insert_element_index
128func.func @insert_element_index(%val: f32, %arg0 : vector<4xf32>, %id : index) -> vector<4xf32> {
129  // CHECK: spirv.VectorInsertDynamic
130  %0 = vector.insertelement %val, %arg0[%id : index] : vector<4xf32>
131  return %0: vector<4xf32>
132}
133
134// -----
135
136// CHECK-LABEL: @insert_element_size1_vector
137//  CHECK-SAME: (%[[S:[a-z0-9]+]]: f32
138func.func @insert_element_size1_vector(%scalar: f32, %vector : vector<1xf32>, %i: index) -> vector<1xf32> {
139  %0 = vector.insertelement %scalar, %vector[%i : index] : vector<1xf32>
140  // CHECK: spirv.ReturnValue %[[S]]
141  return %0: vector<1xf32>
142}
143
144// -----
145
146// CHECK-LABEL: @insert_element_0d_vector
147//  CHECK-SAME: (%[[S:[a-z0-9]+]]: f32
148func.func @insert_element_0d_vector(%scalar: f32, %vector : vector<f32>) -> vector<f32> {
149  %0 = vector.insertelement %scalar, %vector[] : vector<f32>
150  // CHECK: spirv.ReturnValue %[[S]]
151  return %0: vector<f32>
152}
153
154// -----
155
156// CHECK-LABEL: @insert_size1_vector
157//  CHECK-SAME: %[[SUB:.*]]: f32, %[[FULL:.*]]: vector<3xf32>
158//       CHECK:   %[[RET:.*]] = spirv.CompositeInsert %[[SUB]], %[[FULL]][2 : i32] : f32 into vector<3xf32>
159//       CHECK:   spirv.ReturnValue %[[RET]] : vector<3xf32>
160func.func @insert_size1_vector(%arg0 : vector<1xf32>, %arg1: vector<3xf32>) -> vector<3xf32> {
161  %1 = vector.insert_strided_slice %arg0, %arg1 {offsets = [2], strides = [1]} : vector<1xf32> into vector<3xf32>
162  return %1 : vector<3xf32>
163}
164
165// -----
166
167// CHECK-LABEL: @fma
168//  CHECK-SAME: %[[A:.*]]: vector<4xf32>, %[[B:.*]]: vector<4xf32>, %[[C:.*]]: vector<4xf32>
169//       CHECK:   spirv.GL.Fma %[[A]], %[[B]], %[[C]] : vector<4xf32>
170func.func @fma(%a: vector<4xf32>, %b: vector<4xf32>, %c: vector<4xf32>) -> vector<4xf32> {
171  %0 = vector.fma %a, %b, %c: vector<4xf32>
172  return %0 : vector<4xf32>
173}
174
175// -----
176
177// CHECK-LABEL: @fma_size1_vector
178//       CHECK:   spirv.GL.Fma %{{.+}} : f32
179func.func @fma_size1_vector(%a: vector<1xf32>, %b: vector<1xf32>, %c: vector<1xf32>) -> vector<1xf32> {
180  %0 = vector.fma %a, %b, %c: vector<1xf32>
181  return %0 : vector<1xf32>
182}
183
184// -----
185
186// CHECK-LABEL: func @splat
187//  CHECK-SAME: (%[[A:.+]]: f32)
188//       CHECK:   %[[VAL:.+]] = spirv.CompositeConstruct %[[A]], %[[A]], %[[A]], %[[A]]
189//       CHECK:   spirv.ReturnValue %[[VAL]] : vector<4xf32>
190func.func @splat(%f : f32) -> vector<4xf32> {
191  %splat = vector.splat %f : vector<4xf32>
192  return %splat : vector<4xf32>
193}
194
195// -----
196
197// CHECK-LABEL: func @splat_size1_vector
198//  CHECK-SAME: (%[[A:.+]]: f32)
199//       CHECK:   spirv.ReturnValue %[[A]] : f32
200func.func @splat_size1_vector(%f : f32) -> vector<1xf32> {
201  %splat = vector.splat %f : vector<1xf32>
202  return %splat : vector<1xf32>
203}
204
205// -----
206
207// CHECK-LABEL:  func @shuffle
208//  CHECK-SAME:  %[[ARG0:.+]]: f32, %[[ARG1:.+]]: f32
209//       CHECK:    spirv.CompositeConstruct %[[ARG0]], %[[ARG1]], %[[ARG1]], %[[ARG0]] : (f32, f32, f32, f32) -> vector<4xf32>
210func.func @shuffle(%v0 : vector<1xf32>, %v1: vector<1xf32>) -> vector<4xf32> {
211  %shuffle = vector.shuffle %v0, %v1 [0, 1, 1, 0] : vector<1xf32>, vector<1xf32>
212  return %shuffle : vector<4xf32>
213}
214
215// -----
216
217// CHECK-LABEL:  func @shuffle
218//  CHECK-SAME:  %[[V0:.+]]: vector<3xf32>, %[[V1:.+]]: vector<3xf32>
219//       CHECK:    spirv.VectorShuffle [3 : i32, 2 : i32, 5 : i32, 1 : i32] %[[V0]], %[[V1]] : vector<3xf32>, vector<3xf32> -> vector<4xf32>
220func.func @shuffle(%v0 : vector<3xf32>, %v1: vector<3xf32>) -> vector<4xf32> {
221  %shuffle = vector.shuffle %v0, %v1 [3, 2, 5, 1] : vector<3xf32>, vector<3xf32>
222  return %shuffle : vector<4xf32>
223}
224
225// -----
226
227// CHECK-LABEL:  func @shuffle
228//  CHECK-SAME:  %[[ARG0:.+]]: i32, %[[ARG1:.+]]: vector<3xi32>
229//       CHECK:    %[[S1:.+]] = spirv.CompositeExtract %[[ARG1]][1 : i32] : vector<3xi32>
230//       CHECK:    %[[S2:.+]] = spirv.CompositeExtract %[[ARG1]][2 : i32] : vector<3xi32>
231//       CHECK:    %[[RES:.+]] = spirv.CompositeConstruct %[[ARG0]], %[[S1]], %[[S2]] : (i32, i32, i32) -> vector<3xi32>
232//       CHECK:    spirv.ReturnValue %[[RES]]
233func.func @shuffle(%v0 : vector<1xi32>, %v1: vector<3xi32>) -> vector<3xi32> {
234  %shuffle = vector.shuffle %v0, %v1 [0, 2, 3] : vector<1xi32>, vector<3xi32>
235  return %shuffle : vector<3xi32>
236}
237
238// -----
239
240// CHECK-LABEL:  func @shuffle
241//  CHECK-SAME:  %[[ARG0:.+]]: i32, %[[ARG1:.+]]: i32
242//       CHECK:    %[[RES:.+]] = spirv.CompositeConstruct %[[ARG0]], %[[ARG1]] : (i32, i32) -> vector<2xi32>
243//       CHECK:    spirv.ReturnValue %[[RES]]
244func.func @shuffle(%v0 : vector<1xi32>, %v1: vector<1xi32>) -> vector<2xi32> {
245  %shuffle = vector.shuffle %v0, %v1 [0, 1] : vector<1xi32>, vector<1xi32>
246  return %shuffle : vector<2xi32>
247}
248
249// -----
250
251// CHECK-LABEL: func @interleave
252//  CHECK-SAME: (%[[ARG0:.+]]: vector<2xf32>, %[[ARG1:.+]]: vector<2xf32>)
253//       CHECK: %[[SHUFFLE:.*]] = spirv.VectorShuffle [0 : i32, 2 : i32, 1 : i32, 3 : i32] %[[ARG0]], %[[ARG1]] : vector<2xf32>, vector<2xf32> -> vector<4xf32>
254//       CHECK: spirv.ReturnValue %[[SHUFFLE]]
255func.func @interleave(%a: vector<2xf32>, %b: vector<2xf32>) -> vector<4xf32> {
256  %0 = vector.interleave %a, %b : vector<2xf32> -> vector<4xf32>
257  return %0 : vector<4xf32>
258}
259
260// -----
261
262// CHECK-LABEL: func @interleave_size1
263// CHECK-SAME: (%[[ARG0:.+]]: f32, %[[ARG1:.+]]: f32)
264//       CHECK: %[[RES:.*]] = spirv.CompositeConstruct %[[ARG0]], %[[ARG1]] : (f32, f32) -> vector<2xf32>
265//       CHECK: spirv.ReturnValue %[[RES]]
266func.func @interleave_size1(%a: vector<1xf32>, %b: vector<1xf32>) -> vector<2xf32> {
267  %0 = vector.interleave %a, %b : vector<1xf32> -> vector<2xf32>
268  return %0 : vector<2xf32>
269}
270
271// -----
272
273// CHECK-LABEL: func @reduction_add
274//  CHECK-SAME: (%[[V:.+]]: vector<4xi32>)
275//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<4xi32>
276//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<4xi32>
277//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<4xi32>
278//       CHECK:   %[[S3:.+]] = spirv.CompositeExtract %[[V]][3 : i32] : vector<4xi32>
279//       CHECK:   %[[ADD0:.+]] = spirv.IAdd %[[S0]], %[[S1]]
280//       CHECK:   %[[ADD1:.+]] = spirv.IAdd %[[ADD0]], %[[S2]]
281//       CHECK:   %[[ADD2:.+]] = spirv.IAdd %[[ADD1]], %[[S3]]
282//       CHECK:   spirv.ReturnValue %[[ADD2]]
283func.func @reduction_add(%v : vector<4xi32>) -> i32 {
284  %reduce = vector.reduction <add>, %v : vector<4xi32> into i32
285  return %reduce : i32
286}
287
288// -----
289
290// CHECK-LABEL: func @reduction_addf_one_elem
291//  CHECK-SAME:  (%[[ARG0:.+]]: f32)
292//  CHECK:       spirv.ReturnValue %[[ARG0]] : f32
293func.func @reduction_addf_one_elem(%arg0: vector<1xf32>) -> f32 {
294  %red = vector.reduction <add>, %arg0 : vector<1xf32> into f32
295  return %red : f32
296}
297
298// -----
299
300// CHECK-LABEL: func @reduction_addf_one_elem_acc
301//  CHECK-SAME:  (%[[ARG0:.+]]: f32, %[[ACC:.+]]: f32)
302//  CHECK:       %[[RES:.+]] = spirv.FAdd %[[ACC]], %[[ARG0]] : f32
303//  CHECK:       spirv.ReturnValue %[[RES]] : f32
304func.func @reduction_addf_one_elem_acc(%arg0: vector<1xf32>, %acc: f32) -> f32 {
305  %red = vector.reduction <add>, %arg0, %acc : vector<1xf32> into f32
306  return %red : f32
307}
308
309// -----
310
311// CHECK-LABEL: func @reduction_mul
312//  CHECK-SAME: (%[[V:.+]]: vector<3xf32>, %[[S:.+]]: f32)
313//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xf32>
314//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xf32>
315//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xf32>
316//       CHECK:   %[[MUL0:.+]] = spirv.FMul %[[S0]], %[[S1]]
317//       CHECK:   %[[MUL1:.+]] = spirv.FMul %[[MUL0]], %[[S2]]
318//       CHECK:   %[[MUL2:.+]] = spirv.FMul %[[MUL1]], %[[S]]
319//       CHECK:   spirv.ReturnValue %[[MUL2]]
320func.func @reduction_mul(%v : vector<3xf32>, %s: f32) -> f32 {
321  %reduce = vector.reduction <mul>, %v, %s : vector<3xf32> into f32
322  return %reduce : f32
323}
324
325// -----
326
327// CHECK-LABEL: func @reduction_maximumf
328//  CHECK-SAME: (%[[V:.+]]: vector<3xf32>, %[[S:.+]]: f32)
329//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xf32>
330//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xf32>
331//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xf32>
332//       CHECK:   %[[MAX0:.+]] = spirv.GL.FMax %[[S0]], %[[S1]]
333//       CHECK:   %[[MAX1:.+]] = spirv.GL.FMax %[[MAX0]], %[[S2]]
334//       CHECK:   %[[MAX2:.+]] = spirv.GL.FMax %[[MAX1]], %[[S]]
335//       CHECK:   spirv.ReturnValue %[[MAX2]]
336func.func @reduction_maximumf(%v : vector<3xf32>, %s: f32) -> f32 {
337  %reduce = vector.reduction <maximumf>, %v, %s : vector<3xf32> into f32
338  return %reduce : f32
339}
340
341// -----
342
343// CHECK-LABEL: func @reduction_minimumf
344//  CHECK-SAME: (%[[V:.+]]: vector<3xf32>, %[[S:.+]]: f32)
345//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xf32>
346//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xf32>
347//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xf32>
348//       CHECK:   %[[MIN0:.+]] = spirv.GL.FMin %[[S0]], %[[S1]]
349//       CHECK:   %[[MIN1:.+]] = spirv.GL.FMin %[[MIN0]], %[[S2]]
350//       CHECK:   %[[MIN2:.+]] = spirv.GL.FMin %[[MIN1]], %[[S]]
351//       CHECK:   spirv.ReturnValue %[[MIN2]]
352func.func @reduction_minimumf(%v : vector<3xf32>, %s: f32) -> f32 {
353  %reduce = vector.reduction <minimumf>, %v, %s : vector<3xf32> into f32
354  return %reduce : f32
355}
356
357// -----
358
359// CHECK-LABEL: func @reduction_maxsi
360//  CHECK-SAME: (%[[V:.+]]: vector<3xi32>, %[[S:.+]]: i32)
361//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xi32>
362//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xi32>
363//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xi32>
364//       CHECK:   %[[MAX0:.+]] = spirv.GL.SMax %[[S0]], %[[S1]]
365//       CHECK:   %[[MAX1:.+]] = spirv.GL.SMax %[[MAX0]], %[[S2]]
366//       CHECK:   %[[MAX2:.+]] = spirv.GL.SMax %[[MAX1]], %[[S]]
367//       CHECK:   spirv.ReturnValue %[[MAX2]]
368func.func @reduction_maxsi(%v : vector<3xi32>, %s: i32) -> i32 {
369  %reduce = vector.reduction <maxsi>, %v, %s : vector<3xi32> into i32
370  return %reduce : i32
371}
372
373// -----
374
375// CHECK-LABEL: func @reduction_minsi
376//  CHECK-SAME: (%[[V:.+]]: vector<3xi32>, %[[S:.+]]: i32)
377//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xi32>
378//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xi32>
379//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xi32>
380//       CHECK:   %[[MIN0:.+]] = spirv.GL.SMin %[[S0]], %[[S1]]
381//       CHECK:   %[[MIN1:.+]] = spirv.GL.SMin %[[MIN0]], %[[S2]]
382//       CHECK:   %[[MIN2:.+]] = spirv.GL.SMin %[[MIN1]], %[[S]]
383//       CHECK:   spirv.ReturnValue %[[MIN2]]
384func.func @reduction_minsi(%v : vector<3xi32>, %s: i32) -> i32 {
385  %reduce = vector.reduction <minsi>, %v, %s : vector<3xi32> into i32
386  return %reduce : i32
387}
388
389// -----
390
391// CHECK-LABEL: func @reduction_maxui
392//  CHECK-SAME: (%[[V:.+]]: vector<3xi32>, %[[S:.+]]: i32)
393//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xi32>
394//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xi32>
395//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xi32>
396//       CHECK:   %[[MAX0:.+]] = spirv.GL.UMax %[[S0]], %[[S1]]
397//       CHECK:   %[[MAX1:.+]] = spirv.GL.UMax %[[MAX0]], %[[S2]]
398//       CHECK:   %[[MAX2:.+]] = spirv.GL.UMax %[[MAX1]], %[[S]]
399//       CHECK:   spirv.ReturnValue %[[MAX2]]
400func.func @reduction_maxui(%v : vector<3xi32>, %s: i32) -> i32 {
401  %reduce = vector.reduction <maxui>, %v, %s : vector<3xi32> into i32
402  return %reduce : i32
403}
404
405// -----
406
407// CHECK-LABEL: func @reduction_minui
408//  CHECK-SAME: (%[[V:.+]]: vector<3xi32>, %[[S:.+]]: i32)
409//       CHECK:   %[[S0:.+]] = spirv.CompositeExtract %[[V]][0 : i32] : vector<3xi32>
410//       CHECK:   %[[S1:.+]] = spirv.CompositeExtract %[[V]][1 : i32] : vector<3xi32>
411//       CHECK:   %[[S2:.+]] = spirv.CompositeExtract %[[V]][2 : i32] : vector<3xi32>
412//       CHECK:   %[[MIN0:.+]] = spirv.GL.UMin %[[S0]], %[[S1]]
413//       CHECK:   %[[MIN1:.+]] = spirv.GL.UMin %[[MIN0]], %[[S2]]
414//       CHECK:   %[[MIN2:.+]] = spirv.GL.UMin %[[MIN1]], %[[S]]
415//       CHECK:   spirv.ReturnValue %[[MIN2]]
416func.func @reduction_minui(%v : vector<3xi32>, %s: i32) -> i32 {
417  %reduce = vector.reduction <minui>, %v, %s : vector<3xi32> into i32
418  return %reduce : i32
419}
420
421// -----
422
423// CHECK-LABEL: @shape_cast_same_type
424//  CHECK-SAME: (%[[ARG0:.*]]: vector<2xf32>)
425//       CHECK:   spirv.ReturnValue %[[ARG0]]
426func.func @shape_cast_same_type(%arg0 : vector<2xf32>) -> vector<2xf32> {
427  %1 = vector.shape_cast %arg0 : vector<2xf32> to vector<2xf32>
428  return %arg0 : vector<2xf32>
429}
430
431// -----
432
433// CHECK-LABEL: @shape_cast_size1_vector
434//  CHECK-SAME: (%[[ARG0:.*]]: f32)
435//       CHECK:   spirv.ReturnValue %[[ARG0]]
436func.func @shape_cast_size1_vector(%arg0 : vector<f32>) -> vector<1xf32> {
437  %1 = vector.shape_cast %arg0 : vector<f32> to vector<1xf32>
438  return %1 : vector<1xf32>
439}
440