You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
@@ -49,7 +50,7 @@ To know how to generate sync and when its safe to reorder commands, the tg build
49
50
50
51
#### Usage Implications
51
52
52
-
when a task is added, tg will immediately form new access dependencies for all resources assigned to attachments of that task.
53
+
When a task is added, tg will immediately form new access dependencies for all resources assigned to attachments of that task.
53
54
54
55
Example:
55
56
@@ -96,86 +97,51 @@ A Task consists of four parts:
96
97
97
98
Notably, the graph works in two phases: the recording and the execution. The callbacks of tasks are only ever called in the execution of the graph, not the recording.
98
99
99
-
There are two ways to declare a task. You can declare tasks inline, directly inside the add_task function:
> NOTE: There is a third defaulted parameter to inl_attachment, taking in the VIEW_TYPE for the image.
119
-
> When filling this VIEW_TYPE parameter, task graph will create an image view that exactly fits
120
-
> the dimensions of the attachments view slice.
121
-
> When this parameter is defaulted, daxa will fill the image view id with 0.
122
-
> How to access these tg generated image views is shown later.
123
-
124
-
This is convenient for smaller tasks or quick additions that don't necessarily need shaders.
125
-
126
-
The other way to declare tasks (using "task heads") is shown later.
127
-
128
114
### Task Attachments
129
115
130
116
Attachments describe a list of used graph resources that might require synchronization between tasks.
131
117
132
-
> Note: Any resource that is readonly for the execution of the task, like textures, do not need to be mentioned in the attachments.
118
+
> Note: Only make attachments for resources that need sync. Textures that are uploaded and synched once after upload for example should be ignored in the graph.
133
119
134
120
Each attachment consists of:
121
+
- the resources type (image/buffer/acceleration structure)
122
+
- the resources access (stage + read/write/sampled)
123
+
- the resources shader usage (id/index/ptr + image view type)
135
124
136
-
- a `task resource access` (either `TaskBufferAccess` or `TaskImageAccess`),
137
-
- a description of how the resource is meant to be used in a shader,
138
-
- an attachment index
139
-
140
-
For persistent tasks this is obvious, take `DAXA_TH_IMAGE` as an example:
125
+
TaskGraph will use this information to automatically generate sync, reorder tasks and automatically fill push constants with your resources.
TaskGraph will use all this information to generate optimal synchronization and ordering of tasks, based on the attachments and assigned resource views.
145
-
146
-
Inline tasks omit some of these and set them do default values. When listing an inline attachment, one also directly assigns the view to the attachment as well.
127
+
> the automatic push constant/buffer fill is only available via TaskHeads (described later)
147
128
148
129
### TaskInterface
149
130
150
-
The interface provides functions to query information about the graph, attachments and task itself.
151
-
152
-
For example to get the runtime information for a given attachment the interface has the `get` function.
131
+
The resources assigned to each attachment of tasks are not available or even created yet when recording the task. They might also change between graph executions!
153
132
154
-
It takes a resource view or an attachment index directly.
133
+
So the only up to date and correct information about each task resource and attachment is available ONLY when the task callback is executed and ONLY accessible via the task interface.
155
134
156
-
It returns a `TaskAttachmentInfo` (`TaskBufferAttachmentInfo` for buffers and `TaskImageAttachmentInfo` for images), this struct contains all data about the attachment given on construction as well as runtime data used by the graph.
135
+
The interface has functions to query all information on the resources behind the attachments, such as: id, image view, buffer device/host address, image layout, resource inf, task view.
157
136
158
-
This includes:
137
+
Aside from gett9ing attachment information, the interface is used to get:
138
+
* current device
139
+
* current command recorder
140
+
* current buffer suballocator (may be used to allocate small sections of a ring buffer in each task)
141
+
* current task metadata (name,index,queue)
142
+
* current attachment shader blob (described later)
159
143
160
-
- views assigned to attachments
161
-
- runtime daxa resource ids
162
-
- runtime daxa resource view ids (these are created by the graph based on the attachment view type)
163
-
- image layout
164
-
165
-
The get function alone can make the code verbose. The TaskInterface provides many helper functions such as:
166
-
*`id`
167
-
*`view`
168
-
*`info`
169
-
*`device_address`
170
-
171
-
Aside from attachment information the interface also provides:
172
-
173
-
- a command recorder (automatically reused by the graph)
174
-
- a transfer memory allocator (super fast per execution linear allocator for mapped gpu memory)
175
-
- attachment shader data (generated from the list of attachments, can be send to shader)
176
-
- task metadata such as the name and index
177
-
178
-
### TaskHead
144
+
### TaskHead and Attachment Shader Blob
179
145
180
146
When using shader resources like buffers and images, one must transport the image id or buffer pointer to the shader. In traditional apis one would bind buffers and images to an index but in daxa these need to be in a struct that is either stored inside another buffer or directly within a push constant.
181
147
@@ -234,65 +200,14 @@ struct MyTaskHead
234
200
};
235
201
```
236
202
237
-
In c++ this macro declares a namespace containing a few constexpr static variables.
238
-
In the following code i omittied some code as it is hard to read/understand on the spot:
// This push constant is shared in shader and c++!
@@ -301,10 +216,7 @@ struct MyPushStruct
301
216
daxa_u32vec2 size;
302
217
daxa_u32 settings_bitfield;
303
218
// The head field is an aligned byte array in c++ and the attachment struct in shader:
304
-
// Slang:
305
-
MyTaskHead::AttachmentShaderBlob attachments;
306
-
// Glsl:
307
-
DAXA_TH_BLOB(MyTaskHead, attachments);
219
+
DAXA_TH_BLOB(ExampleTaskHead, attachments);
308
220
};
309
221
```
310
222
@@ -342,42 +254,25 @@ Example usage of the above task:
342
254
343
255
```c++
344
256
345
-
daxa::ImageViewId some_img_view = ...;
346
-
daxa::BufferViewId some_buf_view = ...;
347
-
348
-
task_graph.add_task(MyTask{
349
-
.views = MyTask::Views{
350
-
.src_buffer = some_img_view,
351
-
.dst_image = some_img_view,
352
-
},
353
-
.other_stuff = ...,
354
-
});
355
-
```
356
-
357
-
Daxa automatically generates a struct type `MyTask::Views` for syntactic suggar when assigning views. Its a struct with one field for each declared attachment. Each field is of the type `TaskAttachmentViewWrapper<T>` which accept task resource views.
358
-
359
-
### Alternative Use Of TaskHead
360
-
361
-
Task heads can also be directly used in inline tasks without having to declare a struct inheriting the task:
362
-
363
-
```c++
364
-
365
-
daxa::ImageViewId some_img_view = ...;
366
-
daxa::BufferViewId some_buf_view = ...;
367
-
368
-
using MyTask = daxa::InlineTaskWithHead<MyTaskHead::Task>
> Note: Some permutations are missing here. BLAS for example has no \_ID, \_INDEX or \_PTR version. This is intentional, as some resources can not be used in certain ways inside shaders.
0 commit comments