Skip to content

Commit 64f326f

Browse files
authored
[SYCL][FPGA][NFC] Fix num_simd_work_items and reqd_work_group_size argument check (#3275)
According to https://www.intel.com/content/www/us/en/programmable/documentation/mwh1391807965224.html#mwh1391807939093 (section : 5.2.13. Specifying Number of SIMD Work-Items): Important: Introduce the num_simd_work_items attribute in conjunction with the reqd_work_group_size attribute. The num_simd_work_items attribute you specify must evenly divide the work-group size you specify for the reqd_work_group_size attribute. Based on discussion, the requirement applies only for X argument of reqd_work_group_size attribute. Signed-off-by: Soumi Manna <[email protected]>
1 parent 86b0e8d commit 64f326f

File tree

3 files changed

+51
-46
lines changed

3 files changed

+51
-46
lines changed

clang/include/clang/Basic/AttrDocs.td

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2421,8 +2421,8 @@ device kernel, the attribute is not ignored and it is propagated to the kernel.
24212421
If the`` intel::reqd_work_group_size`` or ``cl::reqd_work_group_size``
24222422
attribute is specified on a declaration along with a
24232423
intel::num_simd_work_items attribute, the work group size attribute
2424-
arguments must all be evenly divisible by the argument specified in
2425-
the ``intel::num_simd_work_items`` attribute.
2424+
argument (the first argument) must be evenly divisible by the argument specified
2425+
in the ``intel::num_simd_work_items`` attribute.
24262426

24272427
.. code-block:: c++
24282428

clang/lib/Sema/SemaDeclAttr.cpp

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -3155,9 +3155,7 @@ static void handleWorkGroupSize(Sema &S, Decl *D, const ParsedAttr &AL) {
31553155
int64_t NumSimdWorkItems =
31563156
A->getValue()->getIntegerConstantExpr(Ctx)->getSExtValue();
31573157

3158-
if (!(XDimVal.getZExtValue() % NumSimdWorkItems == 0 ||
3159-
YDimVal.getZExtValue() % NumSimdWorkItems == 0 ||
3160-
ZDimVal.getZExtValue() % NumSimdWorkItems == 0)) {
3158+
if (XDimVal.getZExtValue() % NumSimdWorkItems != 0) {
31613159
S.Diag(A->getLocation(), diag::err_sycl_num_kernel_wrong_reqd_wg_size)
31623160
<< A << AL;
31633161
S.Diag(AL.getLoc(), diag::note_conflicting_attribute);
@@ -3305,14 +3303,12 @@ void Sema::AddSYCLIntelNumSimdWorkItemsAttr(Decl *D,
33053303
}
33063304

33073305
// If the declaration has an [[intel::reqd_work_group_size]] attribute,
3308-
// check to see if can be evenly divided by the num_simd_work_items attr.
3306+
// check to see if the first argument can be evenly divided by the
3307+
// num_simd_work_items attribute.
33093308
if (const auto *DeclAttr = D->getAttr<ReqdWorkGroupSizeAttr>()) {
33103309
Optional<llvm::APSInt> XDimVal = DeclAttr->getXDimVal(Context);
3311-
Optional<llvm::APSInt> YDimVal = DeclAttr->getYDimVal(Context);
3312-
Optional<llvm::APSInt> ZDimVal = DeclAttr->getZDimVal(Context);
33133310

3314-
if (!(*XDimVal % ArgVal == 0 || *YDimVal % ArgVal == 0 ||
3315-
*ZDimVal % ArgVal == 0)) {
3311+
if (*XDimVal % ArgVal != 0) {
33163312
Diag(CI.getLoc(), diag::err_sycl_num_kernel_wrong_reqd_wg_size)
33173313
<< CI << DeclAttr;
33183314
Diag(DeclAttr->getLocation(), diag::note_conflicting_attribute);

clang/test/SemaSYCL/num_simd_work_items_device.cpp

Lines changed: 45 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -40,72 +40,77 @@ struct FuncObj {
4040
};
4141

4242
#ifdef TRIGGER_ERROR
43+
// If the declaration has an [[intel::reqd_work_group_size]] or
44+
// [[cl::reqd_work_group_size]] attribute, tests that check if
45+
// the work group size attribute argument (the first argument)
46+
// can be evenly divided by the num_simd_work_items attribute.
4347
struct TRIFuncObjBad1 {
4448
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
45-
[[intel::reqd_work_group_size(5, 5, 5)]] //expected-note{{conflicting attribute is here}}
49+
[[intel::reqd_work_group_size(5, 3, 3)]] // expected-note{{conflicting attribute is here}}
4650
void
4751
operator()() const {}
4852
};
4953

5054
struct TRIFuncObjBad2 {
51-
[[intel::reqd_work_group_size(5, 5, 5)]] // expected-note{{conflicting attribute is here}}
55+
[[intel::reqd_work_group_size(5, 3, 3)]] // expected-note{{conflicting attribute is here}}
5256
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
5357
void
5458
operator()() const {}
5559
};
5660

5761
struct TRIFuncObjBad3 {
5862
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
59-
[[cl::reqd_work_group_size(5, 5, 5)]] //expected-note{{conflicting attribute is here}}
63+
[[cl::reqd_work_group_size(5, 3, 3)]] // expected-note{{conflicting attribute is here}}
6064
void
6165
operator()() const {}
6266
};
6367

6468
struct TRIFuncObjBad4 {
65-
[[cl::reqd_work_group_size(5, 5, 5)]] // expected-note{{conflicting attribute is here}}
69+
[[cl::reqd_work_group_size(5, 3, 3)]] // expected-note{{conflicting attribute is here}}
6670
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
6771
void
6872
operator()() const {}
6973
};
7074

7175
struct TRIFuncObjBad5 {
72-
[[intel::num_simd_work_items(0)]] // expected-error{{'num_simd_work_items' attribute requires a positive integral compile time constant expression}}
73-
[[intel::reqd_work_group_size(5, 5, 5)]] void
76+
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
77+
[[intel::reqd_work_group_size(5)]] //expected-note{{conflicting attribute is here}}
78+
void
7479
operator()() const {}
7580
};
7681

7782
struct TRIFuncObjBad6 {
83+
[[intel::reqd_work_group_size(5)]] // expected-note{{conflicting attribute is here}}
7884
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
79-
[[intel::reqd_work_group_size(5)]] //expected-note{{conflicting attribute is here}}
8085
void
8186
operator()() const {}
8287
};
8388

8489
struct TRIFuncObjBad7 {
85-
[[intel::reqd_work_group_size(5)]] // expected-note{{conflicting attribute is here}}
86-
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
90+
[[intel::num_simd_work_items(4)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
91+
[[intel::reqd_work_group_size(3, 64)]] // expected-note{{conflicting attribute is here}}
8792
void
8893
operator()() const {}
8994
};
9095

9196
struct TRIFuncObjBad8 {
92-
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
93-
[[intel::reqd_work_group_size(5, 5)]] // expected-note{{conflicting attribute is here}}
97+
[[intel::reqd_work_group_size(3, 64)]] // expected-note{{conflicting attribute is here}}
98+
[[intel::num_simd_work_items(4)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
9499
void
95100
operator()() const {}
96101
};
97102

103+
// Tests for incorrect argument values for Intel FPGA num_simd_work_items and reqd_work_group_size function attributes
98104
struct TRIFuncObjBad9 {
99-
[[intel::reqd_work_group_size(5, 5)]] // expected-note{{conflicting attribute is here}}
100-
[[intel::num_simd_work_items(3)]] // expected-error{{'num_simd_work_items' attribute must evenly divide the work-group size for the 'reqd_work_group_size' attribute}}
101-
void
102-
operator()() const {}
105+
[[intel::reqd_work_group_size(5, 5, 5)]]
106+
[[intel::num_simd_work_items(0)]] // expected-error{{'num_simd_work_items' attribute requires a positive integral compile time constant expression}}
107+
void operator()() const {}
103108
};
104109

105110
struct TRIFuncObjBad10 {
106-
[[intel::reqd_work_group_size(5, 5, 5)]]
107111
[[intel::num_simd_work_items(0)]] // expected-error{{'num_simd_work_items' attribute requires a positive integral compile time constant expression}}
108-
void operator()() const {}
112+
[[intel::reqd_work_group_size(5, 5, 5)]] void
113+
operator()() const {}
109114
};
110115

111116
struct TRIFuncObjBad11 {
@@ -155,28 +160,32 @@ struct TRIFuncObjBad18 {
155160
[[intel::reqd_work_group_size(-1)]] // expected-warning{{implicit conversion changes signedness: 'int' to 'unsigned long long'}}
156161
void operator()() const {}
157162
};
158-
#endif // TRIGGER_ERROR
159163

164+
#endif // TRIGGER_ERROR
165+
// If the declaration has an [[intel::reqd_work_group_size]] or
166+
// [[cl::reqd_work_group_size]] attribute, tests that check if
167+
// the work group size attribute argument (the first argument)
168+
// can be evenly divided by the num_simd_work_items attribute.
160169
struct TRIFuncObjGood1 {
161170
[[intel::num_simd_work_items(4)]]
162-
[[intel::reqd_work_group_size(64, 64, 64)]] void
171+
[[intel::reqd_work_group_size(64, 64, 5)]] void
163172
operator()() const {}
164173
};
165174

166175
struct TRIFuncObjGood2 {
167-
[[intel::reqd_work_group_size(64, 64, 64)]]
176+
[[intel::reqd_work_group_size(64, 64, 5)]]
168177
[[intel::num_simd_work_items(4)]] void
169178
operator()() const {}
170179
};
171180

172181
struct TRIFuncObjGood3 {
173182
[[intel::num_simd_work_items(4)]]
174-
[[cl::reqd_work_group_size(64, 64, 64)]] void
183+
[[cl::reqd_work_group_size(64, 64, 5)]] void
175184
operator()() const {}
176185
};
177186

178187
struct TRIFuncObjGood4 {
179-
[[cl::reqd_work_group_size(64, 64, 64)]]
188+
[[cl::reqd_work_group_size(64, 64, 5)]]
180189
[[intel::num_simd_work_items(4)]] void
181190
operator()() const {}
182191
};
@@ -195,12 +204,12 @@ struct TRIFuncObjGood6 {
195204

196205
struct TRIFuncObjGood7 {
197206
[[intel::num_simd_work_items(4)]]
198-
[[intel::reqd_work_group_size(64, 64)]] void
207+
[[intel::reqd_work_group_size(64, 5)]] void
199208
operator()() const {}
200209
};
201210

202211
struct TRIFuncObjGood8 {
203-
[[intel::reqd_work_group_size(64, 64)]]
212+
[[intel::reqd_work_group_size(64, 5)]]
204213
[[intel::num_simd_work_items(4)]] void
205214
operator()() const {}
206215
};
@@ -242,8 +251,8 @@ int main() {
242251
// CHECK-NEXT: value: Int 64
243252
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
244253
// CHECK-NEXT: ConstantExpr{{.*}}'int'
245-
// CHECK-NEXT: value: Int 64
246-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
254+
// CHECK-NEXT: value: Int 5
255+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
247256
// CHECK: SYCLIntelNumSimdWorkItemsAttr {{.*}}
248257
// CHECK-NEXT: ConstantExpr{{.*}}'int'
249258
// CHECK-NEXT: value: Int 4
@@ -259,8 +268,8 @@ int main() {
259268
// CHECK-NEXT: value: Int 64
260269
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
261270
// CHECK-NEXT: ConstantExpr{{.*}}'int'
262-
// CHECK-NEXT: value: Int 64
263-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
271+
// CHECK-NEXT: value: Int 5
272+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
264273
// CHECK: SYCLIntelNumSimdWorkItemsAttr {{.*}}
265274
// CHECK-NEXT: ConstantExpr{{.*}}'int'
266275
// CHECK-NEXT: value: Int 4
@@ -276,8 +285,8 @@ int main() {
276285
// CHECK-NEXT: value: Int 64
277286
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
278287
// CHECK-NEXT: ConstantExpr{{.*}}'int'
279-
// CHECK-NEXT: value: Int 64
280-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
288+
// CHECK-NEXT: value: Int 5
289+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
281290
// CHECK: SYCLIntelNumSimdWorkItemsAttr {{.*}}
282291
// CHECK-NEXT: ConstantExpr{{.*}}'int'
283292
// CHECK-NEXT: value: Int 4
@@ -293,8 +302,8 @@ int main() {
293302
// CHECK-NEXT: value: Int 64
294303
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
295304
// CHECK-NEXT: ConstantExpr{{.*}}'int'
296-
// CHECK-NEXT: value: Int 64
297-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
305+
// CHECK-NEXT: value: Int 5
306+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
298307
// CHECK: SYCLIntelNumSimdWorkItemsAttr {{.*}}
299308
// CHECK-NEXT: ConstantExpr{{.*}}'int'
300309
// CHECK-NEXT: value: Int 4
@@ -341,8 +350,8 @@ int main() {
341350
// CHECK-NEXT: value: Int 64
342351
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
343352
// CHECK-NEXT: ConstantExpr{{.*}}'int'
344-
// CHECK-NEXT: value: Int 64
345-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
353+
// CHECK-NEXT: value: Int 5
354+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
346355
// CHECK-NEXT: ConstantExpr{{.*}}'int'
347356
// CHECK-NEXT: value: Int 1
348357
// CHECK-NEXT: IntegerLiteral{{.*}}1{{$}}
@@ -358,8 +367,8 @@ int main() {
358367
// CHECK-NEXT: value: Int 64
359368
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
360369
// CHECK-NEXT: ConstantExpr{{.*}}'int'
361-
// CHECK-NEXT: value: Int 64
362-
// CHECK-NEXT: IntegerLiteral{{.*}}64{{$}}
370+
// CHECK-NEXT: value: Int 5
371+
// CHECK-NEXT: IntegerLiteral{{.*}}5{{$}}
363372
// CHECK-NEXT: ConstantExpr{{.*}}'int'
364373
// CHECK-NEXT: value: Int 1
365374
// CHECK-NEXT: IntegerLiteral{{.*}}1{{$}}

0 commit comments

Comments
 (0)