aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm
diff options
context:
space:
mode:
authorDaniel Vetter <daniel.vetter@ffwll.ch>2015-11-24 04:00:36 -0500
committerRussell King <rmk+kernel@arm.linux.org.uk>2015-12-05 16:44:07 -0500
commit0b8ebeacf5ef43a467c7ec5400ccc1ffc3fbdfba (patch)
treeae367b9b8dfa91535a38ec8a62d20184b804d58d /drivers/gpu/drm
parent4bd3fd443aa4bc3cede05de201e9cf3277059477 (diff)
drm/armada: use a private mutex to protect priv->linear
Reusing the Big DRM Lock just leaks, and the few things left that dev->struct_mutex protected are very well contained - it's just the linear drm_mm manager. With this armada is completely struct_mutex free! v2: Convert things properly and also take the lock in armada_gem_free_object, and remove the stale comment (Russell). Signed-off-by: Daniel Vetter <daniel.vetter@intel.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r--drivers/gpu/drm/armada/armada_debugfs.c4
-rw-r--r--drivers/gpu/drm/armada/armada_drm.h3
-rw-r--r--drivers/gpu/drm/armada/armada_drv.c1
-rw-r--r--drivers/gpu/drm/armada/armada_gem.c14
4 files changed, 14 insertions, 8 deletions
diff --git a/drivers/gpu/drm/armada/armada_debugfs.c b/drivers/gpu/drm/armada/armada_debugfs.c
index 471e45627f1e..d4f7ab0a30d4 100644
--- a/drivers/gpu/drm/armada/armada_debugfs.c
+++ b/drivers/gpu/drm/armada/armada_debugfs.c
@@ -21,9 +21,9 @@ static int armada_debugfs_gem_linear_show(struct seq_file *m, void *data)
21 struct armada_private *priv = dev->dev_private; 21 struct armada_private *priv = dev->dev_private;
22 int ret; 22 int ret;
23 23
24 mutex_lock(&dev->struct_mutex); 24 mutex_lock(&priv->linear_lock);
25 ret = drm_mm_dump_table(m, &priv->linear); 25 ret = drm_mm_dump_table(m, &priv->linear);
26 mutex_unlock(&dev->struct_mutex); 26 mutex_unlock(&priv->linear_lock);
27 27
28 return ret; 28 return ret;
29} 29}
diff --git a/drivers/gpu/drm/armada/armada_drm.h b/drivers/gpu/drm/armada/armada_drm.h
index 4df6f2af2b21..3b2bb6128d40 100644
--- a/drivers/gpu/drm/armada/armada_drm.h
+++ b/drivers/gpu/drm/armada/armada_drm.h
@@ -57,7 +57,8 @@ struct armada_private {
57 DECLARE_KFIFO(fb_unref, struct drm_framebuffer *, 8); 57 DECLARE_KFIFO(fb_unref, struct drm_framebuffer *, 8);
58 struct drm_fb_helper *fbdev; 58 struct drm_fb_helper *fbdev;
59 struct armada_crtc *dcrtc[2]; 59 struct armada_crtc *dcrtc[2];
60 struct drm_mm linear; 60 struct drm_mm linear; /* protected by linear_lock */
61 struct mutex linear_lock;
61 struct drm_property *csc_yuv_prop; 62 struct drm_property *csc_yuv_prop;
62 struct drm_property *csc_rgb_prop; 63 struct drm_property *csc_rgb_prop;
63 struct drm_property *colorkey_prop; 64 struct drm_property *colorkey_prop;
diff --git a/drivers/gpu/drm/armada/armada_drv.c b/drivers/gpu/drm/armada/armada_drv.c
index 3f1396e673dd..f7f47cb71db4 100644
--- a/drivers/gpu/drm/armada/armada_drv.c
+++ b/drivers/gpu/drm/armada/armada_drv.c
@@ -101,6 +101,7 @@ static int armada_drm_load(struct drm_device *dev, unsigned long flags)
101 dev->mode_config.preferred_depth = 24; 101 dev->mode_config.preferred_depth = 24;
102 dev->mode_config.funcs = &armada_drm_mode_config_funcs; 102 dev->mode_config.funcs = &armada_drm_mode_config_funcs;
103 drm_mm_init(&priv->linear, mem->start, resource_size(mem)); 103 drm_mm_init(&priv->linear, mem->start, resource_size(mem));
104 mutex_init(&priv->linear_lock);
104 105
105 ret = component_bind_all(dev->dev, dev); 106 ret = component_bind_all(dev->dev, dev);
106 if (ret) 107 if (ret)
diff --git a/drivers/gpu/drm/armada/armada_gem.c b/drivers/gpu/drm/armada/armada_gem.c
index e3a86b96af2a..6e731db31aa4 100644
--- a/drivers/gpu/drm/armada/armada_gem.c
+++ b/drivers/gpu/drm/armada/armada_gem.c
@@ -46,22 +46,26 @@ static size_t roundup_gem_size(size_t size)
46 return roundup(size, PAGE_SIZE); 46 return roundup(size, PAGE_SIZE);
47} 47}
48 48
49/* dev->struct_mutex is held here */
50void armada_gem_free_object(struct drm_gem_object *obj) 49void armada_gem_free_object(struct drm_gem_object *obj)
51{ 50{
52 struct armada_gem_object *dobj = drm_to_armada_gem(obj); 51 struct armada_gem_object *dobj = drm_to_armada_gem(obj);
52 struct armada_private *priv = obj->dev->dev_private;
53 53
54 DRM_DEBUG_DRIVER("release obj %p\n", dobj); 54 DRM_DEBUG_DRIVER("release obj %p\n", dobj);
55 55
56 drm_gem_free_mmap_offset(&dobj->obj); 56 drm_gem_free_mmap_offset(&dobj->obj);
57 57
58 might_lock(&priv->linear_lock);
59
58 if (dobj->page) { 60 if (dobj->page) {
59 /* page backed memory */ 61 /* page backed memory */
60 unsigned int order = get_order(dobj->obj.size); 62 unsigned int order = get_order(dobj->obj.size);
61 __free_pages(dobj->page, order); 63 __free_pages(dobj->page, order);
62 } else if (dobj->linear) { 64 } else if (dobj->linear) {
63 /* linear backed memory */ 65 /* linear backed memory */
66 mutex_lock(&priv->linear_lock);
64 drm_mm_remove_node(dobj->linear); 67 drm_mm_remove_node(dobj->linear);
68 mutex_unlock(&priv->linear_lock);
65 kfree(dobj->linear); 69 kfree(dobj->linear);
66 if (dobj->addr) 70 if (dobj->addr)
67 iounmap(dobj->addr); 71 iounmap(dobj->addr);
@@ -144,10 +148,10 @@ armada_gem_linear_back(struct drm_device *dev, struct armada_gem_object *obj)
144 if (!node) 148 if (!node)
145 return -ENOSPC; 149 return -ENOSPC;
146 150
147 mutex_lock(&dev->struct_mutex); 151 mutex_lock(&priv->linear_lock);
148 ret = drm_mm_insert_node(&priv->linear, node, size, align, 152 ret = drm_mm_insert_node(&priv->linear, node, size, align,
149 DRM_MM_SEARCH_DEFAULT); 153 DRM_MM_SEARCH_DEFAULT);
150 mutex_unlock(&dev->struct_mutex); 154 mutex_unlock(&priv->linear_lock);
151 if (ret) { 155 if (ret) {
152 kfree(node); 156 kfree(node);
153 return ret; 157 return ret;
@@ -158,9 +162,9 @@ armada_gem_linear_back(struct drm_device *dev, struct armada_gem_object *obj)
158 /* Ensure that the memory we're returning is cleared. */ 162 /* Ensure that the memory we're returning is cleared. */
159 ptr = ioremap_wc(obj->linear->start, size); 163 ptr = ioremap_wc(obj->linear->start, size);
160 if (!ptr) { 164 if (!ptr) {
161 mutex_lock(&dev->struct_mutex); 165 mutex_lock(&priv->linear_lock);
162 drm_mm_remove_node(obj->linear); 166 drm_mm_remove_node(obj->linear);
163 mutex_unlock(&dev->struct_mutex); 167 mutex_unlock(&priv->linear_lock);
164 kfree(obj->linear); 168 kfree(obj->linear);
165 obj->linear = NULL; 169 obj->linear = NULL;
166 return -ENOMEM; 170 return -ENOMEM;