Skip to content

Commit 5ef6fe1

Browse files
authored
[SPIR-V][Doc] Add SPV_INTEL_loop_dependence_annotations extension (#13918)
1 parent 2d448f3 commit 5ef6fe1

File tree

1 file changed

+274
-0
lines changed

1 file changed

+274
-0
lines changed
Lines changed: 274 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,274 @@
1+
:extension_name: SPV_INTEL_loop_dependence_annotations
2+
:llvm_capability_name: AccessGroupAnnotationINTEL
3+
:sycl_capability_name: DependencyAnnotationINTEL
4+
:instruction_name: OpAccessGroupDeclINTEL
5+
:aggregator_name: OpAccessGroupListINTEL
6+
:decoration_name: AccessGroupINTEL
7+
:mem_op_name: AccessGroupMaskINTEL
8+
:da_loop_control: DependencyAccessesINTEL
9+
:pa_loop_control: ParallelAccessesINTEL
10+
11+
= {extension_name}
12+
13+
== Name Strings
14+
15+
{extension_name}
16+
17+
== Contact
18+
19+
To report problems with this extension, please open a new issue at:
20+
21+
https://github.com/KhronosGroup/SPIRV-Registry
22+
23+
== Contributors
24+
25+
* Adel Ejjeh, Intel
26+
* Joe Garvey, Intel
27+
* Mark P Mendell, Intel
28+
29+
== Notice
30+
31+
Copyright (c) 2024 Intel Corporation. All rights reserved.
32+
33+
== Status
34+
35+
* Working Draft
36+
37+
This is a preview extension specification, intended to provide early access to a feature for review and community feedback. When the feature matures, this specification may be released as a formal extension.
38+
39+
Because the interfaces defined by this specification are not final and are subject to change they are not intended to be used by shipping software products. If you are interested in using this feature in your software product, please let us know!
40+
41+
== Version
42+
43+
[width="40%",cols="25,25"]
44+
|========================================
45+
| Last Modified Date | {docdate}
46+
| Revision | 2
47+
|========================================
48+
49+
== Dependencies
50+
51+
This extension is written against the SPIR-V Specification, Version 1.6 Revision
52+
3.
53+
54+
This extension requires SPIR-V 1.0.
55+
56+
== Overview
57+
58+
This extension adds the ability to specify an access group for memory operations
59+
and function calls, and then use these access groups to identify which memory
60+
operations have no loop-carried dependencies. The extension was added to
61+
incorporate support for the community LLVM metadata: `llvm.access.group` and
62+
`llvm.loop.parallel_accesses`, as well as Intel-specific metadata:
63+
`llvm.loop.no_depends` and `llvm.loop.no_depends_safelen`. The extension tracks
64+
access groups using literals, and introduces a new instruction for aggregating
65+
access groups into a list (*{aggregator_name}*), a decoration
66+
(*{decoration_name}*) and memory operand (*{mem_op_name}*) to assign access
67+
groups to operations, and two loop controls that indicate that operations with
68+
the specified access groups don't have loop-carried data dependencies
69+
(*{da_loop_control}*) and don't have loop-carried data and memory ordering
70+
dependencies (*{pa_loop_control}*). We split the new additions into two
71+
capabilities, one that is sufficient to support community LLVM
72+
(*{llvm_capability_name}*), and one that adds the support for the Intel-specific
73+
LLVM-extensions (*{sycl_capability_name}*).
74+
75+
== Extension Name
76+
77+
To use this extension within a SPIR-V module, the following
78+
*OpExtension* must be present in the module:
79+
80+
[subs="attributes"]
81+
----
82+
OpExtension "{extension_name}"
83+
----
84+
85+
== Modifications to the SPIR-V Specification, Version 1.6
86+
87+
=== Capabilities
88+
89+
Modify Section 3.31, "Capability", adding these rows to the Capability table:
90+
91+
--
92+
[cols="^.^2,16,15",options="header"]
93+
|====
94+
2+^.^| Capability | Implicitly Declares
95+
| 6200 | *{llvm_capability_name}* +
96+
Enables specifying access groups on operations and identifying which operations
97+
don't have loop-carried data and memory-ordering dependences.
98+
|
99+
| 6201 | *{sycl_capability_name}* +
100+
Enables identifying which operations
101+
don't have loop-carried data (only) dependences.
102+
|*{llvm_capability_name}*
103+
|====
104+
--
105+
106+
=== Instructions
107+
108+
Add to Section 3.49.3, "Annotation Instructions":
109+
110+
// [cols="1,2,2",width="100%"]
111+
// |=====
112+
// 2+|*{instruction_name}* +
113+
// +
114+
// This instruction declares an access group. +
115+
116+
// _Result_ is used by *{aggregator_name}*, *{decoration_name}*, and
117+
// *{mem_op_name}*.
118+
119+
// 1+|Capability: +
120+
// *{llvm_capability_name}*
121+
// 1+| 2 | 6450
122+
// | _Result <id>_
123+
// |=====
124+
125+
[cols="1,2,3,3",width="100%"]
126+
|=====
127+
3+|*{aggregator_name}* +
128+
+
129+
This instruction declares an access group list. +
130+
131+
_Result_ is used by *{da_loop_control}* and *{pa_loop_control}*. +
132+
133+
Operands are one or more access groups (literals).
134+
1+|Capability: +
135+
*{llvm_capability_name}*
136+
1+| 3+variable | 6202
137+
| _Result <id>_
138+
| _literal_, _literal_, ... +
139+
_Access Group 1_, _Access Group 2_, ...
140+
|=====
141+
142+
Add to Section 3.49.18, Atomic Instructions:
143+
144+
[cols="1,1,2,2,2,3,2",width="100%"]
145+
|=====
146+
5+|*OpAtomicStoreRetINTEL* +
147+
+
148+
A variant of *OpAtomicStore* that returns a _Result_ to allow decorations. This
149+
is needed to be able to decorate an atomic store with *{decoration_name}*. +
150+
151+
The _Result_ can only be used in decoration instructions and nothing else.
152+
153+
2+|Capability: +
154+
*{llvm_capability_name}*
155+
1+| 6 | 6203
156+
| _Result <id>_
157+
| _<id>_ +
158+
_Pointer_
159+
| _Scope <id>_ +
160+
_Memory_
161+
| _Memory Semantics <id>_ +
162+
_Semantics_
163+
|_<id>_ +
164+
_Value_
165+
|=====
166+
167+
[cols="1,1,2,2,2,3",width="100%"]
168+
|=====
169+
5+|*OpAtomicFlagClearRetINTEL* +
170+
+
171+
A variant of *OpAtomicFlagClear* that returns a _Result_ to allow decorations. This
172+
is needed to be able to decorate an atomic flag clear with *{decoration_name}*. +
173+
174+
The _Result_ can only be used in decoration instructions and nothing else.
175+
176+
1+|Capability: +
177+
*{llvm_capability_name}*
178+
1+| 5 | 6204
179+
| _Result <id>_
180+
| _<id>_ +
181+
_Pointer_
182+
| _Scope <id>_ +
183+
_Memory_
184+
| _Memory Semantics <id>_ +
185+
_Semantics_
186+
|=====
187+
188+
189+
190+
=== Validation Rules
191+
192+
Add a validation rule to section 2.16.1, "Universal Validation Rules":
193+
194+
* The _Result_ of *OpAtomicStoreRetINTEL* and *OpAtomicFlagClearRetINTEL* can only be used
195+
in decoration instructions.
196+
197+
Additionally, we need to verify whether any changes to the existing validation
198+
rules will be necessary to accommodate the modified instructions, and if adding
199+
instructions whose returned ID cannot be used as operands to other instructions
200+
may break any fundamental assumptions in the validator.
201+
202+
=== Decorations
203+
204+
Modify Section 3.20, Decoration, adding these rows to the Decoration table:
205+
206+
--
207+
[cols="^4,20,10,10",options="header",subs="attributes"]
208+
|====
209+
2+^.^| Decoration | Extra Operands | Enabling Capabilities
210+
| 6205 | *{decoration_name}* +
211+
Can only be applied to *OpFunctionCall* and _Atomic_ instructions. Indicates the
212+
list of access groups that the decorated instruction belongs to. Operand is one
213+
or more literals that correspond to the access groups.
214+
| _literal_, _literal_, ... +
215+
_Access Group 1_, _Access Group 2_, ... | *{llvm_capability_name}*
216+
|====
217+
--
218+
219+
220+
221+
=== Memory Operands
222+
223+
Modify Section 3.26, "Memory Operands", adding these rows to the Memory Operand table:
224+
225+
--
226+
[cols="^.^2,16,5",options="header"]
227+
|====
228+
2+^.^| Memory Operands | Enabling Capabilities
229+
| 0x40000 | *{mem_op_name}* +
230+
Followed by a number _N_ that indicates how many access groups this operation
231+
belongs to, and _N_ literals that correspond to the access groups. Indicates
232+
that this memory operation belongs to the specified access group(s).
233+
| *{llvm_capability_name}*
234+
|====
235+
--
236+
237+
=== Loop Control
238+
239+
Modify Section 3.23, "Loop Control", adding these rows to the Loop Control table:
240+
241+
--
242+
[cols="^.^2,16,5",options="header"]
243+
|====
244+
2+^.^| Loop Control | Enabling Capabilities
245+
| 0x4000000 | *{pa_loop_control}* +
246+
Followed by a number _N_ >= 1 that indicates how many operands will follow, and
247+
_N_ _<id>_'s that are the result of *{aggregator_name}*. Indicates that for each
248+
list of access groups pointed to by an _<id>_, all operations with those access
249+
groups do not have any loop-carried data or memory-ordering dependencies carried by this loop.
250+
| *{llvm_capability_name}*
251+
| 0x8000000 | *{da_loop_control}* +
252+
Followed by a number _N_ >= 1 that indicates how many operands will follow, and
253+
_N_ pairs {_<id>_, _S_}. _<id>_ is a list of access groups coming from
254+
*{aggregator_name}*. _S_ is a literal >=0 indicating that the loop-carried
255+
dependence distance between any operations that belong to the specified access
256+
group(s) in _<id>_ is guaranteed to be greater than _S_. This means that there
257+
is no dependence with distance < _S_, but there could be a dependence with
258+
distance >= _S_. _S_=0 means that there are no loop-carried data dependencies
259+
carried by this loop between the operations.
260+
| *{sycl_capability_name}*
261+
|====
262+
--
263+
264+
== Revision History
265+
266+
[cols="5,15,15,70"]
267+
[grid="rows"]
268+
[options="header"]
269+
|========================================
270+
|Rev|Date|Author|Changes
271+
|1|2024-02-28|Adel Ejjeh|*Initial revision*
272+
|2|2024-03-04|Adel Ejjeh|*Make AGs literals, update tokens*
273+
|3|2024-05-14|Adel Ejjeh|*Update instruction names and Validation section*
274+
|========================================

0 commit comments

Comments
 (0)