Re: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

2012-07-27 Thread Ben Widawsky
On Fri, 27 Jul 2012 04:19:10 +
Zhang, Xiong Y xiong.y.zh...@intel.com wrote:


Who will monitor this sysfs interface, 2D driver or 3D driver or other 
 application ?
Now, I don't find any user of this sysfs interface in 2D driver or 3D 
 driver.
 
 thanks

The notification is meant to be received through a udev event. What user
space should do at that point has been somewhat up to discussion thus
far. In order to correct the issues, a neutral root third party should
receieve the event and program the sysfs entry with the remap
information (possibly also force a GPU reset through debugfs).

In the ideal case, I think we should have GPU clients somehow register
that they want to be notified by such an event, maybe a signal based
mechanism, so they can dump all of their buffers and start over. That
should allow us to not force the GPU reset.

So far, we've not had any GPU clients that care enough abuot a faulty
cacheline to use such an interface. It was really provided as a
gpgpu/compute shader type of feature.


 
 -Original Message-
 From: intel-gfx-bounces+xiong.y.zhang=intel@lists.freedesktop.org 
 [mailto:intel-gfx-bounces+xiong.y.zhang=intel@lists.freedesktop.org] On 
 Behalf Of Ben Widawsky
 Sent: Saturday, May 26, 2012 7:56 AM
 To: intel-gfx@lists.freedesktop.org
 Cc: Ben Widawsky
 Subject: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface
 
 Dumb binary interfaces which allow root-only updates of the cache remapping 
 registers. As mentioned in a previous patch, software using this interface 
 needs to know about HW limits, and other programming considerations as the 
 kernel interface does no checking for these things on the root-only interface.
 
 v1: Drop extra posting reads (Chris)
 Return negative values in the sysfs interfaces on errors (Chris)
 
 v2: Return -EINVAL for offset % 4 (Jesse) Move schizo userspace check out 
 (Jesse) Cleaner sysfs item initializers (Daniel)
 
 Signed-off-by: Ben Widawsky b...@bwidawsk.net
 ---
  drivers/gpu/drm/i915/i915_sysfs.c |  121 
 -
  1 file changed, 119 insertions(+), 2 deletions(-)
 
 diff --git a/drivers/gpu/drm/i915/i915_sysfs.c 
 b/drivers/gpu/drm/i915/i915_sysfs.c
 index 79f8344..c201327 100644
 --- a/drivers/gpu/drm/i915/i915_sysfs.c
 +++ b/drivers/gpu/drm/i915/i915_sysfs.c
 @@ -29,6 +29,7 @@
  #include linux/module.h
  #include linux/stat.h
  #include linux/sysfs.h
 +#include intel_drv.h
  #include i915_drv.h
  
  static u32 calc_residency(struct drm_device *dev, const u32 reg) @@ -92,20 
 +93,136 @@ static struct attribute_group rc6_attr_group = {
   .attrs =  rc6_attrs
  };
  
 +static int l3_access_valid(struct drm_device *dev, loff_t offset) {
 + if (!IS_IVYBRIDGE(dev))
 + return -EPERM;
 +
 + if (offset % 4 != 0)
 + return -EINVAL;
 +
 + if (offset = GEN7_L3LOG_SIZE)
 + return -ENXIO;
 +
 + return 0;
 +}
 +
 +static ssize_t
 +i915_l3_read(struct file *filp, struct kobject *kobj,
 +  struct bin_attribute *attr, char *buf,
 +  loff_t offset, size_t count)
 +{
 + struct device *dev = container_of(kobj, struct device, kobj);
 + struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
 + struct drm_device *drm_dev = dminor-dev;
 + struct drm_i915_private *dev_priv = drm_dev-dev_private;
 + uint32_t misccpctl;
 + int i, ret;
 +
 + ret = l3_access_valid(drm_dev, offset);
 + if (ret)
 + return ret;
 +
 + ret = i915_mutex_lock_interruptible(drm_dev);
 + if (ret)
 + return ret;
 +
 + misccpctl = I915_READ(GEN7_MISCCPCTL);
 + I915_WRITE(GEN7_MISCCPCTL, misccpctl  ~GEN7_DOP_CLOCK_GATE_ENABLE);
 +
 + for (i = offset; count = 4  i  GEN7_L3LOG_SIZE; i += 4, count -= 4)
 + *((uint32_t *)(buf[i])) = I915_READ(GEN7_L3LOG_BASE + i);
 +
 + I915_WRITE(GEN7_MISCCPCTL, misccpctl);
 +
 + mutex_unlock(drm_dev-struct_mutex);
 +
 + return i - offset;
 +}
 +
 +static ssize_t
 +i915_l3_write(struct file *filp, struct kobject *kobj,
 +   struct bin_attribute *attr, char *buf,
 +   loff_t offset, size_t count)
 +{
 + struct device *dev = container_of(kobj, struct device, kobj);
 + struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
 + struct drm_device *drm_dev = dminor-dev;
 + struct drm_i915_private *dev_priv = drm_dev-dev_private;
 + u32 *temp = NULL; /* Just here to make handling failures easy */
 + int ret;
 +
 + ret = l3_access_valid(drm_dev, offset);
 + if (ret)
 + return ret;
 +
 + ret = i915_mutex_lock_interruptible(drm_dev);
 + if (ret)
 + return ret;
 +
 + if (!dev_priv-mm.l3_remap_info) {
 + temp = kzalloc(GEN7_L3LOG_SIZE, GFP_KERNEL);
 + if (!temp) {
 + mutex_unlock(drm_dev-struct_mutex);
 + return -ENOMEM

Re: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

2012-07-26 Thread Zhang, Xiong Y
   
   Who will monitor this sysfs interface, 2D driver or 3D driver or other 
application ?
   Now, I don't find any user of this sysfs interface in 2D driver or 3D driver.

thanks

-Original Message-
From: intel-gfx-bounces+xiong.y.zhang=intel@lists.freedesktop.org 
[mailto:intel-gfx-bounces+xiong.y.zhang=intel@lists.freedesktop.org] On 
Behalf Of Ben Widawsky
Sent: Saturday, May 26, 2012 7:56 AM
To: intel-gfx@lists.freedesktop.org
Cc: Ben Widawsky
Subject: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

Dumb binary interfaces which allow root-only updates of the cache remapping 
registers. As mentioned in a previous patch, software using this interface 
needs to know about HW limits, and other programming considerations as the 
kernel interface does no checking for these things on the root-only interface.

v1: Drop extra posting reads (Chris)
Return negative values in the sysfs interfaces on errors (Chris)

v2: Return -EINVAL for offset % 4 (Jesse) Move schizo userspace check out 
(Jesse) Cleaner sysfs item initializers (Daniel)

Signed-off-by: Ben Widawsky b...@bwidawsk.net
---
 drivers/gpu/drm/i915/i915_sysfs.c |  121 -
 1 file changed, 119 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_sysfs.c 
b/drivers/gpu/drm/i915/i915_sysfs.c
index 79f8344..c201327 100644
--- a/drivers/gpu/drm/i915/i915_sysfs.c
+++ b/drivers/gpu/drm/i915/i915_sysfs.c
@@ -29,6 +29,7 @@
 #include linux/module.h
 #include linux/stat.h
 #include linux/sysfs.h
+#include intel_drv.h
 #include i915_drv.h
 
 static u32 calc_residency(struct drm_device *dev, const u32 reg) @@ -92,20 
+93,136 @@ static struct attribute_group rc6_attr_group = {
.attrs =  rc6_attrs
 };
 
+static int l3_access_valid(struct drm_device *dev, loff_t offset) {
+   if (!IS_IVYBRIDGE(dev))
+   return -EPERM;
+
+   if (offset % 4 != 0)
+   return -EINVAL;
+
+   if (offset = GEN7_L3LOG_SIZE)
+   return -ENXIO;
+
+   return 0;
+}
+
+static ssize_t
+i915_l3_read(struct file *filp, struct kobject *kobj,
+struct bin_attribute *attr, char *buf,
+loff_t offset, size_t count)
+{
+   struct device *dev = container_of(kobj, struct device, kobj);
+   struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
+   struct drm_device *drm_dev = dminor-dev;
+   struct drm_i915_private *dev_priv = drm_dev-dev_private;
+   uint32_t misccpctl;
+   int i, ret;
+
+   ret = l3_access_valid(drm_dev, offset);
+   if (ret)
+   return ret;
+
+   ret = i915_mutex_lock_interruptible(drm_dev);
+   if (ret)
+   return ret;
+
+   misccpctl = I915_READ(GEN7_MISCCPCTL);
+   I915_WRITE(GEN7_MISCCPCTL, misccpctl  ~GEN7_DOP_CLOCK_GATE_ENABLE);
+
+   for (i = offset; count = 4  i  GEN7_L3LOG_SIZE; i += 4, count -= 4)
+   *((uint32_t *)(buf[i])) = I915_READ(GEN7_L3LOG_BASE + i);
+
+   I915_WRITE(GEN7_MISCCPCTL, misccpctl);
+
+   mutex_unlock(drm_dev-struct_mutex);
+
+   return i - offset;
+}
+
+static ssize_t
+i915_l3_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *attr, char *buf,
+ loff_t offset, size_t count)
+{
+   struct device *dev = container_of(kobj, struct device, kobj);
+   struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
+   struct drm_device *drm_dev = dminor-dev;
+   struct drm_i915_private *dev_priv = drm_dev-dev_private;
+   u32 *temp = NULL; /* Just here to make handling failures easy */
+   int ret;
+
+   ret = l3_access_valid(drm_dev, offset);
+   if (ret)
+   return ret;
+
+   ret = i915_mutex_lock_interruptible(drm_dev);
+   if (ret)
+   return ret;
+
+   if (!dev_priv-mm.l3_remap_info) {
+   temp = kzalloc(GEN7_L3LOG_SIZE, GFP_KERNEL);
+   if (!temp) {
+   mutex_unlock(drm_dev-struct_mutex);
+   return -ENOMEM;
+   }
+   }
+
+   ret = i915_gpu_idle(drm_dev);
+   if (ret) {
+   kfree(temp);
+   mutex_unlock(drm_dev-struct_mutex);
+   return ret;
+   }
+
+   /* TODO: Ideally we really want a GPU reset here to make sure errors
+* aren't propagated. Since I cannot find a stable way to reset the GPU
+* at this point it is left as a TODO.
+   */
+   if (temp)
+   dev_priv-mm.l3_remap_info = temp;
+
+   memcpy(dev_priv-mm.l3_remap_info + (offset/4),
+  buf + (offset/4),
+  count);
+
+   i915_gem_l3_remap(drm_dev);
+
+   mutex_unlock(drm_dev-struct_mutex);
+
+   return count;
+}
+
+static struct bin_attribute dpf_attrs = {
+   .attr = {.name = l3_parity, .mode = (S_IRUSR | S_IWUSR)},
+   .size = GEN7_L3LOG_SIZE,
+   .read = i915_l3_read,
+   .write

Re: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

2012-05-31 Thread Daniel Vetter
On Fri, May 25, 2012 at 04:56:25PM -0700, Ben Widawsky wrote:
 Dumb binary interfaces which allow root-only updates of the cache
 remapping registers. As mentioned in a previous patch, software using
 this interface needs to know about HW limits, and other programming
 considerations as the kernel interface does no checking for these things
 on the root-only interface.
 
 v1: Drop extra posting reads (Chris)
 Return negative values in the sysfs interfaces on errors (Chris)
 
 v2: Return -EINVAL for offset % 4 (Jesse)
 Move schizo userspace check out (Jesse)
 Cleaner sysfs item initializers (Daniel)
 
 Signed-off-by: Ben Widawsky b...@bwidawsk.net

I've queued this series for -next. Although you haven't fixed up the one
issue in patch 2 I've noticed and I also don't see my bikeshed for this
patch (despite that you claim to have done so). Whatever, I'll follow up
with patches.
-Daniel
-- 
Daniel Vetter
Mail: dan...@ffwll.ch
Mobile: +41 (0)79 365 57 48
___
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/intel-gfx


Re: [Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

2012-05-31 Thread Ben Widawsky
On Thu, 31 May 2012 12:45:56 +0200
Daniel Vetter dan...@ffwll.ch wrote:

 On Fri, May 25, 2012 at 04:56:25PM -0700, Ben Widawsky wrote:
  Dumb binary interfaces which allow root-only updates of the cache
  remapping registers. As mentioned in a previous patch, software using
  this interface needs to know about HW limits, and other programming
  considerations as the kernel interface does no checking for these things
  on the root-only interface.
  
  v1: Drop extra posting reads (Chris)
  Return negative values in the sysfs interfaces on errors (Chris)
  
  v2: Return -EINVAL for offset % 4 (Jesse)
  Move schizo userspace check out (Jesse)
  Cleaner sysfs item initializers (Daniel)
  
  Signed-off-by: Ben Widawsky b...@bwidawsk.net
 
 I've queued this series for -next. Although you haven't fixed up the one
 issue in patch 2 I've noticed and I also don't see my bikeshed for this
 patch (despite that you claim to have done so). Whatever, I'll follow up
 with patches.
 -Daniel

Thanks for moving the patches forward, I'll review your fixes to them
shortly. The fixes are somewhere; I am not sure how they got lost.
___
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/intel-gfx


[Intel-gfx] [PATCH 4/4] drm/i915: l3 parity sysfs interface

2012-05-25 Thread Ben Widawsky
Dumb binary interfaces which allow root-only updates of the cache
remapping registers. As mentioned in a previous patch, software using
this interface needs to know about HW limits, and other programming
considerations as the kernel interface does no checking for these things
on the root-only interface.

v1: Drop extra posting reads (Chris)
Return negative values in the sysfs interfaces on errors (Chris)

v2: Return -EINVAL for offset % 4 (Jesse)
Move schizo userspace check out (Jesse)
Cleaner sysfs item initializers (Daniel)

Signed-off-by: Ben Widawsky b...@bwidawsk.net
---
 drivers/gpu/drm/i915/i915_sysfs.c |  121 -
 1 file changed, 119 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_sysfs.c 
b/drivers/gpu/drm/i915/i915_sysfs.c
index 79f8344..c201327 100644
--- a/drivers/gpu/drm/i915/i915_sysfs.c
+++ b/drivers/gpu/drm/i915/i915_sysfs.c
@@ -29,6 +29,7 @@
 #include linux/module.h
 #include linux/stat.h
 #include linux/sysfs.h
+#include intel_drv.h
 #include i915_drv.h
 
 static u32 calc_residency(struct drm_device *dev, const u32 reg)
@@ -92,20 +93,136 @@ static struct attribute_group rc6_attr_group = {
.attrs =  rc6_attrs
 };
 
+static int l3_access_valid(struct drm_device *dev, loff_t offset)
+{
+   if (!IS_IVYBRIDGE(dev))
+   return -EPERM;
+
+   if (offset % 4 != 0)
+   return -EINVAL;
+
+   if (offset = GEN7_L3LOG_SIZE)
+   return -ENXIO;
+
+   return 0;
+}
+
+static ssize_t
+i915_l3_read(struct file *filp, struct kobject *kobj,
+struct bin_attribute *attr, char *buf,
+loff_t offset, size_t count)
+{
+   struct device *dev = container_of(kobj, struct device, kobj);
+   struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
+   struct drm_device *drm_dev = dminor-dev;
+   struct drm_i915_private *dev_priv = drm_dev-dev_private;
+   uint32_t misccpctl;
+   int i, ret;
+
+   ret = l3_access_valid(drm_dev, offset);
+   if (ret)
+   return ret;
+
+   ret = i915_mutex_lock_interruptible(drm_dev);
+   if (ret)
+   return ret;
+
+   misccpctl = I915_READ(GEN7_MISCCPCTL);
+   I915_WRITE(GEN7_MISCCPCTL, misccpctl  ~GEN7_DOP_CLOCK_GATE_ENABLE);
+
+   for (i = offset; count = 4  i  GEN7_L3LOG_SIZE; i += 4, count -= 4)
+   *((uint32_t *)(buf[i])) = I915_READ(GEN7_L3LOG_BASE + i);
+
+   I915_WRITE(GEN7_MISCCPCTL, misccpctl);
+
+   mutex_unlock(drm_dev-struct_mutex);
+
+   return i - offset;
+}
+
+static ssize_t
+i915_l3_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *attr, char *buf,
+ loff_t offset, size_t count)
+{
+   struct device *dev = container_of(kobj, struct device, kobj);
+   struct drm_minor *dminor = container_of(dev, struct drm_minor, kdev);
+   struct drm_device *drm_dev = dminor-dev;
+   struct drm_i915_private *dev_priv = drm_dev-dev_private;
+   u32 *temp = NULL; /* Just here to make handling failures easy */
+   int ret;
+
+   ret = l3_access_valid(drm_dev, offset);
+   if (ret)
+   return ret;
+
+   ret = i915_mutex_lock_interruptible(drm_dev);
+   if (ret)
+   return ret;
+
+   if (!dev_priv-mm.l3_remap_info) {
+   temp = kzalloc(GEN7_L3LOG_SIZE, GFP_KERNEL);
+   if (!temp) {
+   mutex_unlock(drm_dev-struct_mutex);
+   return -ENOMEM;
+   }
+   }
+
+   ret = i915_gpu_idle(drm_dev);
+   if (ret) {
+   kfree(temp);
+   mutex_unlock(drm_dev-struct_mutex);
+   return ret;
+   }
+
+   /* TODO: Ideally we really want a GPU reset here to make sure errors
+* aren't propagated. Since I cannot find a stable way to reset the GPU
+* at this point it is left as a TODO.
+   */
+   if (temp)
+   dev_priv-mm.l3_remap_info = temp;
+
+   memcpy(dev_priv-mm.l3_remap_info + (offset/4),
+  buf + (offset/4),
+  count);
+
+   i915_gem_l3_remap(drm_dev);
+
+   mutex_unlock(drm_dev-struct_mutex);
+
+   return count;
+}
+
+static struct bin_attribute dpf_attrs = {
+   .attr = {.name = l3_parity, .mode = (S_IRUSR | S_IWUSR)},
+   .size = GEN7_L3LOG_SIZE,
+   .read = i915_l3_read,
+   .write = i915_l3_write,
+   .mmap = NULL
+};
+
 void i915_setup_sysfs(struct drm_device *dev)
 {
int ret;
 
-   /* ILK doesn't have any residency information */
+   /* ILK and below don't yet have relevant sysfs files */
if (INTEL_INFO(dev)-gen  6)
return;
 
ret = sysfs_merge_group(dev-primary-kdev.kobj, rc6_attr_group);
if (ret)
-   DRM_ERROR(sysfs setup failed\n);
+   DRM_ERROR(RC6 residency sysfs setup failed\n);
+
+   if (!IS_IVYBRIDGE(dev))
+   return;