uint8_t patch_vertices;
uint8_t index_size;
unsigned index_offset;
+ unsigned index_buffer_size; //UINT32_MAX for unset
struct pipe_resource *index_buffer;
struct pipe_constant_buffer const_buffer[LVP_SHADER_STAGES][16];
struct lvp_descriptor_set *desc_sets[2][MAX_SETS];
if (state->info.primitive_restart)
state->info.restart_index = util_prim_restart_index_from_size(state->info.index_size);
- draw.count = cmd->u.draw_indexed.index_count;
+ draw.count = MIN2(cmd->u.draw_indexed.index_count, state->index_buffer_size / state->index_size);
draw.index_bias = cmd->u.draw_indexed.vertex_offset;
/* TODO: avoid calculating multiple times if cmdbuf is submitted again */
draw.start = util_clamped_uadd(state->index_offset / state->index_size,
unsigned size = cmd->u.draw_multi_indexed_ext.draw_count * sizeof(struct pipe_draw_start_count_bias);
memcpy(draws, cmd->u.draw_multi_indexed_ext.index_info, size);
+ if (state->index_buffer_size != UINT32_MAX) {
+ for (unsigned i = 0; i < cmd->u.draw_multi_indexed_ext.draw_count; i++)
+ draws[i].count = MIN2(draws[i].count, state->index_buffer_size / state->index_size - draws[i].start);
+ }
/* only the first member is read if index_bias_varies is true */
if (cmd->u.draw_multi_indexed_ext.draw_count &&
state->info.max_index = ~0U;
if (state->info.primitive_restart)
state->info.restart_index = util_prim_restart_index_from_size(state->info.index_size);
- if (state->index_offset) {
+ if (state->index_offset || state->index_buffer_size != UINT32_MAX) {
struct pipe_transfer *xfer;
uint8_t *mem = pipe_buffer_map(state->pctx, state->index_buffer, 0, &xfer);
state->pctx->buffer_unmap(state->pctx, xfer);
index = get_buffer_resource(state->pctx, mem + state->index_offset);
- index->width0 = state->index_buffer->width0 - state->index_offset;
+ index->width0 = MIN2(state->index_buffer->width0 - state->index_offset, state->index_buffer_size);
state->info.index.resource = index;
}
} else
{
struct vk_cmd_bind_index_buffer *ib = &cmd->u.bind_index_buffer;
state->index_size = vk_index_type_to_bytes(ib->index_type);
+ state->index_buffer_size = UINT32_MAX;
+
+ if (ib->buffer) {
+ state->index_offset = ib->offset;
+ state->index_buffer = lvp_buffer_from_handle(ib->buffer)->bo;
+ } else {
+ state->index_offset = 0;
+ state->index_buffer = state->device->zero_buffer;
+ }
+
+ state->ib_dirty = true;
+}
+
+static void handle_index_buffer2(struct vk_cmd_queue_entry *cmd,
+ struct rendering_state *state)
+{
+ struct vk_cmd_bind_index_buffer2_khr *ib = &cmd->u.bind_index_buffer2_khr;
+ state->index_size = vk_index_type_to_bytes(ib->index_type);
+ state->index_buffer_size = ib->size;
if (ib->buffer) {
state->index_offset = ib->offset;
state->info.index_size = state->index_size;
state->info.index.resource = state->index_buffer;
state->info.max_index = ~0U;
- if (state->index_offset) {
+ if (state->index_offset || state->index_buffer_size != UINT32_MAX) {
struct pipe_transfer *xfer;
uint8_t *mem = pipe_buffer_map(state->pctx, state->index_buffer, 0, &xfer);
state->pctx->buffer_unmap(state->pctx, xfer);
index = get_buffer_resource(state->pctx, mem + state->index_offset);
- index->width0 = state->index_buffer->width0 - state->index_offset;
+ index->width0 = MIN2(state->index_buffer->width0 - state->index_offset, state->index_buffer_size);
state->info.index.resource = index;
}
} else
ENQUEUE_CMD(CmdSetStencilReference)
ENQUEUE_CMD(CmdBindDescriptorSets)
ENQUEUE_CMD(CmdBindIndexBuffer)
+ ENQUEUE_CMD(CmdBindIndexBuffer2KHR)
ENQUEUE_CMD(CmdBindVertexBuffers2)
ENQUEUE_CMD(CmdDraw)
ENQUEUE_CMD(CmdDrawMultiEXT)
case VK_CMD_BIND_INDEX_BUFFER:
handle_index_buffer(cmd, state);
break;
+ case VK_CMD_BIND_INDEX_BUFFER2_KHR:
+ handle_index_buffer2(cmd, state);
+ break;
case VK_CMD_BIND_VERTEX_BUFFERS2:
handle_vertex_buffers2(cmd, state);
break;