[Mesa-dev] [PATCH 15/20] radeonsi: add basic infrastructure for atom-based states

Christian König deathsimple at vodafone.de
Thu Aug 8 01:32:16 PDT 2013


Am 08.08.2013 02:20, schrieb Marek Olšák:
> It's the same as in r600g. Look how simple it is.

That concept has the problem that we don't necessary know in which order 
the state is emitted.

Why not just add an "emit" callback to si_pm4_state for the short term 
instead?

For the long term we should probably teach the kernel interface to 
accept a bunch of pointers to smaller IB fragments instead of one large 
IB. That would allow us to not only save the copy of commands for the 
CSO states, but also allows us to emit optional IB fragments that are 
only inserted if the we had a context switch in between.

Christian.

> ---
>   src/gallium/drivers/radeonsi/r600_hw_context.c |  8 ++++++++
>   src/gallium/drivers/radeonsi/radeonsi_pipe.h   |  9 +++++++++
>   src/gallium/drivers/radeonsi/si_state.h        | 10 ++++++++++
>   src/gallium/drivers/radeonsi/si_state_draw.c   |  8 +++++++-
>   4 files changed, 34 insertions(+), 1 deletion(-)
>
> diff --git a/src/gallium/drivers/radeonsi/r600_hw_context.c b/src/gallium/drivers/radeonsi/r600_hw_context.c
> index 382382b..7ed7496 100644
> --- a/src/gallium/drivers/radeonsi/r600_hw_context.c
> +++ b/src/gallium/drivers/radeonsi/r600_hw_context.c
> @@ -114,9 +114,17 @@ err:
>   void si_need_cs_space(struct r600_context *ctx, unsigned num_dw,
>   			boolean count_draw_in)
>   {
> +	int i;
> +
>   	/* The number of dwords we already used in the CS so far. */
>   	num_dw += ctx->cs->cdw;
>   
> +	for (i = 0; i < ctx->num_atoms; i++) {
> +		if (ctx->atoms[i]->dirty) {
> +			num_dw += ctx->atoms[i]->num_dw;
> +		}
> +	}
> +
>   	if (count_draw_in) {
>   		/* The number of dwords all the dirty states would take. */
>   		num_dw += ctx->pm4_dirty_cdwords;
> diff --git a/src/gallium/drivers/radeonsi/radeonsi_pipe.h b/src/gallium/drivers/radeonsi/radeonsi_pipe.h
> index e370149..5fa9bdc 100644
> --- a/src/gallium/drivers/radeonsi/radeonsi_pipe.h
> +++ b/src/gallium/drivers/radeonsi/radeonsi_pipe.h
> @@ -145,6 +145,10 @@ struct r600_context {
>   	void				*custom_blend_decompress;
>   	struct r600_screen		*screen;
>   	struct radeon_winsys		*ws;
> +
> +	struct si_atom			*atoms[SI_MAX_ATOMS];
> +	unsigned			num_atoms;
> +
>   	struct si_vertex_element	*vertex_elements;
>   	struct pipe_framebuffer_state	framebuffer;
>   	unsigned			fb_log_samples;
> @@ -329,4 +333,9 @@ static INLINE uint64_t r600_resource_va(struct pipe_screen *screen, struct pipe_
>   	return rscreen->ws->buffer_get_virtual_address(rresource->cs_buf);
>   }
>   
> +static INLINE void si_add_atom(struct r600_context *rctx, struct si_atom *atom)
> +{
> +	rctx->atoms[rctx->num_atoms++] = atom;
> +}
> +
>   #endif
> diff --git a/src/gallium/drivers/radeonsi/si_state.h b/src/gallium/drivers/radeonsi/si_state.h
> index b01fbf2..4aabdef 100644
> --- a/src/gallium/drivers/radeonsi/si_state.h
> +++ b/src/gallium/drivers/radeonsi/si_state.h
> @@ -29,6 +29,16 @@
>   
>   #include "radeonsi_pm4.h"
>   
> +#define SI_MAX_ATOMS 2
> +
> +/* This encapsulates a state or an operation which can emitted into the GPU
> + * command stream. */
> +struct si_atom {
> +	void (*emit)(struct r600_context *ctx, struct si_atom *state);
> +	unsigned		num_dw;
> +	bool			dirty;
> +};
> +
>   struct si_state_blend {
>   	struct si_pm4_state	pm4;
>   	uint32_t		cb_target_mask;
> diff --git a/src/gallium/drivers/radeonsi/si_state_draw.c b/src/gallium/drivers/radeonsi/si_state_draw.c
> index 4208fa7..bcae778 100644
> --- a/src/gallium/drivers/radeonsi/si_state_draw.c
> +++ b/src/gallium/drivers/radeonsi/si_state_draw.c
> @@ -664,7 +664,7 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
>   {
>   	struct r600_context *rctx = (struct r600_context *)ctx;
>   	struct pipe_index_buffer ib = {};
> -	uint32_t cp_coher_cntl;
> +	uint32_t cp_coher_cntl, i;
>   
>   	if (!info->count && (info->indexed || !info->count_from_stream_output))
>   		return;
> @@ -728,6 +728,12 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
>   
>   	si_need_cs_space(rctx, 0, TRUE);
>   
> +	for (i = 0; i < rctx->num_atoms; i++) {
> +		if (rctx->atoms[i]->dirty) {
> +			rctx->atoms[i]->emit(rctx, rctx->atoms[i]);
> +		}
> +	}
> +
>   	si_pm4_emit_dirty(rctx);
>   	rctx->pm4_dirty_cdwords = 0;
>   



More information about the mesa-dev mailing list