aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/gallium/drivers/r600/r600_context.c141
-rw-r--r--src/gallium/drivers/r600/r600_context.h29
-rw-r--r--src/gallium/drivers/r600/r600_draw.c104
-rw-r--r--src/gallium/drivers/r600/r600_shader.c34
-rw-r--r--src/gallium/drivers/r600/r600_state.c283
-rw-r--r--src/gallium/drivers/r600/radeon.h52
-rw-r--r--src/gallium/targets/dri-r600/Makefile4
-rw-r--r--src/gallium/winsys/r600/drm/radeon.c11
-rw-r--r--src/gallium/winsys/r600/drm/radeon_ctx.c160
-rw-r--r--src/gallium/winsys/r600/drm/radeon_draw.c92
-rw-r--r--src/gallium/winsys/r600/drm/radeon_priv.h29
-rw-r--r--src/gallium/winsys/r600/drm/radeon_state.c70
12 files changed, 647 insertions, 362 deletions
diff --git a/src/gallium/drivers/r600/r600_context.c b/src/gallium/drivers/r600/r600_context.c
index f7732d89524..ae1780a1d40 100644
--- a/src/gallium/drivers/r600/r600_context.c
+++ b/src/gallium/drivers/r600/r600_context.c
@@ -48,14 +48,18 @@ void r600_flush(struct pipe_context *ctx, unsigned flags,
struct r600_screen *rscreen = rctx->screen;
static int dc = 0;
- if (radeon_ctx_pm4(&rctx->ctx))
+ if (radeon_ctx_pm4(rctx->ctx))
return;
/* FIXME dumping should be removed once shader support instructions
* without throwing bad code
*/
if (!dc)
- radeon_ctx_dump_bof(&rctx->ctx, "gallium.bof");
- radeon_ctx_submit(&rctx->ctx);
+ radeon_ctx_dump_bof(rctx->ctx, "gallium.bof");
+#if 1
+ radeon_ctx_submit(rctx->ctx);
+#endif
+ rctx->ctx = radeon_ctx_decref(rctx->ctx);
+ rctx->ctx = radeon_ctx(rscreen->rw);
dc++;
}
@@ -216,8 +220,9 @@ static void r600_init_config(struct r600_context *rctx)
printf("num_gs_stack_entries : %d\n", num_gs_stack_entries);
printf("num_es_stack_entries : %d\n", num_es_stack_entries);
- radeon_state_init(&rctx->config, rctx->rw, R600_CONFIG_TYPE, R600_CONFIG);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] = 0x00000000;
+ rctx->hw_states.config = radeon_state(rctx->rw, R600_CONFIG_TYPE, R600_CONFIG);
+
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] = 0x00000000;
switch (family) {
case CHIP_RV610:
case CHIP_RV620:
@@ -226,75 +231,75 @@ static void r600_init_config(struct r600_context *rctx)
case CHIP_RV710:
break;
default:
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_VC_ENABLE(1);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_VC_ENABLE(1);
break;
}
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_DX9_CONSTS(1);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_ALU_INST_PREFER_VECTOR(1);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_PS_PRIO(ps_prio);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_VS_PRIO(vs_prio);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_GS_PRIO(gs_prio);
- rctx->config.states[R600_CONFIG__SQ_CONFIG] |= S_008C00_ES_PRIO(es_prio);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_DX9_CONSTS(1);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_ALU_INST_PREFER_VECTOR(1);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_PS_PRIO(ps_prio);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_VS_PRIO(vs_prio);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_GS_PRIO(gs_prio);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_CONFIG] |= S_008C00_ES_PRIO(es_prio);
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] = 0;
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_PS_GPRS(num_ps_gprs);
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_VS_GPRS(num_vs_gprs);
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_CLAUSE_TEMP_GPRS(num_temp_gprs);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] = 0;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_PS_GPRS(num_ps_gprs);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_VS_GPRS(num_vs_gprs);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_1] |= S_008C04_NUM_CLAUSE_TEMP_GPRS(num_temp_gprs);
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] = 0;
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] |= S_008C08_NUM_GS_GPRS(num_gs_gprs);
- rctx->config.states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] |= S_008C08_NUM_GS_GPRS(num_es_gprs);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] = 0;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] |= S_008C08_NUM_GS_GPRS(num_gs_gprs);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GPR_RESOURCE_MGMT_2] |= S_008C08_NUM_GS_GPRS(num_es_gprs);
- rctx->config.states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] = 0;
- rctx->config.states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_PS_THREADS(num_ps_threads);
- rctx->config.states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_VS_THREADS(num_vs_threads);
- rctx->config.states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_GS_THREADS(num_gs_threads);
- rctx->config.states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_ES_THREADS(num_es_threads);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] = 0;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_PS_THREADS(num_ps_threads);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_VS_THREADS(num_vs_threads);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_GS_THREADS(num_gs_threads);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_THREAD_RESOURCE_MGMT] |= S_008C0C_NUM_ES_THREADS(num_es_threads);
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] = 0;
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] |= S_008C10_NUM_PS_STACK_ENTRIES(num_ps_stack_entries);
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] |= S_008C10_NUM_VS_STACK_ENTRIES(num_vs_stack_entries);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] = 0;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] |= S_008C10_NUM_PS_STACK_ENTRIES(num_ps_stack_entries);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_1] |= S_008C10_NUM_VS_STACK_ENTRIES(num_vs_stack_entries);
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] = 0;
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] |= S_008C14_NUM_GS_STACK_ENTRIES(num_gs_stack_entries);
- rctx->config.states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] |= S_008C14_NUM_ES_STACK_ENTRIES(num_es_stack_entries);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] = 0;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] |= S_008C14_NUM_GS_STACK_ENTRIES(num_gs_stack_entries);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_STACK_RESOURCE_MGMT_2] |= S_008C14_NUM_ES_STACK_ENTRIES(num_es_stack_entries);
- rctx->config.states[R600_CONFIG__SQ_DYN_GPR_CNTL_PS_FLUSH_REQ] = 0x00004000;
- rctx->config.states[R600_CONFIG__TA_CNTL_AUX] = 0x07000002;
- rctx->config.states[R600_CONFIG__VC_ENHANCE] = 0x00000000;
- rctx->config.states[R600_CONFIG__DB_DEBUG] = 0x00000000;
- rctx->config.states[R600_CONFIG__DB_WATERMARKS] = 0x00420204;
- rctx->config.states[R600_CONFIG__SX_MISC] = 0x00000000;
- rctx->config.states[R600_CONFIG__SPI_THREAD_GROUPING] = 0x00000001;
- rctx->config.states[R600_CONFIG__CB_SHADER_CONTROL] = 0x00000003;
- rctx->config.states[R600_CONFIG__SQ_ESGS_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_GSVS_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_ESTMP_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_GSTMP_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_VSTMP_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_PSTMP_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_FBUF_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_REDUC_RING_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__SQ_GS_VERT_ITEMSIZE] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_OUTPUT_PATH_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_HOS_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_HOS_MAX_TESS_LEVEL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_HOS_MIN_TESS_LEVEL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_HOS_REUSE_DEPTH] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_PRIM_TYPE] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_FIRST_DECR] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_DECR] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_VECT_0_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_VECT_1_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_VECT_0_FMT_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GROUP_VECT_1_FMT_CNTL] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_GS_MODE] = 0x00000000;
- rctx->config.states[R600_CONFIG__PA_SC_MODE_CNTL] = 0x00514000;
- rctx->config.states[R600_CONFIG__VGT_STRMOUT_EN] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_REUSE_OFF] = 0x00000001;
- rctx->config.states[R600_CONFIG__VGT_VTX_CNT_EN] = 0x00000000;
- rctx->config.states[R600_CONFIG__VGT_STRMOUT_BUFFER_EN] = 0x00000000;
- radeon_state_pm4(&rctx->config);
+ rctx->hw_states.config->states[R600_CONFIG__SQ_DYN_GPR_CNTL_PS_FLUSH_REQ] = 0x00004000;
+ rctx->hw_states.config->states[R600_CONFIG__TA_CNTL_AUX] = 0x07000002;
+ rctx->hw_states.config->states[R600_CONFIG__VC_ENHANCE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__DB_DEBUG] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__DB_WATERMARKS] = 0x00420204;
+ rctx->hw_states.config->states[R600_CONFIG__SX_MISC] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SPI_THREAD_GROUPING] = 0x00000001;
+ rctx->hw_states.config->states[R600_CONFIG__CB_SHADER_CONTROL] = 0x00000003;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_ESGS_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GSVS_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_ESTMP_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GSTMP_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_VSTMP_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_PSTMP_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_FBUF_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_REDUC_RING_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__SQ_GS_VERT_ITEMSIZE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_OUTPUT_PATH_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_HOS_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_HOS_MAX_TESS_LEVEL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_HOS_MIN_TESS_LEVEL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_HOS_REUSE_DEPTH] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_PRIM_TYPE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_FIRST_DECR] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_DECR] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_VECT_0_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_VECT_1_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_VECT_0_FMT_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GROUP_VECT_1_FMT_CNTL] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_GS_MODE] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__PA_SC_MODE_CNTL] = 0x00514000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_STRMOUT_EN] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_REUSE_OFF] = 0x00000001;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_VTX_CNT_EN] = 0x00000000;
+ rctx->hw_states.config->states[R600_CONFIG__VGT_STRMOUT_BUFFER_EN] = 0x00000000;
+ radeon_state_pm4(rctx->hw_states.config);
}
struct pipe_context *r600_create_context(struct pipe_screen *screen, void *priv)
@@ -328,7 +333,7 @@ struct pipe_context *r600_create_context(struct pipe_screen *screen, void *priv)
r600_init_config(rctx);
- radeon_ctx_init(&rctx->ctx, rscreen->rw);
- radeon_draw_init(&rctx->draw, rscreen->rw);
+ rctx->ctx = radeon_ctx(rscreen->rw);
+ rctx->draw = radeon_draw(rscreen->rw);
return &rctx->context;
}
diff --git a/src/gallium/drivers/r600/r600_context.h b/src/gallium/drivers/r600/r600_context.h
index c83949de425..431f8951b2a 100644
--- a/src/gallium/drivers/r600/r600_context.h
+++ b/src/gallium/drivers/r600/r600_context.h
@@ -76,7 +76,7 @@ struct r600_context_state {
union pipe_states state;
unsigned refcount;
unsigned type;
- struct radeon_state rstate;
+ struct radeon_state *rstate;
struct r600_shader shader;
struct radeon_bo *bo;
};
@@ -89,28 +89,28 @@ struct r600_vertex_element
};
struct r600_context_hw_states {
- struct radeon_state rasterizer;
- struct radeon_state scissor;
- struct radeon_state dsa;
- struct radeon_state blend;
- struct radeon_state viewport;
- struct radeon_state cb[7];
- struct radeon_state config;
- struct radeon_state cb_cntl;
- struct radeon_state db;
+ struct radeon_state *rasterizer;
+ struct radeon_state *scissor;
+ struct radeon_state *dsa;
+ struct radeon_state *blend;
+ struct radeon_state *viewport;
+ struct radeon_state *cb[7];
+ struct radeon_state *config;
+ struct radeon_state *cb_cntl;
+ struct radeon_state *db;
unsigned ps_nresource;
unsigned ps_nsampler;
- struct radeon_state ps_resource[160];
- struct radeon_state ps_sampler[16];
+ struct radeon_state *ps_resource[160];
+ struct radeon_state *ps_sampler[16];
};
struct r600_context {
struct pipe_context context;
struct r600_screen *screen;
struct radeon *rw;
- struct radeon_ctx ctx;
+ struct radeon_ctx *ctx;
struct blitter_context *blitter;
- struct radeon_draw draw;
+ struct radeon_draw *draw;
/* hw states */
struct r600_context_hw_states hw_states;
/* pipe states */
@@ -120,7 +120,6 @@ struct r600_context {
unsigned ps_nsampler_view;
unsigned vs_nsampler_view;
unsigned nvertex_buffer;
- struct radeon_state config;
struct r600_context_state *rasterizer;
struct r600_context_state *poly_stipple;
struct r600_context_state *scissor;
diff --git a/src/gallium/drivers/r600/r600_draw.c b/src/gallium/drivers/r600/r600_draw.c
index 3a54cee2d95..2420b763188 100644
--- a/src/gallium/drivers/r600/r600_draw.c
+++ b/src/gallium/drivers/r600/r600_draw.c
@@ -38,8 +38,8 @@
struct r600_draw {
struct pipe_context *ctx;
- struct radeon_state draw;
- struct radeon_state vgt;
+ struct radeon_state *draw;
+ struct radeon_state *vgt;
unsigned mode;
unsigned start;
unsigned count;
@@ -51,7 +51,7 @@ static int r600_draw_common(struct r600_draw *draw)
{
struct r600_context *rctx = r600_context(draw->ctx);
struct r600_screen *rscreen = rctx->screen;
- struct radeon_state vs_resource;
+ struct radeon_state *vs_resource;
struct r600_resource *rbuffer;
unsigned i, j, offset, format, prim;
u32 vgt_dma_index_type, vgt_draw_initiator;
@@ -88,10 +88,10 @@ static int r600_draw_common(struct r600_draw *draw)
r = r600_pipe_shader_update(draw->ctx, rctx->ps_shader);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->vs_shader->rstate);
+ r = radeon_draw_set(rctx->draw, rctx->vs_shader->rstate);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->ps_shader->rstate);
+ r = radeon_draw_set(rctx->draw, rctx->ps_shader->rstate);
if (r)
return r;
@@ -101,68 +101,68 @@ static int r600_draw_common(struct r600_draw *draw)
rbuffer = (struct r600_resource*)vertex_buffer->buffer;
offset = rctx->vertex_elements->elements[i].src_offset + vertex_buffer->buffer_offset;
format = r600_translate_colorformat(rctx->vertex_elements->elements[i].src_format);
- r = radeon_state_init(&vs_resource, rscreen->rw, R600_VS_RESOURCE_TYPE, R600_VS_RESOURCE + i);
- if (r)
- return r;
- vs_resource.bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
- vs_resource.nbo = 1;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD0] = offset;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD1] = rbuffer->bo->size - offset;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD2] = S_038008_STRIDE(vertex_buffer->stride) |
+ vs_resource = radeon_state(rscreen->rw, R600_VS_RESOURCE_TYPE, R600_VS_RESOURCE + i);
+ if (vs_resource == NULL)
+ return -ENOMEM;
+ vs_resource->bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
+ vs_resource->nbo = 1;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD0] = offset;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD1] = rbuffer->bo->size - offset;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD2] = S_038008_STRIDE(vertex_buffer->stride) |
S_038008_DATA_FORMAT(format);
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD3] = 0x00000000;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD4] = 0x00000000;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD5] = 0x00000000;
- vs_resource.states[R600_PS_RESOURCE__RESOURCE0_WORD6] = 0xC0000000;
- vs_resource.placement[0] = RADEON_GEM_DOMAIN_GTT;
- vs_resource.placement[1] = RADEON_GEM_DOMAIN_GTT;
- radeon_state_pm4(&vs_resource);
- r = radeon_draw_set(&rctx->draw, &vs_resource);
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD3] = 0x00000000;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD4] = 0x00000000;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD5] = 0x00000000;
+ vs_resource->states[R600_PS_RESOURCE__RESOURCE0_WORD6] = 0xC0000000;
+ vs_resource->placement[0] = RADEON_GEM_DOMAIN_GTT;
+ vs_resource->placement[1] = RADEON_GEM_DOMAIN_GTT;
+ r = radeon_draw_set_new(rctx->draw, vs_resource);
if (r)
return r;
}
/* FIXME start need to change winsys */
- r = radeon_state_init(&draw->draw, rscreen->rw, R600_DRAW_TYPE, R600_DRAW);
- if (r)
- return r;
- draw->draw.states[R600_DRAW__VGT_NUM_INDICES] = draw->count;
- draw->draw.states[R600_DRAW__VGT_DRAW_INITIATOR] = vgt_draw_initiator;
+ draw->draw = radeon_state(rscreen->rw, R600_DRAW_TYPE, R600_DRAW);
+ if (draw->draw == NULL)
+ return -ENOMEM;
+ draw->draw->states[R600_DRAW__VGT_NUM_INDICES] = draw->count;
+ draw->draw->states[R600_DRAW__VGT_DRAW_INITIATOR] = vgt_draw_initiator;
if (draw->index_buffer) {
- rbuffer = (struct r600_resource*)draw->index_buffer;
- draw->draw.bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
- draw->draw.placement[0] = RADEON_GEM_DOMAIN_GTT;
- draw->draw.placement[1] = RADEON_GEM_DOMAIN_GTT;
- draw->draw.nbo = 1;
+ rbuffer = (struct r600_buffer*)draw->index_buffer;
+ draw->draw->bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
+ draw->draw->placement[0] = RADEON_GEM_DOMAIN_GTT;
+ draw->draw->placement[1] = RADEON_GEM_DOMAIN_GTT;
+ draw->draw->nbo = 1;
}
- radeon_state_pm4(&draw->draw);
- r = radeon_draw_set(&rctx->draw, &draw->draw);
+ r = radeon_draw_set_new(rctx->draw, draw->draw);
if (r)
return r;
- r = radeon_state_init(&draw->vgt, rscreen->rw, R600_VGT_TYPE, R600_VGT);
- if (r)
- return r;
- draw->vgt.states[R600_VGT__VGT_PRIMITIVE_TYPE] = prim;
- draw->vgt.states[R600_VGT__VGT_MAX_VTX_INDX] = 0x00FFFFFF;
- draw->vgt.states[R600_VGT__VGT_MIN_VTX_INDX] = 0x00000000;
- draw->vgt.states[R600_VGT__VGT_INDX_OFFSET] = draw->start;
- draw->vgt.states[R600_VGT__VGT_MULTI_PRIM_IB_RESET_INDX] = 0x00000000;
- draw->vgt.states[R600_VGT__VGT_DMA_INDEX_TYPE] = vgt_dma_index_type;
- draw->vgt.states[R600_VGT__VGT_PRIMITIVEID_EN] = 0x00000000;
- draw->vgt.states[R600_VGT__VGT_DMA_NUM_INSTANCES] = 0x00000001;
- draw->vgt.states[R600_VGT__VGT_MULTI_PRIM_IB_RESET_EN] = 0x00000000;
- draw->vgt.states[R600_VGT__VGT_INSTANCE_STEP_RATE_0] = 0x00000000;
- draw->vgt.states[R600_VGT__VGT_INSTANCE_STEP_RATE_1] = 0x00000000;
- radeon_state_pm4(&draw->vgt);
- r = radeon_draw_set(&rctx->draw, &draw->vgt);
+ draw->vgt = radeon_state(rscreen->rw, R600_VGT_TYPE, R600_VGT);
+ if (draw->vgt == NULL)
+ return -ENOMEM;
+ draw->vgt->states[R600_VGT__VGT_PRIMITIVE_TYPE] = prim;
+ draw->vgt->states[R600_VGT__VGT_MAX_VTX_INDX] = 0x00FFFFFF;
+ draw->vgt->states[R600_VGT__VGT_MIN_VTX_INDX] = 0x00000000;
+ draw->vgt->states[R600_VGT__VGT_INDX_OFFSET] = draw->start;
+ draw->vgt->states[R600_VGT__VGT_MULTI_PRIM_IB_RESET_INDX] = 0x00000000;
+ draw->vgt->states[R600_VGT__VGT_DMA_INDEX_TYPE] = vgt_dma_index_type;
+ draw->vgt->states[R600_VGT__VGT_PRIMITIVEID_EN] = 0x00000000;
+ draw->vgt->states[R600_VGT__VGT_DMA_NUM_INSTANCES] = 0x00000001;
+ draw->vgt->states[R600_VGT__VGT_MULTI_PRIM_IB_RESET_EN] = 0x00000000;
+ draw->vgt->states[R600_VGT__VGT_INSTANCE_STEP_RATE_0] = 0x00000000;
+ draw->vgt->states[R600_VGT__VGT_INSTANCE_STEP_RATE_1] = 0x00000000;
+ r = radeon_draw_set_new(rctx->draw, draw->vgt);
if (r)
return r;
/* FIXME */
- r = radeon_ctx_set_draw(&rctx->ctx, &rctx->draw);
+ r = radeon_ctx_set_draw_new(rctx->ctx, rctx->draw);
if (r == -EBUSY) {
r600_flush(draw->ctx, 0, NULL);
- r = radeon_ctx_set_draw(&rctx->ctx, &rctx->draw);
+ r = radeon_ctx_set_draw_new(rctx->ctx, rctx->draw);
}
- return r;
+ if (r)
+ return r;
+ rctx->draw = radeon_draw_duplicate(rctx->draw);
+ return 0;
}
void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
diff --git a/src/gallium/drivers/r600/r600_shader.c b/src/gallium/drivers/r600/r600_shader.c
index d925dcbe4bb..dc8d4cb3151 100644
--- a/src/gallium/drivers/r600/r600_shader.c
+++ b/src/gallium/drivers/r600/r600_shader.c
@@ -130,12 +130,11 @@ static int r600_pipe_shader_vs(struct pipe_context *ctx, struct r600_context_sta
struct r600_shader *rshader = &rpshader->shader;
struct radeon_state *state;
unsigned i, tmp;
- int r;
- r = radeon_state_init(&rpshader->rstate, rscreen->rw, R600_VS_SHADER_TYPE, R600_VS_SHADER);
- if (r)
- return r;
- state = &rpshader->rstate;
+ rpshader->rstate = radeon_state_decref(rpshader->rstate);
+ state = radeon_state(rscreen->rw, R600_VS_SHADER_TYPE, R600_VS_SHADER);
+ if (state == NULL)
+ return -ENOMEM;
for (i = 0; i < 10; i++) {
state->states[R600_VS_SHADER__SPI_VS_OUT_ID_0 + i] = 0;
}
@@ -146,10 +145,11 @@ static int r600_pipe_shader_vs(struct pipe_context *ctx, struct r600_context_sta
}
state->states[R600_VS_SHADER__SPI_VS_OUT_CONFIG] = S_0286C4_VS_EXPORT_COUNT(rshader->noutput - 2);
state->states[R600_VS_SHADER__SQ_PGM_RESOURCES_VS] = S_028868_NUM_GPRS(rshader->bc.ngpr);
- rpshader->rstate.bo[0] = radeon_bo_incref(rscreen->rw, rpshader->bo);
- rpshader->rstate.bo[1] = radeon_bo_incref(rscreen->rw, rpshader->bo);
- rpshader->rstate.nbo = 2;
- rpshader->rstate.placement[0] = RADEON_GEM_DOMAIN_GTT;
+ rpshader->rstate = state;
+ rpshader->rstate->bo[0] = radeon_bo_incref(rscreen->rw, rpshader->bo);
+ rpshader->rstate->bo[1] = radeon_bo_incref(rscreen->rw, rpshader->bo);
+ rpshader->rstate->nbo = 2;
+ rpshader->rstate->placement[0] = RADEON_GEM_DOMAIN_GTT;
return radeon_state_pm4(state);
}
@@ -159,12 +159,11 @@ static int r600_pipe_shader_ps(struct pipe_context *ctx, struct r600_context_sta
struct r600_shader *rshader = &rpshader->shader;
struct radeon_state *state;
unsigned i, tmp, exports_ps, num_cout;
- int r;
- r = radeon_state_init(&rpshader->rstate, rscreen->rw, R600_PS_SHADER_TYPE, R600_PS_SHADER);
- if (r)
- return r;
- state = &rpshader->rstate;
+ rpshader->rstate = radeon_state_decref(rpshader->rstate);
+ state = radeon_state(rscreen->rw, R600_PS_SHADER_TYPE, R600_PS_SHADER);
+ if (state == NULL)
+ return -ENOMEM;
for (i = 0; i < rshader->ninput; i++) {
tmp = S_028644_SEMANTIC(i);
tmp |= S_028644_SEL_CENTROID(1);
@@ -190,9 +189,10 @@ static int r600_pipe_shader_ps(struct pipe_context *ctx, struct r600_context_sta
state->states[R600_PS_SHADER__SPI_PS_IN_CONTROL_1] = 0x00000000;
state->states[R600_PS_SHADER__SQ_PGM_RESOURCES_PS] = S_028868_NUM_GPRS(rshader->bc.ngpr);
state->states[R600_PS_SHADER__SQ_PGM_EXPORTS_PS] = exports_ps;
- rpshader->rstate.bo[0] = radeon_bo_incref(rscreen->rw, rpshader->bo);
- rpshader->rstate.nbo = 1;
- rpshader->rstate.placement[0] = RADEON_GEM_DOMAIN_GTT;
+ rpshader->rstate = state;
+ rpshader->rstate->bo[0] = radeon_bo_incref(rscreen->rw, rpshader->bo);
+ rpshader->rstate->nbo = 1;
+ rpshader->rstate->placement[0] = RADEON_GEM_DOMAIN_GTT;
return radeon_state_pm4(state);
}
diff --git a/src/gallium/drivers/r600/r600_state.c b/src/gallium/drivers/r600/r600_state.c
index c5e74d1efcb..e8871cd7481 100644
--- a/src/gallium/drivers/r600/r600_state.c
+++ b/src/gallium/drivers/r600/r600_state.c
@@ -277,10 +277,9 @@ static void r600_set_constant_buffer(struct pipe_context *ctx,
struct r600_screen *rscreen = r600_screen(ctx->screen);
struct r600_context *rctx = r600_context(ctx);
unsigned nconstant = 0, i, type, id;
- struct radeon_state rstate;
+ struct radeon_state *rstate;
struct pipe_transfer *transfer;
u32 *ptr;
- int r;
switch (shader) {
case PIPE_SHADER_VERTEX:
@@ -301,16 +300,16 @@ static void r600_set_constant_buffer(struct pipe_context *ctx,
if (ptr == NULL)
return;
for (i = 0; i < nconstant; i++) {
- r = radeon_state_init(&rstate, rscreen->rw, type, id + i);
- if (r)
+ rstate = radeon_state(rscreen->rw, type, id + i);
+ if (rstate == NULL)
return;
- rstate.states[R600_PS_CONSTANT__SQ_ALU_CONSTANT0_0] = ptr[i * 4 + 0];
- rstate.states[R600_PS_CONSTANT__SQ_ALU_CONSTANT1_0] = ptr[i * 4 + 1];
- rstate.states[R600_PS_CONSTANT__SQ_ALU_CONSTANT2_0] = ptr[i * 4 + 2];
- rstate.states[R600_PS_CONSTANT__SQ_ALU_CONSTANT3_0] = ptr[i * 4 + 3];
- if (radeon_state_pm4(&rstate))
+ rstate->states[R600_PS_CONSTANT__SQ_ALU_CONSTANT0_0] = ptr[i * 4 + 0];
+ rstate->states[R600_PS_CONSTANT__SQ_ALU_CONSTANT1_0] = ptr[i * 4 + 1];
+ rstate->states[R600_PS_CONSTANT__SQ_ALU_CONSTANT2_0] = ptr[i * 4 + 2];
+ rstate->states[R600_PS_CONSTANT__SQ_ALU_CONSTANT3_0] = ptr[i * 4 + 3];
+ if (radeon_state_pm4(rstate))
return;
- if (radeon_draw_set(&rctx->draw, &rstate))
+ if (radeon_draw_set_new(rctx->draw, rstate))
return;
}
pipe_buffer_unmap(ctx, buffer, transfer);
@@ -521,6 +520,7 @@ struct r600_context_state *r600_context_state_decref(struct r600_context_state *
R600_ERR("invalid type %d\n", rstate->type);
return NULL;
}
+ radeon_state_decref(rstate->rstate);
FREE(rstate);
return NULL;
}
@@ -603,17 +603,16 @@ struct r600_context_state *r600_context_state(struct r600_context *rctx, unsigne
return rstate;
}
-static int r600_blend(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_blend(struct r600_context *rctx)
{
struct r600_screen *rscreen = rctx->screen;
+ struct radeon_state *rstate;
const struct pipe_blend_state *state = &rctx->blend->state.blend;
int i;
- int r;
-
- r = radeon_state_init(rstate, rscreen->rw, R600_BLEND_TYPE, R600_BLEND);
- if (r)
- return r;
+ rstate = radeon_state(rscreen->rw, R600_BLEND_TYPE, R600_BLEND);
+ if (rstate == NULL)
+ return NULL;
rstate->states[R600_BLEND__CB_BLEND_RED] = fui(rctx->blend_color.color[0]);
rstate->states[R600_BLEND__CB_BLEND_GREEN] = fui(rctx->blend_color.color[1]);
rstate->states[R600_BLEND__CB_BLEND_BLUE] = fui(rctx->blend_color.color[2]);
@@ -657,27 +656,30 @@ static int r600_blend(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_BLEND__CB_BLEND_CONTROL] = bc;
}
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_cb(struct r600_context *rctx, struct radeon_state *rstate, int cb)
+static struct radeon_state *r600_cb(struct r600_context *rctx, int cb)
{
struct r600_screen *rscreen = rctx->screen;
struct r600_resource_texture *rtex;
struct r600_resource *rbuffer;
+ struct radeon_state *rstate;
const struct pipe_framebuffer_state *state = &rctx->framebuffer->state.framebuffer;
unsigned level = state->cbufs[cb]->level;
unsigned pitch, slice;
unsigned color_info;
unsigned format, swap, ntype;
- int r;
const struct util_format_description *desc;
int id = R600_CB0 + cb;
- r = radeon_state_init(rstate, rscreen->rw, R600_CB0_TYPE, id);
- if (r)
- return r;
-
+ rstate = radeon_state(rscreen->rw, R600_CB0_TYPE, id);
+ if (rstate == NULL)
+ return NULL;
rtex = (struct r600_resource_texture*)state->cbufs[cb]->texture;
rbuffer = &rtex->resource;
rstate->bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
@@ -712,25 +714,30 @@ static int r600_cb(struct r600_context *rctx, struct radeon_state *rstate, int c
rstate->states[R600_CB0__CB_COLOR0_FRAG] = 0x00000000;
rstate->states[R600_CB0__CB_COLOR0_TILE] = 0x00000000;
rstate->states[R600_CB0__CB_COLOR0_MASK] = 0x00000000;
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_db(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_db(struct r600_context *rctx)
{
struct r600_screen *rscreen = rctx->screen;
struct r600_resource_texture *rtex;
struct r600_resource *rbuffer;
+ struct radeon_state *rstate;
const struct pipe_framebuffer_state *state = &rctx->framebuffer->state.framebuffer;
unsigned level = state->cbufs[0]->level;
unsigned pitch, slice, format;
- int r;
-
- r = radeon_state_init(rstate, rscreen->rw, R600_DB_TYPE, R600_DB);
- if (r)
- return r;
if (state->zsbuf == NULL)
- return 0;
+ return NULL;
+
+ rstate = radeon_state(rscreen->rw, R600_DB_TYPE, R600_DB);
+ if (rstate == NULL)
+ return NULL;
+
rtex = (struct r600_resource_texture*)state->zsbuf->texture;
rbuffer = &rtex->resource;
rstate->bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo);
@@ -747,22 +754,23 @@ static int r600_db(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_DB__DB_PREFETCH_LIMIT] = (state->zsbuf->height / 8) -1;
rstate->states[R600_DB__DB_DEPTH_SIZE] = S_028000_PITCH_TILE_MAX(pitch) |
S_028000_SLICE_TILE_MAX(slice);
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_rasterizer(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_rasterizer(struct r600_context *rctx)
{
const struct pipe_rasterizer_state *state = &rctx->rasterizer->state.rasterizer;
const struct pipe_framebuffer_state *fb = &rctx->framebuffer->state.framebuffer;
struct r600_screen *rscreen = rctx->screen;
+ struct radeon_state *rstate;
float offset_units = 0, offset_scale = 0;
char depth = 0;
unsigned offset_db_fmt_cntl = 0;
- int r;
- r = radeon_state_init(rstate, rscreen->rw, R600_RASTERIZER_TYPE, R600_RASTERIZER);
- if (r)
- return r;
if (fb->zsbuf) {
offset_units = state->offset_units;
offset_scale = state->offset_scale * 12.0f;
@@ -783,12 +791,15 @@ static int r600_rasterizer(struct r600_context *rctx, struct radeon_state *rstat
break;
default:
R600_ERR("unsupported %d\n", fb->zsbuf->texture->format);
- return -EINVAL;
+ return NULL;
}
}
offset_db_fmt_cntl |= S_028DF8_POLY_OFFSET_NEG_NUM_DB_BITS(depth);
rctx->flat_shade = state->flatshade;
+ rstate = radeon_state(rscreen->rw, R600_RASTERIZER_TYPE, R600_RASTERIZER);
+ if (rstate == NULL)
+ return NULL;
rstate->states[R600_RASTERIZER__SPI_INTERP_CONTROL_0] = 0x00000001;
rstate->states[R600_RASTERIZER__PA_CL_CLIP_CNTL] = 0x00000000;
rstate->states[R600_RASTERIZER__PA_SU_SC_MODE_CNTL] = 0x00080000 |
@@ -816,21 +827,25 @@ static int r600_rasterizer(struct r600_context *rctx, struct radeon_state *rstat
rstate->states[R600_RASTERIZER__PA_SU_POLY_OFFSET_FRONT_OFFSET] = fui(offset_units);
rstate->states[R600_RASTERIZER__PA_SU_POLY_OFFSET_BACK_SCALE] = fui(offset_scale);
rstate->states[R600_RASTERIZER__PA_SU_POLY_OFFSET_BACK_OFFSET] = fui(offset_units);
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_scissor(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_scissor(struct r600_context *rctx)
{
const struct pipe_scissor_state *state = &rctx->scissor->state.scissor;
struct r600_screen *rscreen = rctx->screen;
+ struct radeon_state *rstate;
u32 tl, br;
- int r;
- r = radeon_state_init(rstate, rscreen->rw, R600_SCISSOR_TYPE, R600_SCISSOR);
- if (r)
- return r;
tl = S_028240_TL_X(state->minx) | S_028240_TL_Y(state->miny) | S_028240_WINDOW_OFFSET_DISABLE(1);
br = S_028244_BR_X(state->maxx) | S_028244_BR_Y(state->maxy);
+ rstate = radeon_state(rscreen->rw, R600_SCISSOR_TYPE, R600_SCISSOR);
+ if (rstate == NULL)
+ return NULL;
rstate->states[R600_SCISSOR__PA_SC_SCREEN_SCISSOR_TL] = tl;
rstate->states[R600_SCISSOR__PA_SC_SCREEN_SCISSOR_BR] = br;
rstate->states[R600_SCISSOR__PA_SC_WINDOW_OFFSET] = 0x00000000;
@@ -850,18 +865,22 @@ static int r600_scissor(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_SCISSOR__PA_SC_GENERIC_SCISSOR_BR] = br;
rstate->states[R600_SCISSOR__PA_SC_VPORT_SCISSOR_0_TL] = tl;
rstate->states[R600_SCISSOR__PA_SC_VPORT_SCISSOR_0_BR] = br;
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_viewport(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_viewport(struct r600_context *rctx)
{
const struct pipe_viewport_state *state = &rctx->viewport->state.viewport;
struct r600_screen *rscreen = rctx->screen;
- int r;
+ struct radeon_state *rstate;
- r = radeon_state_init(rstate, rscreen->rw, R600_VIEWPORT_TYPE, R600_VIEWPORT);
- if (r)
- return r;
+ rstate = radeon_state(rscreen->rw, R600_VIEWPORT_TYPE, R600_VIEWPORT);
+ if (rstate == NULL)
+ return NULL;
rstate->states[R600_VIEWPORT__PA_SC_VPORT_ZMIN_0] = 0x00000000;
rstate->states[R600_VIEWPORT__PA_SC_VPORT_ZMAX_0] = 0x3F800000;
rstate->states[R600_VIEWPORT__PA_CL_VPORT_XSCALE_0] = fui(state->scale[0]);
@@ -871,22 +890,27 @@ static int r600_viewport(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_VIEWPORT__PA_CL_VPORT_YOFFSET_0] = fui(state->translate[1]);
rstate->states[R600_VIEWPORT__PA_CL_VPORT_ZOFFSET_0] = fui(state->translate[2]);
rstate->states[R600_VIEWPORT__PA_CL_VTE_CNTL] = 0x0000043F;
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_dsa(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_dsa(struct r600_context *rctx)
{
const struct pipe_depth_stencil_alpha_state *state = &rctx->dsa->state.dsa;
const struct pipe_stencil_ref *stencil_ref = &rctx->stencil_ref->state.stencil_ref;
struct r600_screen *rscreen = rctx->screen;
unsigned db_depth_control, alpha_test_control, alpha_ref, db_shader_control;
unsigned stencil_ref_mask, stencil_ref_mask_bf;
- int r, i;
struct r600_shader *rshader = &rctx->ps_shader->shader;
+ struct radeon_state *rstate;
+ int i;
- r = radeon_state_init(rstate, rscreen->rw, R600_DSA_TYPE, R600_DSA);
- if (r)
- return r;
+ rstate = radeon_state(rscreen->rw, R600_DSA_TYPE, R600_DSA);
+ if (rstate == NULL)
+ return NULL;
db_shader_control = 0x210;
for (i = 0; i < rshader->noutput; i++) {
@@ -898,8 +922,8 @@ static int r600_dsa(struct r600_context *rctx, struct radeon_state *rstate)
db_depth_control = S_028800_Z_ENABLE(state->depth.enabled) |
S_028800_Z_WRITE_ENABLE(state->depth.writemask) |
S_028800_ZFUNC(state->depth.func);
-
/* set stencil enable */
+
if (state->stencil[0].enabled) {
db_depth_control |= S_028800_STENCIL_ENABLE(1);
db_depth_control |= S_028800_STENCILFUNC(r600_translate_ds_func(state->stencil[0].func));
@@ -946,7 +970,11 @@ static int r600_dsa(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_DSA__DB_SRESULTS_COMPARE_STATE1] = 0x00000000;
rstate->states[R600_DSA__DB_PRELOAD_CONTROL] = 0x00000000;
rstate->states[R600_DSA__DB_ALPHA_TO_MASK] = 0x0000AA00;
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
static inline unsigned r600_tex_wrap(unsigned wrap)
@@ -1024,15 +1052,16 @@ static INLINE u32 S_FIXED(float value, u32 frac_bits)
return value * (1 << frac_bits);
}
-static int r600_sampler(struct r600_context *rctx, struct radeon_state *rstate,
- const struct pipe_sampler_state *state, unsigned id)
+static struct radeon_state *r600_sampler(struct r600_context *rctx,
+ const struct pipe_sampler_state *state,
+ unsigned id)
{
struct r600_screen *rscreen = rctx->screen;
- int r;
+ struct radeon_state *rstate;
- r = radeon_state_init(rstate, rscreen->rw, R600_PS_SAMPLER_TYPE, id);
- if (r)
- return r;
+ rstate = radeon_state(rscreen->rw, R600_PS_SAMPLER_TYPE, id);
+ if (rstate == NULL)
+ return NULL;
rstate->states[R600_PS_SAMPLER__SQ_TEX_SAMPLER_WORD0_0] =
S_03C000_CLAMP_X(r600_tex_wrap(state->wrap_s)) |
S_03C000_CLAMP_Y(r600_tex_wrap(state->wrap_t)) |
@@ -1047,7 +1076,11 @@ static int r600_sampler(struct r600_context *rctx, struct radeon_state *rstate,
S_03C004_MAX_LOD(S_FIXED(CLAMP(state->max_lod, 0, 15), 6)) |
S_03C004_LOD_BIAS(S_FIXED(CLAMP(state->lod_bias, -16, 16), 6));
rstate->states[R600_PS_SAMPLER__SQ_TEX_SAMPLER_WORD2_0] = S_03C008_TYPE(1);
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
static inline unsigned r600_tex_swizzle(unsigned swizzle)
@@ -1097,26 +1130,28 @@ static inline unsigned r600_tex_dim(unsigned dim)
}
}
-static int r600_resource(struct r600_context *rctx, struct radeon_state *rstate,
- const struct pipe_sampler_view *view, unsigned id)
+static struct radeon_state *r600_resource(struct r600_context *rctx,
+ const struct pipe_sampler_view *view,
+ unsigned id)
{
struct r600_screen *rscreen = rctx->screen;
const struct util_format_description *desc;
struct r600_resource_texture *tmp;
struct r600_resource *rbuffer;
+ struct radeon_state *rstate;
unsigned format;
- int r;
- r = radeon_state_init(rstate, rscreen->rw, R600_PS_RESOURCE_TYPE, id);
- if (r)
- return r;
format = r600_translate_colorformat(view->texture->format);
if (format == ~0)
- return -EINVAL;
+ return NULL;
desc = util_format_description(view->texture->format);
if (desc == NULL) {
R600_ERR("unknow format %d\n", view->texture->format);
- return -EINVAL;
+ return NULL;
+ }
+ rstate = radeon_state(rscreen->rw, R600_PS_RESOURCE_TYPE, id);
+ if (rstate == NULL) {
+ return NULL;
}
tmp = (struct r600_resource_texture*)view->texture;
rbuffer = &tmp->resource;
@@ -1159,16 +1194,21 @@ static int r600_resource(struct r600_context *rctx, struct radeon_state *rstate,
S_038014_LAST_ARRAY(0);
rstate->states[R600_PS_RESOURCE__RESOURCE0_WORD6] =
S_038018_TYPE(V_038010_SQ_TEX_VTX_VALID_TEXTURE);
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
-static int r600_cb_cntl(struct r600_context *rctx, struct radeon_state *rstate)
+static struct radeon_state *r600_cb_cntl(struct r600_context *rctx)
{
struct r600_screen *rscreen = rctx->screen;
+ struct radeon_state *rstate;
const struct pipe_blend_state *pbs = &rctx->blend->state.blend;
int nr_cbufs = rctx->framebuffer->state.framebuffer.nr_cbufs;
uint32_t color_control, target_mask, shader_mask;
- int i, r;
+ int i;
target_mask = 0;
shader_mask = 0;
@@ -1190,10 +1230,7 @@ static int r600_cb_cntl(struct r600_context *rctx, struct radeon_state *rstate)
target_mask |= (pbs->rt[i].colormask << (4 * i));
}
- r = radeon_state_init(rstate, rscreen->rw, R600_CB_CNTL_TYPE, R600_CB_CNTL);
- if (r)
- return r;
-
+ rstate = radeon_state(rscreen->rw, R600_CB_CNTL_TYPE, R600_CB_CNTL);
rstate->states[R600_CB_CNTL__CB_SHADER_MASK] = shader_mask;
rstate->states[R600_CB_CNTL__CB_TARGET_MASK] = target_mask;
rstate->states[R600_CB_CNTL__CB_COLOR_CONTROL] = color_control;
@@ -1205,7 +1242,11 @@ static int r600_cb_cntl(struct r600_context *rctx, struct radeon_state *rstate)
rstate->states[R600_CB_CNTL__CB_CLRCMP_DST] = 0x000000FF;
rstate->states[R600_CB_CNTL__CB_CLRCMP_MSK] = 0xFFFFFFFF;
rstate->states[R600_CB_CNTL__PA_SC_AA_MASK] = 0xFFFFFFFF;
- return radeon_state_pm4(rstate);
+ if (radeon_state_pm4(rstate)) {
+ radeon_state_decref(rstate);
+ return NULL;
+ }
+ return rstate;
}
int r600_context_hw_states(struct r600_context *rctx)
@@ -1217,77 +1258,97 @@ int r600_context_hw_states(struct r600_context *rctx)
/* free previous TODO determine what need to be updated, what
* doesn't
*/
- memset(&rctx->hw_states, 0, sizeof(struct r600_context_hw_states));
+ //radeon_state_decref(rctx->hw_states.config);
+ rctx->hw_states.cb_cntl = radeon_state_decref(rctx->hw_states.cb_cntl);
+ rctx->hw_states.db = radeon_state_decref(rctx->hw_states.db);
+ rctx->hw_states.rasterizer = radeon_state_decref(rctx->hw_states.rasterizer);
+ rctx->hw_states.scissor = radeon_state_decref(rctx->hw_states.scissor);
+ rctx->hw_states.dsa = radeon_state_decref(rctx->hw_states.dsa);
+ rctx->hw_states.blend = radeon_state_decref(rctx->hw_states.blend);
+ rctx->hw_states.viewport = radeon_state_decref(rctx->hw_states.viewport);
+ for (i = 0; i < 8; i++) {
+ rctx->hw_states.cb[i] = radeon_state_decref(rctx->hw_states.cb[i]);
+ }
+ for (i = 0; i < rctx->hw_states.ps_nresource; i++) {
+ radeon_state_decref(rctx->hw_states.ps_resource[i]);
+ rctx->hw_states.ps_resource[i] = NULL;
+ }
+ rctx->hw_states.ps_nresource = 0;
+ for (i = 0; i < rctx->hw_states.ps_nsampler; i++) {
+ radeon_state_decref(rctx->hw_states.ps_sampler[i]);
+ rctx->hw_states.ps_sampler[i] = NULL;
+ }
+ rctx->hw_states.ps_nsampler = 0;
/* build new states */
- rctx->hw_states.config = rctx->config;
- r600_rasterizer(rctx, &rctx->hw_states.rasterizer);
- r600_scissor(rctx, &rctx->hw_states.scissor);
- r600_dsa(rctx, &rctx->hw_states.dsa);
- r600_blend(rctx, &rctx->hw_states.blend);
- r600_viewport(rctx, &rctx->hw_states.viewport);
- for (i = 0; i < nr_cbufs; i++)
- r600_cb(rctx, &rctx->hw_states.cb[i], i);
- r600_db(rctx, &rctx->hw_states.db);
- r600_cb_cntl(rctx, &rctx->hw_states.cb_cntl);
+ rctx->hw_states.rasterizer = r600_rasterizer(rctx);
+ rctx->hw_states.scissor = r600_scissor(rctx);
+ rctx->hw_states.dsa = r600_dsa(rctx);
+ rctx->hw_states.blend = r600_blend(rctx);
+ rctx->hw_states.viewport = r600_viewport(rctx);
+ for (i = 0; i < nr_cbufs; i++) {
+ rctx->hw_states.cb[i] = r600_cb(rctx, i);
+ }
+ rctx->hw_states.db = r600_db(rctx);
+ rctx->hw_states.cb_cntl = r600_cb_cntl(rctx);
for (i = 0; i < rctx->ps_nsampler; i++) {
if (rctx->ps_sampler[i]) {
- r600_sampler(rctx, &rctx->hw_states.ps_sampler[i],
- &rctx->ps_sampler[i]->state.sampler,
- R600_PS_SAMPLER + i);
+ rctx->hw_states.ps_sampler[i] = r600_sampler(rctx,
+ &rctx->ps_sampler[i]->state.sampler,
+ R600_PS_SAMPLER + i);
}
}
rctx->hw_states.ps_nsampler = rctx->ps_nsampler;
for (i = 0; i < rctx->ps_nsampler_view; i++) {
if (rctx->ps_sampler_view[i]) {
- r600_resource(rctx, &rctx->hw_states.ps_resource[i],
- &rctx->ps_sampler_view[i]->state.sampler_view,
- R600_PS_RESOURCE + i);
+ rctx->hw_states.ps_resource[i] = r600_resource(rctx,
+ &rctx->ps_sampler_view[i]->state.sampler_view,
+ R600_PS_RESOURCE + i);
}
}
rctx->hw_states.ps_nresource = rctx->ps_nsampler_view;
/* bind states */
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.db);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.db);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.rasterizer);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.rasterizer);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.scissor);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.scissor);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.dsa);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.dsa);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.blend);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.blend);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.viewport);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.viewport);
if (r)
return r;
for (i = 0; i < nr_cbufs; i++) {
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.cb[i]);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.cb[i]);
if (r)
return r;
}
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.config);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.config);
if (r)
return r;
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.cb_cntl);
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.cb_cntl);
if (r)
return r;
for (i = 0; i < rctx->hw_states.ps_nresource; i++) {
- if (rctx->hw_states.ps_resource[i].valid) {
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.ps_resource[i]);
+ if (rctx->hw_states.ps_resource[i]) {
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.ps_resource[i]);
if (r)
return r;
}
}
for (i = 0; i < rctx->hw_states.ps_nsampler; i++) {
- if (rctx->hw_states.ps_sampler[i].valid) {
- r = radeon_draw_set(&rctx->draw, &rctx->hw_states.ps_sampler[i]);
+ if (rctx->hw_states.ps_sampler[i]) {
+ r = radeon_draw_set(rctx->draw, rctx->hw_states.ps_sampler[i]);
if (r)
return r;
}
diff --git a/src/gallium/drivers/r600/radeon.h b/src/gallium/drivers/r600/radeon.h
index 709ef8a85ae..3a8405f9b40 100644
--- a/src/gallium/drivers/r600/radeon.h
+++ b/src/gallium/drivers/r600/radeon.h
@@ -103,17 +103,17 @@ int radeon_bo_wait(struct radeon *radeon, struct radeon_bo *bo);
*/
struct radeon_state {
struct radeon *radeon;
- unsigned valid;
+ unsigned refcount;
unsigned type;
unsigned id;
unsigned nstates;
- u32 states[64];
+ u32 *states;
unsigned npm4;
unsigned cpm4;
u32 pm4_crc;
- u32 pm4[128];
+ u32 *pm4;
u32 nimmd;
- u32 immd[64];
+ u32 *immd;
unsigned nbo;
struct radeon_bo *bo[4];
unsigned nreloc;
@@ -123,51 +123,35 @@ struct radeon_state {
unsigned bo_dirty[4];
};
-int radeon_state_init(struct radeon_state *state, struct radeon *radeon, u32 type, u32 id);
+struct radeon_state *radeon_state(struct radeon *radeon, u32 type, u32 id);
+struct radeon_state *radeon_state_incref(struct radeon_state *state);
+struct radeon_state *radeon_state_decref(struct radeon_state *state);
int radeon_state_pm4(struct radeon_state *state);
/*
* draw functions
*/
struct radeon_draw {
+ unsigned refcount;
struct radeon *radeon;
unsigned nstate;
- struct radeon_state state[1273];
+ struct radeon_state **state;
unsigned cpm4;
};
-int radeon_draw_init(struct radeon_draw *draw, struct radeon *radeon);
+struct radeon_draw *radeon_draw(struct radeon *radeon);
+struct radeon_draw *radeon_draw_duplicate(struct radeon_draw *draw);
+struct radeon_draw *radeon_draw_incref(struct radeon_draw *draw);
+struct radeon_draw *radeon_draw_decref(struct radeon_draw *draw);
int radeon_draw_set(struct radeon_draw *draw, struct radeon_state *state);
+int radeon_draw_set_new(struct radeon_draw *draw, struct radeon_state *state);
int radeon_draw_check(struct radeon_draw *draw);
-/*
- * Context
- */
-#pragma pack(1)
-struct radeon_cs_reloc {
- uint32_t handle;
- uint32_t read_domain;
- uint32_t write_domain;
- uint32_t flags;
-};
-#pragma pack()
-
-struct radeon_ctx {
- struct radeon *radeon;
- u32 *pm4;
- u32 cpm4;
- u32 draw_cpm4;
- unsigned id;
- unsigned nreloc;
- struct radeon_cs_reloc reloc[2048];
- unsigned nbo;
- struct radeon_bo *bo[2048];
- unsigned ndraw;
- struct radeon_draw draw[128];
-};
-
-int radeon_ctx_init(struct radeon_ctx *ctx, struct radeon *radeon);
+struct radeon_ctx *radeon_ctx(struct radeon *radeon);
+struct radeon_ctx *radeon_ctx_decref(struct radeon_ctx *ctx);
+struct radeon_ctx *radeon_ctx_incref(struct radeon_ctx *ctx);
int radeon_ctx_set_draw(struct radeon_ctx *ctx, struct radeon_draw *draw);
+int radeon_ctx_set_draw_new(struct radeon_ctx *ctx, struct radeon_draw *draw);
int radeon_ctx_pm4(struct radeon_ctx *ctx);
int radeon_ctx_submit(struct radeon_ctx *ctx);
void radeon_ctx_dump_bof(struct radeon_ctx *ctx, const char *file);
diff --git a/src/gallium/targets/dri-r600/Makefile b/src/gallium/targets/dri-r600/Makefile
index 9c8b4ab2526..932303d194e 100644
--- a/src/gallium/targets/dri-r600/Makefile
+++ b/src/gallium/targets/dri-r600/Makefile
@@ -4,12 +4,12 @@ include $(TOP)/configs/current
LIBNAME = r600_dri.so
PIPE_DRIVERS = \
- $(TOP)/src/gallium/drivers/r600/libr600.a \
$(TOP)/src/gallium/state_trackers/dri/drm/libdridrm.a \
$(TOP)/src/gallium/winsys/r600/drm/libr600winsys.a \
$(TOP)/src/gallium/drivers/softpipe/libsoftpipe.a \
$(TOP)/src/gallium/drivers/trace/libtrace.a \
- $(TOP)/src/gallium/drivers/rbug/librbug.a
+ $(TOP)/src/gallium/drivers/rbug/librbug.a \
+ $(TOP)/src/gallium/drivers/r600/libr600.a
C_SOURCES = \
target.c \
diff --git a/src/gallium/winsys/r600/drm/radeon.c b/src/gallium/winsys/r600/drm/radeon.c
index 24d821d5cf0..7e656698064 100644
--- a/src/gallium/winsys/r600/drm/radeon.c
+++ b/src/gallium/winsys/r600/drm/radeon.c
@@ -43,6 +43,16 @@ static int radeon_get_device(struct radeon *radeon)
return r;
}
+/* symbol missing drove me crazy hack to get symbol exported */
+static void fake(void)
+{
+ struct radeon_ctx *ctx;
+ struct radeon_draw *draw;
+
+ ctx = radeon_ctx(NULL);
+ draw = radeon_draw(NULL);
+}
+
struct radeon *radeon_new(int fd, unsigned device)
{
struct radeon *radeon;
@@ -50,6 +60,7 @@ struct radeon *radeon_new(int fd, unsigned device)
radeon = calloc(1, sizeof(*radeon));
if (radeon == NULL) {
+ fake();
return NULL;
}
radeon->fd = fd;
diff --git a/src/gallium/winsys/r600/drm/radeon_ctx.c b/src/gallium/winsys/r600/drm/radeon_ctx.c
index af270d5d20b..6b0eba0b289 100644
--- a/src/gallium/winsys/r600/drm/radeon_ctx.c
+++ b/src/gallium/winsys/r600/drm/radeon_ctx.c
@@ -32,8 +32,13 @@
int radeon_ctx_set_bo_new(struct radeon_ctx *ctx, struct radeon_bo *bo)
{
- if (ctx->nbo >= 2048)
- return -EBUSY;
+ void *ptr;
+
+ ptr = realloc(ctx->bo, sizeof(struct radeon_bo) * (ctx->nbo + 1));
+ if (ptr == NULL) {
+ return -ENOMEM;
+ }
+ ctx->bo = ptr;
ctx->bo[ctx->nbo] = bo;
ctx->nbo++;
return 0;
@@ -71,26 +76,49 @@ void radeon_ctx_get_placement(struct radeon_ctx *ctx, unsigned reloc, u32 *place
}
}
-static void radeon_ctx_clear(struct radeon_ctx *ctx)
+struct radeon_ctx *radeon_ctx(struct radeon *radeon)
{
- ctx->draw_cpm4 = 0;
- ctx->cpm4 = 0;
- ctx->ndraw = 0;
- ctx->nbo = 0;
- ctx->nreloc = 0;
+ struct radeon_ctx *ctx;
+
+ if (radeon == NULL)
+ return NULL;
+ ctx = calloc(1, sizeof(*ctx));
+ if (ctx == NULL)
+ return NULL;
+ ctx->radeon = radeon_incref(radeon);
+ return ctx;
}
-int radeon_ctx_init(struct radeon_ctx *ctx, struct radeon *radeon)
+struct radeon_ctx *radeon_ctx_incref(struct radeon_ctx *ctx)
{
- memset(ctx, 0, sizeof(struct radeon_ctx));
- ctx->radeon = radeon_incref(radeon);
- radeon_ctx_clear(ctx);
+ ctx->refcount++;
+ return ctx;
+}
+
+struct radeon_ctx *radeon_ctx_decref(struct radeon_ctx *ctx)
+{
+ unsigned i;
+
+ if (ctx == NULL)
+ return NULL;
+ if (--ctx->refcount > 0) {
+ return NULL;
+ }
+
+ for (i = 0; i < ctx->ndraw; i++) {
+ ctx->draw[i] = radeon_draw_decref(ctx->draw[i]);
+ }
+ for (i = 0; i < ctx->nbo; i++) {
+ ctx->bo[i] = radeon_bo_decref(ctx->radeon, ctx->bo[i]);
+ }
+ ctx->radeon = radeon_decref(ctx->radeon);
+ free(ctx->draw);
+ free(ctx->bo);
free(ctx->pm4);
- ctx->cpm4 = 0;
- ctx->pm4 = malloc(64 * 1024);
- if (ctx->pm4 == NULL)
- return -ENOMEM;
- return 0;
+ free(ctx->reloc);
+ memset(ctx, 0, sizeof(*ctx));
+ free(ctx);
+ return NULL;
}
static int radeon_ctx_state_bo(struct radeon_ctx *ctx, struct radeon_state *state)
@@ -115,6 +143,7 @@ static int radeon_ctx_state_bo(struct radeon_ctx *ctx, struct radeon_state *stat
return 0;
}
+
int radeon_ctx_submit(struct radeon_ctx *ctx)
{
struct drm_radeon_cs drmib;
@@ -141,7 +170,6 @@ int radeon_ctx_submit(struct radeon_ctx *ctx)
r = drmCommandWriteRead(ctx->radeon->fd, DRM_RADEON_CS, &drmib,
sizeof(struct drm_radeon_cs));
#endif
- radeon_ctx_clear(ctx);
return r;
}
@@ -149,6 +177,7 @@ static int radeon_ctx_reloc(struct radeon_ctx *ctx, struct radeon_bo *bo,
unsigned id, unsigned *placement)
{
unsigned i;
+ struct radeon_cs_reloc *ptr;
for (i = 0; i < ctx->nreloc; i++) {
if (ctx->reloc[i].handle == bo->handle) {
@@ -156,12 +185,14 @@ static int radeon_ctx_reloc(struct radeon_ctx *ctx, struct radeon_bo *bo,
return 0;
}
}
- if (ctx->nreloc >= 2048)
- return -EINVAL;
- ctx->reloc[ctx->nreloc].handle = bo->handle;
- ctx->reloc[ctx->nreloc].read_domain = placement[0] | placement [1];
- ctx->reloc[ctx->nreloc].write_domain = placement[0] | placement [1];
- ctx->reloc[ctx->nreloc].flags = 0;
+ ptr = realloc(ctx->reloc, sizeof(struct radeon_cs_reloc) * (ctx->nreloc + 1));
+ if (ptr == NULL)
+ return -ENOMEM;
+ ctx->reloc = ptr;
+ ptr[ctx->nreloc].handle = bo->handle;
+ ptr[ctx->nreloc].read_domain = placement[0] | placement [1];
+ ptr[ctx->nreloc].write_domain = placement[0] | placement [1];
+ ptr[ctx->nreloc].flags = 0;
ctx->pm4[id] = ctx->nreloc * sizeof(struct radeon_cs_reloc) / 4;
ctx->nreloc++;
return 0;
@@ -190,13 +221,21 @@ static int radeon_ctx_state_schedule(struct radeon_ctx *ctx, struct radeon_state
return 0;
}
-int radeon_ctx_set_draw(struct radeon_ctx *ctx, struct radeon_draw *draw)
+int radeon_ctx_set_draw_new(struct radeon_ctx *ctx, struct radeon_draw *draw)
{
- unsigned cpm4, i;
+ struct radeon_draw *pdraw = NULL;
+ struct radeon_draw **ndraw;
+ struct radeon_state *nstate, *ostate;
+ unsigned cpm4, i, cstate;
+ void *tmp;
int r = 0;
+ ndraw = realloc(ctx->draw, sizeof(void*) * (ctx->ndraw + 1));
+ if (ndraw == NULL)
+ return -ENOMEM;
+ ctx->draw = ndraw;
for (i = 0; i < draw->nstate; i++) {
- r = radeon_ctx_state_bo(ctx, &draw->state[i]);
+ r = radeon_ctx_state_bo(ctx, draw->state[i]);
if (r)
return r;
}
@@ -208,48 +247,69 @@ int radeon_ctx_set_draw(struct radeon_ctx *ctx, struct radeon_draw *draw)
__func__, draw->cpm4, RADEON_CTX_MAX_PM4);
return -EINVAL;
}
- ctx->draw[ctx->ndraw] = *draw;
- for (i = 0, cpm4 = 0; i < draw->nstate - 1; i++) {
- ctx->draw[ctx->ndraw].state[i].valid &= ~2;
- if (ctx->draw[ctx->ndraw].state[i].valid) {
- if (ctx->ndraw > 1 && ctx->draw[ctx->ndraw - 1].state[i].valid) {
- if (ctx->draw[ctx->ndraw - 1].state[i].pm4_crc == draw->state[i].pm4_crc)
- continue;
+ tmp = realloc(ctx->state, (ctx->nstate + draw->nstate) * sizeof(void*));
+ if (tmp == NULL)
+ return -ENOMEM;
+ ctx->state = tmp;
+ pdraw = ctx->cdraw;
+ for (i = 0, cpm4 = 0, cstate = ctx->nstate; i < draw->nstate - 1; i++) {
+ nstate = draw->state[i];
+ if (nstate) {
+ if (pdraw && pdraw->state[i]) {
+ ostate = pdraw->state[i];
+ if (ostate->pm4_crc != nstate->pm4_crc) {
+ ctx->state[cstate++] = nstate;
+ cpm4 += nstate->cpm4;
+ }
+ } else {
+ ctx->state[cstate++] = nstate;
+ cpm4 += nstate->cpm4;
}
- ctx->draw[ctx->ndraw].state[i].valid |= 2;
- cpm4 += ctx->draw[ctx->ndraw].state[i].cpm4;
}
}
/* The last state is the draw state always add it */
- if (!draw->state[i].valid) {
+ if (draw->state[i] == NULL) {
fprintf(stderr, "%s no draw command\n", __func__);
return -EINVAL;
}
- ctx->draw[ctx->ndraw].state[i].valid |= 2;
- cpm4 += ctx->draw[ctx->ndraw].state[i].cpm4;
+ ctx->state[cstate++] = draw->state[i];
+ cpm4 += draw->state[i]->cpm4;
if ((ctx->draw_cpm4 + cpm4) > RADEON_CTX_MAX_PM4) {
/* need to flush */
return -EBUSY;
}
ctx->draw_cpm4 += cpm4;
- ctx->ndraw++;
+ ctx->nstate = cstate;
+ ctx->draw[ctx->ndraw++] = draw;
+ ctx->cdraw = draw;
return 0;
}
+int radeon_ctx_set_draw(struct radeon_ctx *ctx, struct radeon_draw *draw)
+{
+ int r;
+
+ radeon_draw_incref(draw);
+ r = radeon_ctx_set_draw_new(ctx, draw);
+ if (r)
+ radeon_draw_decref(draw);
+ return r;
+}
+
int radeon_ctx_pm4(struct radeon_ctx *ctx)
{
- unsigned i, j, c;
+ unsigned i;
int r;
- for (i = 0, c = 0, ctx->id = 0; i < ctx->ndraw; i++) {
- for (j = 0; j < ctx->draw[i].nstate; j++) {
- if (ctx->draw[i].state[j].valid & 2) {
- r = radeon_ctx_state_schedule(ctx, &ctx->draw[i].state[j]);
- if (r)
- return r;
- c += ctx->draw[i].state[j].cpm4;
- }
- }
+ free(ctx->pm4);
+ ctx->cpm4 = 0;
+ ctx->pm4 = malloc(ctx->draw_cpm4 * 4);
+ if (ctx->pm4 == NULL)
+ return -EINVAL;
+ for (i = 0, ctx->id = 0; i < ctx->nstate; i++) {
+ r = radeon_ctx_state_schedule(ctx, ctx->state[i]);
+ if (r)
+ return r;
}
if (ctx->id != ctx->draw_cpm4) {
fprintf(stderr, "%s miss predicted pm4 size %d for %d\n",
diff --git a/src/gallium/winsys/r600/drm/radeon_draw.c b/src/gallium/winsys/r600/drm/radeon_draw.c
index 53699eb0b1c..4413ed79fbd 100644
--- a/src/gallium/winsys/r600/drm/radeon_draw.c
+++ b/src/gallium/winsys/r600/drm/radeon_draw.c
@@ -31,33 +31,111 @@
/*
* draw functions
*/
-int radeon_draw_init(struct radeon_draw *draw, struct radeon *radeon)
+struct radeon_draw *radeon_draw(struct radeon *radeon)
{
- memset(draw, 0, sizeof(struct radeon_draw));
+ struct radeon_draw *draw;
+
+ draw = calloc(1, sizeof(*draw));
+ if (draw == NULL)
+ return NULL;
draw->nstate = radeon->nstate;
draw->radeon = radeon;
- return 0;
+ draw->refcount = 1;
+ draw->state = calloc(1, sizeof(void*) * draw->nstate);
+ if (draw->state == NULL) {
+ free(draw);
+ return NULL;
+ }
+ return draw;
}
-int radeon_draw_set(struct radeon_draw *draw, struct radeon_state *state)
+struct radeon_draw *radeon_draw_incref(struct radeon_draw *draw)
+{
+ draw->refcount++;
+ return draw;
+}
+
+struct radeon_draw *radeon_draw_decref(struct radeon_draw *draw)
+{
+ unsigned i;
+
+ if (draw == NULL)
+ return NULL;
+ if (--draw->refcount > 0)
+ return NULL;
+ for (i = 0; i < draw->nstate; i++) {
+ draw->state[i] = radeon_state_decref(draw->state[i]);
+ }
+ free(draw->state);
+ memset(draw, 0, sizeof(*draw));
+ free(draw);
+ return NULL;
+}
+
+int radeon_draw_set_new(struct radeon_draw *draw, struct radeon_state *state)
{
if (state == NULL)
return 0;
if (state->type >= draw->radeon->ntype)
return -EINVAL;
- draw->state[state->id] = *state;
+ draw->state[state->id] = radeon_state_decref(draw->state[state->id]);
+ draw->state[state->id] = state;
return 0;
}
+int radeon_draw_set(struct radeon_draw *draw, struct radeon_state *state)
+{
+ if (state == NULL)
+ return 0;
+ radeon_state_incref(state);
+ return radeon_draw_set_new(draw, state);
+}
+
int radeon_draw_check(struct radeon_draw *draw)
{
unsigned i;
int r;
+ r = radeon_draw_pm4(draw);
+ if (r)
+ return r;
for (i = 0, draw->cpm4 = 0; i < draw->nstate; i++) {
- if (draw->state[i].valid) {
- draw->cpm4 += draw->state[i].cpm4;
+ if (draw->state[i]) {
+ draw->cpm4 += draw->state[i]->cpm4;
}
}
return 0;
}
+
+struct radeon_draw *radeon_draw_duplicate(struct radeon_draw *draw)
+{
+ struct radeon_draw *ndraw;
+ unsigned i;
+
+ if (draw == NULL)
+ return NULL;
+ ndraw = radeon_draw(draw->radeon);
+ if (ndraw == NULL) {
+ return NULL;
+ }
+ for (i = 0; i < draw->nstate; i++) {
+ if (radeon_draw_set(ndraw, draw->state[i])) {
+ radeon_draw_decref(ndraw);
+ return NULL;
+ }
+ }
+ return ndraw;
+}
+
+int radeon_draw_pm4(struct radeon_draw *draw)
+{
+ unsigned i;
+ int r;
+
+ for (i = 0; i < draw->nstate; i++) {
+ r = radeon_state_pm4(draw->state[i]);
+ if (r)
+ return r;
+ }
+ return 0;
+}
diff --git a/src/gallium/winsys/r600/drm/radeon_priv.h b/src/gallium/winsys/r600/drm/radeon_priv.h
index 80392cda967..b91421f4389 100644
--- a/src/gallium/winsys/r600/drm/radeon_priv.h
+++ b/src/gallium/winsys/r600/drm/radeon_priv.h
@@ -24,6 +24,7 @@
#include "radeon.h"
struct radeon;
+struct radeon_ctx;
/*
* radeon functions
@@ -70,6 +71,34 @@ extern unsigned radeon_type_from_id(struct radeon *radeon, unsigned id);
/*
* radeon context functions
*/
+#pragma pack(1)
+struct radeon_cs_reloc {
+ uint32_t handle;
+ uint32_t read_domain;
+ uint32_t write_domain;
+ uint32_t flags;
+};
+#pragma pack()
+
+struct radeon_ctx {
+ int refcount;
+ struct radeon *radeon;
+ u32 *pm4;
+ u32 cpm4;
+ u32 draw_cpm4;
+ unsigned id;
+ unsigned next_id;
+ unsigned nreloc;
+ struct radeon_cs_reloc *reloc;
+ unsigned nbo;
+ struct radeon_bo **bo;
+ unsigned ndraw;
+ struct radeon_draw *cdraw;
+ struct radeon_draw **draw;
+ unsigned nstate;
+ struct radeon_state **state;
+};
+
int radeon_ctx_set_bo_new(struct radeon_ctx *ctx, struct radeon_bo *bo);
struct radeon_bo *radeon_ctx_get_bo(struct radeon_ctx *ctx, unsigned reloc);
void radeon_ctx_get_placement(struct radeon_ctx *ctx, unsigned reloc, u32 *placement);
diff --git a/src/gallium/winsys/r600/drm/radeon_state.c b/src/gallium/winsys/r600/drm/radeon_state.c
index d7cd1d7a946..308288557a4 100644
--- a/src/gallium/winsys/r600/drm/radeon_state.c
+++ b/src/gallium/winsys/r600/drm/radeon_state.c
@@ -32,23 +32,82 @@
/*
* state core functions
*/
-int radeon_state_init(struct radeon_state *state, struct radeon *radeon, u32 type, u32 id)
+struct radeon_state *radeon_state(struct radeon *radeon, u32 type, u32 id)
{
+ struct radeon_state *state;
+
if (type > radeon->ntype) {
fprintf(stderr, "%s invalid type %d\n", __func__, type);
- return -EINVAL;
+ return NULL;
}
if (id > radeon->nstate) {
fprintf(stderr, "%s invalid state id %d\n", __func__, id);
- return -EINVAL;
+ return NULL;
}
- memset(state, 0, sizeof(struct radeon_state));
+ state = calloc(1, sizeof(*state));
+ if (state == NULL)
+ return NULL;
state->radeon = radeon;
state->type = type;
state->id = id;
+ state->refcount = 1;
state->npm4 = radeon->type[type].npm4;
state->nstates = radeon->type[type].nstates;
- return 0;
+ state->states = calloc(1, state->nstates * 4);
+ state->pm4 = calloc(1, radeon->type[type].npm4 * 4);
+ if (state->states == NULL || state->pm4 == NULL) {
+ radeon_state_decref(state);
+ return NULL;
+ }
+ return state;
+}
+
+struct radeon_state *radeon_state_duplicate(struct radeon_state *state)
+{
+ struct radeon_state *nstate = radeon_state(state->radeon, state->type, state->id);
+ unsigned i;
+
+ if (state == NULL)
+ return NULL;
+ nstate->cpm4 = state->cpm4;
+ nstate->nbo = state->nbo;
+ nstate->nreloc = state->nreloc;
+ memcpy(nstate->states, state->states, state->nstates * 4);
+ memcpy(nstate->pm4, state->pm4, state->npm4 * 4);
+ memcpy(nstate->placement, state->placement, 8 * 4);
+ memcpy(nstate->reloc_pm4_id, state->reloc_pm4_id, 8 * 4);
+ memcpy(nstate->reloc_bo_id, state->reloc_bo_id, 8 * 4);
+ memcpy(nstate->bo_dirty, state->bo_dirty, 4 * 4);
+ for (i = 0; i < state->nbo; i++) {
+ nstate->bo[i] = radeon_bo_incref(state->radeon, state->bo[i]);
+ }
+ return nstate;
+}
+
+struct radeon_state *radeon_state_incref(struct radeon_state *state)
+{
+ state->refcount++;
+ return state;
+}
+
+struct radeon_state *radeon_state_decref(struct radeon_state *state)
+{
+ unsigned i;
+
+ if (state == NULL)
+ return NULL;
+ if (--state->refcount > 0) {
+ return NULL;
+ }
+ for (i = 0; i < state->nbo; i++) {
+ state->bo[i] = radeon_bo_decref(state->radeon, state->bo[i]);
+ }
+ free(state->immd);
+ free(state->states);
+ free(state->pm4);
+ memset(state, 0, sizeof(*state));
+ free(state);
+ return NULL;
}
int radeon_state_replace_always(struct radeon_state *ostate,
@@ -97,7 +156,6 @@ int radeon_state_pm4(struct radeon_state *state)
return r;
}
state->pm4_crc = crc32(state->pm4, state->cpm4 * 4);
- state->valid = 1;
return 0;
}