diff --git a/src/gallium/drivers/iris/iris_batch.c b/src/gallium/drivers/iris/iris_batch.c index fabea867b48..e3be9c3df8a 100644 --- a/src/gallium/drivers/iris/iris_batch.c +++ b/src/gallium/drivers/iris/iris_batch.c @@ -398,6 +398,9 @@ iris_batch_reset(struct iris_batch *batch) iris_cache_sets_clear(batch); + assert(!batch->sync_region_depth); + iris_batch_sync_boundary(batch); + /* Always add the workaround BO, it contains a driver identifier at the * beginning quite helpful to debug error states. */ diff --git a/src/gallium/drivers/iris/iris_batch.h b/src/gallium/drivers/iris/iris_batch.h index c95fd23491f..50de99289cf 100644 --- a/src/gallium/drivers/iris/iris_batch.h +++ b/src/gallium/drivers/iris/iris_batch.h @@ -144,9 +144,21 @@ struct iris_batch { struct gen_batch_decode_ctx decoder; struct hash_table_u64 *state_sizes; + /** + * Sequence number used to track the completion of any subsequent memory + * operations in the batch until the next sync boundary. + */ + uint64_t next_seqno; + /** Have we emitted any draw calls to this batch? */ bool contains_draw; + /** + * Number of times iris_batch_sync_region_start() has been called without a + * matching iris_batch_sync_region_end() on this batch. + */ + uint32_t sync_region_depth; + uint32_t last_aux_map_state; }; @@ -260,4 +272,41 @@ iris_record_state_size(struct hash_table_u64 *ht, } } +/** + * Mark the start of a region in the batch with stable synchronization + * sequence number. Any buffer object accessed by the batch buffer only needs + * to be marked once (e.g. via iris_bo_bump_seqno()) within a region delimited + * by iris_batch_sync_region_start() and iris_batch_sync_region_end(). + */ +static inline void +iris_batch_sync_region_start(struct iris_batch *batch) +{ + batch->sync_region_depth++; +} + +/** + * Mark the end of a region in the batch with stable synchronization sequence + * number. Should be called once after each call to + * iris_batch_sync_region_start(). + */ +static inline void +iris_batch_sync_region_end(struct iris_batch *batch) +{ + assert(batch->sync_region_depth); + batch->sync_region_depth--; +} + +/** + * Start a new synchronization section at the current point of the batch, + * unless disallowed by a previous iris_batch_sync_region_start(). + */ +static inline void +iris_batch_sync_boundary(struct iris_batch *batch) +{ + if (!batch->sync_region_depth) { + batch->next_seqno = p_atomic_inc_return(&batch->screen->last_seqno); + assert(batch->next_seqno > 0); + } +} + #endif diff --git a/src/gallium/drivers/iris/iris_screen.h b/src/gallium/drivers/iris/iris_screen.h index bfc5284fc72..b536e10642b 100644 --- a/src/gallium/drivers/iris/iris_screen.h +++ b/src/gallium/drivers/iris/iris_screen.h @@ -182,6 +182,15 @@ struct iris_screen { uint64_t aperture_bytes; + /** + * Last sequence number allocated by the cache tracking mechanism. + * + * These are used for synchronization and are expected to identify a single + * section of a batch, so they should be monotonically increasing and + * unique across a single pipe_screen. + */ + uint64_t last_seqno; + struct gen_device_info devinfo; struct isl_device isl_dev; struct iris_bufmgr *bufmgr;