summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBen Widawsky <benjamin.widawsky@intel.com>2013-12-26 09:17:52 -0800
committerBen Widawsky <benjamin.widawsky@intel.com>2013-12-26 09:17:52 -0800
commite387bee671cb152211671550f297717ef0d01533 (patch)
treea01ce5231f017c8e2018039bd9431c6bbed94560
parent0733fe95e36b4559c8e696d3570e2372c62150a3 (diff)
drm/i915: Special case default context creation
Previously, the default context was special cased, and not part of the idr. With the recent PPGTT patches it became ideal to have the default context simply exist as any other context, and locatable within the idr. For a future patch, I intend to make it possible to supplant the default context (see that commit for the details). Remember that the default context continues to be a special case as its state is not saved/restored. Therefore if we were to destroy the default context, and something else ended up with the default context ID, that context would not have its state saved/restored. That is not correct behavior. This patch simple provides the ability to differentiate between a real default context, and a usurper. Signed-off-by: Ben Widawsky <ben@bwidawsk.net>
-rw-r--r--drivers/gpu/drm/i915/i915_gem_context.c29
1 files changed, 21 insertions, 8 deletions
diff --git a/drivers/gpu/drm/i915/i915_gem_context.c b/drivers/gpu/drm/i915/i915_gem_context.c
index ebe0f67eac08..cd15add766bf 100644
--- a/drivers/gpu/drm/i915/i915_gem_context.c
+++ b/drivers/gpu/drm/i915/i915_gem_context.c
@@ -176,7 +176,8 @@ create_vm_for_ctx(struct drm_device *dev, struct i915_hw_context *ctx)
static struct i915_hw_context *
__create_hw_context(struct drm_device *dev,
- struct drm_i915_file_private *file_priv)
+ struct drm_i915_file_private *file_priv,
+ bool default_ctx)
{
struct drm_i915_private *dev_priv = dev->dev_private;
struct i915_hw_context *ctx;
@@ -209,8 +210,16 @@ __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);
+ if (default_ctx) {
+ ret = idr_alloc(&file_priv->context_idr, ctx,
+ DEFAULT_CONTEXT_ID, DEFAULT_CONTEXT_ID,
+ GFP_KERNEL);
+ } else {
+ ret = idr_alloc_cyclic(&file_priv->context_idr, ctx,
+ DEFAULT_CONTEXT_ID + 1, 0,
+ GFP_KERNEL);
+ }
+
if (ret < 0)
goto err_out;
@@ -241,7 +250,8 @@ static inline bool is_default_context(struct i915_hw_context *ctx)
static struct i915_hw_context *
i915_gem_create_context(struct drm_device *dev,
struct drm_i915_file_private *file_priv,
- bool create_vm)
+ bool create_vm,
+ bool default_ctx)
{
struct drm_i915_private *dev_priv = dev->dev_private;
struct i915_hw_context *ctx;
@@ -249,7 +259,7 @@ i915_gem_create_context(struct drm_device *dev,
BUG_ON(!mutex_is_locked(&dev->struct_mutex));
- ctx = __create_hw_context(dev, file_priv);
+ ctx = __create_hw_context(dev, file_priv, default_ctx);
if (IS_ERR(ctx))
return ctx;
@@ -371,7 +381,8 @@ int i915_gem_context_init(struct drm_device *dev)
}
dev_priv->ring[RCS].default_context =
- i915_gem_create_context(dev, NULL, USES_ALIASING_PPGTT(dev));
+ i915_gem_create_context(dev, NULL, USES_ALIASING_PPGTT(dev),
+ true);
if (IS_ERR_OR_NULL(dev_priv->ring[RCS].default_context)) {
DRM_DEBUG_DRIVER("Disabling HW Contexts; create failed %ld\n",
@@ -498,7 +509,8 @@ int i915_gem_context_open(struct drm_device *dev, struct drm_file *file)
mutex_lock(&dev->struct_mutex);
file_priv->private_default_ctx =
- i915_gem_create_context(dev, file_priv, USES_FULL_PPGTT(dev));
+ i915_gem_create_context(dev, file_priv, USES_FULL_PPGTT(dev),
+ true);
mutex_unlock(&dev->struct_mutex);
if (IS_ERR(file_priv->private_default_ctx)) {
@@ -746,7 +758,8 @@ int i915_gem_context_create_ioctl(struct drm_device *dev, void *data,
if (ret)
return ret;
- ctx = i915_gem_create_context(dev, file_priv, USES_FULL_PPGTT(dev));
+ ctx = i915_gem_create_context(dev, file_priv, USES_FULL_PPGTT(dev),
+ false);
mutex_unlock(&dev->struct_mutex);
if (IS_ERR(ctx))
return PTR_ERR(ctx);