{
struct nvk_device *dev = nvk_queue_device(queue);
- uint32_t push_data[1024 + 512];
+ uint32_t push_data[2048];
struct nv_push push;
nv_push_init(&push, push_data, ARRAY_SIZE(push_data));
struct nv_push *p = &push;
mme_emit(b, p->first_vertex);
mme_emit(b, p->first_instance);
mme_emit(b, p->draw_idx);
+ mme_emit(b, mme_zero() /* view_index */);
mme_mthd(b, NV9097_SET_GLOBAL_BASE_VERTEX_INDEX);
mme_emit(b, p->base_vertex);
if (b->devinfo->cls_eng3d < TURING_A)
nvk_mme_spill(b, DRAW_IDX, draw_idx);
- nvk_mme_build_draw_loop(b, instance_count,
- first_vertex, vertex_count);
+ struct mme_value view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ieq, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ nvk_mme_build_draw_loop(b, instance_count,
+ first_vertex, vertex_count);
+ }
+
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ine, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ struct mme_value view = mme_mov(b, mme_zero());
+ mme_while(b, ine, view, mme_imm(32)) {
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ struct mme_value has_view = mme_bfe(b, view_mask, view, 1);
+ mme_free_reg(b, view_mask);
+ mme_if(b, ine, has_view, mme_zero()) {
+ mme_free_reg(b, has_view);
+
+ /* Set the push constant */
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER_OFFSET);
+ mme_emit(b, mme_imm(nvk_root_descriptor_offset(draw.view_index)));
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER(0));
+ mme_emit(b, view);
+
+ /* Set the layer to the view index */
+ STATIC_ASSERT(DRF_LO(NV9097_SET_RT_LAYER_V) == 0);
+ STATIC_ASSERT(NV9097_SET_RT_LAYER_CONTROL_V_SELECTS_LAYER == 0);
+ mme_mthd(b, NV9097_SET_RT_LAYER);
+ mme_emit(b, view);
+
+ nvk_mme_build_draw_loop(b, instance_count,
+ first_vertex, vertex_count);
+ }
+
+ mme_add_to(b, view, view, mme_imm(1));
+ }
+ mme_free_reg(b, view);
+ }
mme_free_reg(b, instance_count);
mme_free_reg(b, first_vertex);
nvk_mme_draw(struct mme_builder *b)
{
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
nvk_mme_build_draw(b, mme_zero());
}
.split_mode = SPLIT_MODE_NORMAL_BEGIN_NORMAL_END,
});
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 6);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 7);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, vertexCount);
P_INLINE_DATA(p, instanceCount);
P_INLINE_DATA(p, firstVertex);
if (b->devinfo->cls_eng3d < TURING_A)
nvk_mme_spill(b, DRAW_IDX, draw_idx);
- nvk_mme_build_draw_indexed_loop(b, instance_count,
- first_index, index_count);
+ struct mme_value view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ieq, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ nvk_mme_build_draw_indexed_loop(b, instance_count,
+ first_index, index_count);
+ }
+
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ine, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ struct mme_value view = mme_mov(b, mme_zero());
+ mme_while(b, ine, view, mme_imm(32)) {
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ struct mme_value has_view = mme_bfe(b, view_mask, view, 1);
+ mme_free_reg(b, view_mask);
+ mme_if(b, ine, has_view, mme_zero()) {
+ mme_free_reg(b, has_view);
+
+ /* Set the push constant */
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER_OFFSET);
+ mme_emit(b, mme_imm(nvk_root_descriptor_offset(draw.view_index)));
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER(0));
+ mme_emit(b, view);
+
+ /* Set the layer to the view index */
+ STATIC_ASSERT(DRF_LO(NV9097_SET_RT_LAYER_V) == 0);
+ STATIC_ASSERT(NV9097_SET_RT_LAYER_CONTROL_V_SELECTS_LAYER == 0);
+ mme_mthd(b, NV9097_SET_RT_LAYER);
+ mme_emit(b, view);
+
+ nvk_mme_build_draw_indexed_loop(b, instance_count,
+ first_index, index_count);
+ }
+
+ mme_add_to(b, view, view, mme_imm(1));
+ }
+ mme_free_reg(b, view);
+ }
mme_free_reg(b, instance_count);
mme_free_reg(b, first_index);
nvk_mme_draw_indexed(struct mme_builder *b)
{
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
nvk_mme_build_draw_indexed(b, mme_zero());
}
.split_mode = SPLIT_MODE_NORMAL_BEGIN_NORMAL_END,
});
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 7);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 8);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDEXED));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, indexCount);
P_INLINE_DATA(p, instanceCount);
P_INLINE_DATA(p, firstIndex);
nvk_mme_draw_indirect(struct mme_builder *b)
{
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
if (b->devinfo->cls_eng3d >= TURING_A) {
struct mme_value64 draw_addr = mme_load_addr64(b);
});
if (nvk_cmd_buffer_3d_cls(cmd) >= TURING_A) {
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 8);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 9);
P_IMMD(p, NVC597, SET_MME_DATA_FIFO_CONFIG, FIFO_SIZE_SIZE_4KB);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
uint64_t draw_addr = nvk_buffer_address(buffer, offset);
P_INLINE_DATA(p, draw_addr >> 32);
P_INLINE_DATA(p, draw_addr);
while (drawCount) {
const uint32_t count = MIN2(drawCount, max_draws_per_push);
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 4);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 5);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, count);
P_INLINE_DATA(p, (stride - sizeof(VkDrawIndirectCommand)) / 4);
nvk_mme_draw_indexed_indirect(struct mme_builder *b)
{
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
if (b->devinfo->cls_eng3d >= TURING_A) {
struct mme_value64 draw_addr = mme_load_addr64(b);
});
if (nvk_cmd_buffer_3d_cls(cmd) >= TURING_A) {
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 8);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 9);
P_IMMD(p, NVC597, SET_MME_DATA_FIFO_CONFIG, FIFO_SIZE_SIZE_4KB);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDEXED_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
uint64_t draw_addr = nvk_buffer_address(buffer, offset);
P_INLINE_DATA(p, draw_addr >> 32);
P_INLINE_DATA(p, draw_addr);
while (drawCount) {
const uint32_t count = MIN2(drawCount, max_draws_per_push);
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 4);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 5);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDEXED_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, count);
P_INLINE_DATA(p, (stride - sizeof(VkDrawIndexedIndirectCommand)) / 4);
return;
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
struct mme_value64 draw_addr = mme_load_addr64(b);
struct mme_value64 draw_count_addr = mme_load_addr64(b);
.split_mode = SPLIT_MODE_NORMAL_BEGIN_NORMAL_END,
});
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 10);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 11);
P_IMMD(p, NVC597, SET_MME_DATA_FIFO_CONFIG, FIFO_SIZE_SIZE_4KB);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDIRECT_COUNT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
uint64_t draw_addr = nvk_buffer_address(buffer, offset);
P_INLINE_DATA(p, draw_addr >> 32);
P_INLINE_DATA(p, draw_addr);
return;
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
struct mme_value64 draw_addr = mme_load_addr64(b);
struct mme_value64 draw_count_addr = mme_load_addr64(b);
.split_mode = SPLIT_MODE_NORMAL_BEGIN_NORMAL_END,
});
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 10);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 11);
P_IMMD(p, NVC597, SET_MME_DATA_FIFO_CONFIG, FIFO_SIZE_SIZE_4KB);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_DRAW_INDEXED_INDIRECT_COUNT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
uint64_t draw_addr = nvk_buffer_address(buffer, offset);
P_INLINE_DATA(p, draw_addr >> 32);
P_INLINE_DATA(p, draw_addr);
nvk_mme_xfb_draw_indirect(struct mme_builder *b)
{
nvk_mme_load_to_scratch(b, DRAW_BEGIN);
+ nvk_mme_load_to_scratch(b, VIEW_MASK);
struct mme_value instance_count = mme_load(b);
struct mme_value first_instance = mme_load(b);
mme_free_reg(b, first_instance);
- nvk_mme_xfb_draw_indirect_loop(b, instance_count, counter);
+ struct mme_value view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ieq, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ nvk_mme_xfb_draw_indirect_loop(b, instance_count, counter);
+ }
+
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ mme_if(b, ine, view_mask, mme_zero()) {
+ mme_free_reg(b, view_mask);
+
+ struct mme_value view = mme_mov(b, mme_zero());
+ mme_while(b, ine, view, mme_imm(32)) {
+ view_mask = nvk_mme_load_scratch(b, VIEW_MASK);
+ struct mme_value has_view = mme_bfe(b, view_mask, view, 1);
+ mme_free_reg(b, view_mask);
+ mme_if(b, ine, has_view, mme_zero()) {
+ mme_free_reg(b, has_view);
+
+ /* Set the push constant */
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER_OFFSET);
+ mme_emit(b, mme_imm(nvk_root_descriptor_offset(draw.view_index)));
+ mme_mthd(b, NV9097_LOAD_CONSTANT_BUFFER(0));
+ mme_emit(b, view);
+
+ /* Set the layer to the view index */
+ STATIC_ASSERT(DRF_LO(NV9097_SET_RT_LAYER_V) == 0);
+ STATIC_ASSERT(NV9097_SET_RT_LAYER_CONTROL_V_SELECTS_LAYER == 0);
+ mme_mthd(b, NV9097_SET_RT_LAYER);
+ mme_emit(b, view);
+
+ nvk_mme_xfb_draw_indirect_loop(b, instance_count, counter);
+ }
+
+ mme_add_to(b, view, view, mme_imm(1));
+ }
+ }
mme_free_reg(b, instance_count);
mme_free_reg(b, counter);
});
if (nvk_cmd_buffer_3d_cls(cmd) >= TURING_A) {
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 12);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 13);
P_IMMD(p, NV9097, SET_DRAW_AUTO_START, counterOffset);
P_IMMD(p, NV9097, SET_DRAW_AUTO_STRIDE, vertexStride);
P_IMMD(p, NVC597, SET_MME_DATA_FIFO_CONFIG, FIFO_SIZE_SIZE_4KB);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_XFB_DRAW_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, instanceCount);
P_INLINE_DATA(p, firstInstance);
uint64_t counter_addr = nvk_buffer_address(counter_buffer,
P_INLINE_DATA(p, counter_addr >> 32);
P_INLINE_DATA(p, counter_addr);
} else {
- struct nv_push *p = nvk_cmd_buffer_push(cmd, 10);
+ struct nv_push *p = nvk_cmd_buffer_push(cmd, 11);
/* Stall the command streamer */
__push_immd(p, SUBC_NV9097, NV906F_SET_REFERENCE, 0);
P_IMMD(p, NV9097, SET_DRAW_AUTO_START, counterOffset);
P_1INC(p, NV9097, CALL_MME_MACRO(NVK_MME_XFB_DRAW_INDIRECT));
P_INLINE_DATA(p, begin);
+ P_INLINE_DATA(p, cmd->state.gfx.render.view_mask);
P_INLINE_DATA(p, instanceCount);
P_INLINE_DATA(p, firstInstance);
nv_push_update_count(p, 1);