-
Notifications
You must be signed in to change notification settings - Fork 308
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add multi draw indirect feature #2315
base: main
Are you sure you want to change the base?
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you!
Hey! Any updates on this? Can we expect this feature to be available in v1.0? |
Since this is an optional feature I don't think it will be a blocking feature for V1 release. After V1 this will be a living spec, and we'll be doing incremental additions like this one (there won't be a wait for a V1.1 or V2). |
Briefly discussed in meeting: We're going to keep this in polish post-v1, won't be able to spend the time to get it into the spec for V1. Will be soon after. Sorry to folks waiting for this! |
@kainino0x We would like to restart this discussion based on your comment above. We're happy to assist in any investigations required to move this forward. |
Let me propose this for Milestone 1 and add it to the agenda. Unfortunately we don't have a meeting this week, but hopefully next week (in the Pacific-timed meeting). |
Sounds good. |
Draws primitives using an array of parameters read from a {{GPUBuffer}}. | ||
See [[#rendering-operations]] for the detailed specification. | ||
|
||
This method is defined if and only if the {{GPUFeatureName/"multi-draw-indirect"}} [=feature=] is enabled. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is the check I was missing above.
Just an editorial thing but we'll need to move this to a content-timeline check that throws "TypeError" if the feature isn't enabled, as WebIDL doesn't let us dynamically decide whether to define something or not.
spec/index.bs
Outdated
optional GPUSize64 drawCountOffset = 0); | ||
undefined multiDrawIndexedIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset, | ||
GPUSize32 maxDrawCount, | ||
optional GPUBuffer drawCountBuffer = null, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit for editors: need to check if these GPUBuffers need to be nullable
If you make revisions on this PR, feel free to not deal with doing a rebase (though you can if you want to). We can deal with it later. |
4b20359
to
a58d222
Compare
@kainino0x I think the feedback is addressed. I was able to do the rebase, but some of the editor notes got stomped. |
@@ -1828,6 +1828,12 @@ A <dfn dfn>supported limits</dfn> object has a value for every limit defined by | |||
<tr class=row-continuation><td colspan=4> | |||
The maximum value for the arguments of | |||
{{GPUComputePassEncoder/dispatchWorkgroups(workgroupCountX, workgroupCountY, workgroupCountZ)}}. | |||
|
|||
<tr><td><dfn>maxMultiDrawIndirectCount</dfn> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A few thoughts here:
- Shouldn't this also apply to the value in the
drawCountBuffer
? - Does this mean that after enabling the feature you still need to request a higher limit or else will be stuck to 1? It's workable but seems a bit weird.
- Seems a bit weird that this could be 1 when the feature is not enabled. In fact it seems weird the limit exists at all when the feature isn't enabled...I don't think there precedent for feature related limits though.
- @kvark had suggested in a previous comment to " lift the limit entirely...I.e. it becomes limited in the same way as maximum index count is limited." It's not clear to me how "maximum index count is limited", other than it's tied to the max buffer size. Maybe the feature should only be available when the implementation max count is >=
maxStorageBufferBindingSize
and then this limit goes away? Not sure how reasonable that is.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't this also apply to the value in the drawCountBuffer?
Realized this is already covered transitively since drawCountBuffer is already limited by maxDrawCount. Nm.
|
||
undefined multiDrawIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset, | ||
GPUSize32 maxDrawCount, | ||
optional GPUBuffer drawCountBuffer = null, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
from @kainino0x: nit for editors: need to check if these GPUBuffers need to be nullable
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
To match feature parity with D3D12 and Vulkan the drawCountBuffer
should be nullable, in which case maxDrawCount
becomes the draw count.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think the question was about optional vs nullable
The <dfn dfn for=>indirect multiDraw parameters</dfn> encoded in the |indirectBuffer| must be zero or more | ||
tightly packed blocks of **four 32-bit unsigned integer values (16 bytes total)**, given in the same | ||
order as the arguments for {{GPURenderCommandsMixin/draw()}}. For example: | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we should call out here that indirect-first-instance
is not required to use firstInstance here, since it is not obvious.
The <dfn dfn for=>indirect multiDrawIndexed parameters</dfn> encoded in the |indirectBuffer| must be zero or more | ||
tightly packed blocks of **five 32-bit unsigned integer values (20 bytes total)**, given in | ||
the same order as the arguments for {{GPURenderCommandsMixin/drawIndexed()}}. For example: | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
same
^ just dropping some editorial notes for when we pick up this PR again |
- |drawCountOffset| + sizeof([=indirect multiDraw count=]) ≤ | ||
|drawCountBuffer|.{{GPUBuffer/[[size]]}}. | ||
- |drawCountOffset| is a multiple of 4. | ||
</div> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When implementing this for D3D12, the driver / validation layer checks if maxDrawCount exceeds the range of the indirect buffer. Specifically it returns E_INVALIDARG
when closing the command list. We should add this to the validation. Something along the lines of: indirectOffset + sizeof(indirectDrawParams) * maxDrawCount should not be out of bounds of indirectBuffer
This PR adds a multi-draw-indirect feature and is meant to replace #1949
It is rebased over the now merged #2022
Fixes #1354