[PATCH 36/49] drm/i915/bdw: Prepare for a 20-bits globally unique submission ID

oscar.mateo
2014-03-27T17:12:45Z

From: Oscar Mateo <oscar.mateo@intel.com>

Consisting on 12 bits with the filepriv ID, 5 bits with the context
ID and 3 bits with the ring ID.

Note: this changes the ABI (only 4096 file descriptors are now allowed,
with 8 contexts per-fd) and will break some IGT tests (those that open
a big number of fds). If required, I can try to rewrite this so that
only legacy ring contexts are affected (as it stands now, legacy hw
contexts limits are also modified).

Signed-off-by: Oscar Mateo <oscar.mateo@intel.com>
---
drivers/gpu/drm/i915/i915_drv.h | 5 ++++-
drivers/gpu/drm/i915/i915_gem.c | 3 ++-
drivers/gpu/drm/i915/i915_gem_context.c | 4 ++--
drivers/gpu/drm/i915/i915_lrc.c | 18 ++++++++++++++++++
4 files changed, 26 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
index 2f6e55d..ba3d262 100644
--- a/drivers/gpu/drm/i915/i915_drv.h
+++ b/drivers/gpu/drm/i915/i915_drv.h
@@ -588,7 +588,8 @@ struct i915_ctx_hang_stats {
};

/* This must match up with the value previously used for execbuf2.rsvd1. */
-#define DEFAULT_CONTEXT_ID 0
+#define DEFAULT_CONTEXT_ID 0
+#define CONTEXT_ID_BITS 5
struct i915_hw_context {
struct kref ref;
int id;
@@ -1262,6 +1263,8 @@ struct intel_pipe_crc {
wait_queue_head_t wq;
};

+#define MIN_FILEPRIV_ID 1
+#define FILEPRIV_ID_BITS 12
typedef struct drm_i915_private {
struct drm_device *dev;
struct kmem_cache *slab;
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c
index 07d88847..10bb50f 100644
--- a/drivers/gpu/drm/i915/i915_gem.c
+++ b/drivers/gpu/drm/i915/i915_gem.c
@@ -4893,7 +4893,8 @@ int i915_gem_open(struct drm_device *dev, struct drm_file *file)
file_priv->dev_priv = dev->dev_private;
file_priv->file = file;

- ret = idr_alloc(&dev_priv->filepriv_idr, file_priv, 0, 0, GFP_KERNEL);
+ ret = idr_alloc(&dev_priv->filepriv_idr, file_priv, MIN_FILEPRIV_ID,
+ (1 << FILEPRIV_ID_BITS) - 1, GFP_KERNEL);
if (ret < 0) {
kfree(file_priv);
return ret;
diff --git a/drivers/gpu/drm/i915/i915_gem_context.c b/drivers/gpu/drm/i915/i915_gem_context.c
index a4e878e..1322e00 100644
--- a/drivers/gpu/drm/i915/i915_gem_context.c
+++ b/drivers/gpu/drm/i915/i915_gem_context.c
@@ -259,8 +259,8 @@ __create_hw_context(struct drm_device *dev,
if (file_priv == NULL)
return ctx;

- ret = idr_alloc(&file_priv->context_idr, ctx, DEFAULT_CONTEXT_ID, 0,
- GFP_KERNEL);
+ ret = idr_alloc(&file_priv->context_idr, ctx, DEFAULT_CONTEXT_ID,
+ (1 << CONTEXT_ID_BITS) - 1, GFP_KERNEL);
if (ret < 0)
goto err_out;

diff --git a/drivers/gpu/drm/i915/i915_lrc.c b/drivers/gpu/drm/i915/i915_lrc.c
index 9d1e7f3..91e7ea6 100644
--- a/drivers/gpu/drm/i915/i915_lrc.c
+++ b/drivers/gpu/drm/i915/i915_lrc.c
@@ -77,6 +77,24 @@
#define CTX_R_PWR_CLK_STATE 0x42
#define CTX_GPGPU_CSR_BASE_ADDRESS 0x44

+static inline u32 get_submission_id(struct i915_hw_context *ctx)
+{
+ struct drm_i915_file_private *file_priv = ctx->file_priv;
+ u32 submission_id;
+
+ if (file_priv) {
+ WARN(ctx->ring_id & ~0x7, "Ring ID > 3 bits!\n");
+ submission_id = ctx->ring_id;
+ submission_id |= (ctx->id << 3);
+ submission_id |= (file_priv->id << (CONTEXT_ID_BITS + 3));
+ } else {
+ submission_id = ctx->ring_id;
+ submission_id |= (ctx->id << 3);
+ }
+
+ return submission_id;
+}
+
void gen8_gem_context_free(struct i915_hw_context *ctx)
{
/* Global default contexts ringbuffers are take care of
--
1.9.0