aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGuido Martínez <guido@vanguardiasur.com.ar>2014-06-17 10:17:10 -0400
committerDave Airlie <airlied@redhat.com>2014-07-07 21:25:32 -0400
commit7cdcce9f8b4c15dc55f880307b844a49127db86e (patch)
tree22f5da5209c5d9475857630c99576128a7703db9
parentc9a3ad25eddfdb898114a9d73cdb4c3472d9dfca (diff)
drm/tilcdc: remove submodule destroy calls
The TI tilcdc driver is designed with a notion of submodules. Currently, at unload time, these submodules are iterated and destroyed. Now that the tilcdc remove order is fixed, this can be handled perfectly by the kernel using the device infrastructure, since each submodule is a kernel driver itself, and they are only destroy()'ed at unload time. Therefore we move the destroy() functionality to each submodule's remove(). Also, remove some checks in the unloading process since the new code guarantees the resources are allocated and need a release. Signed-off-by: Guido Martínez <guido@vanguardiasur.com.ar> Tested-by: Darren Etheridge <detheridge@ti.com> Signed-off-by: Dave Airlie <airlied@redhat.com>
-rw-r--r--drivers/gpu/drm/tilcdc/Module.symvers0
-rw-r--r--drivers/gpu/drm/tilcdc/tilcdc_drv.c6
-rw-r--r--drivers/gpu/drm/tilcdc/tilcdc_drv.h1
-rw-r--r--drivers/gpu/drm/tilcdc/tilcdc_panel.c36
-rw-r--r--drivers/gpu/drm/tilcdc/tilcdc_slave.c26
-rw-r--r--drivers/gpu/drm/tilcdc/tilcdc_tfp410.c34
6 files changed, 50 insertions, 53 deletions
diff --git a/drivers/gpu/drm/tilcdc/Module.symvers b/drivers/gpu/drm/tilcdc/Module.symvers
new file mode 100644
index 000000000000..e69de29bb2d1
--- /dev/null
+++ b/drivers/gpu/drm/tilcdc/Module.symvers
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_drv.c b/drivers/gpu/drm/tilcdc/tilcdc_drv.c
index 006a30e90390..2c860c41dfdb 100644
--- a/drivers/gpu/drm/tilcdc/tilcdc_drv.c
+++ b/drivers/gpu/drm/tilcdc/tilcdc_drv.c
@@ -120,7 +120,6 @@ static int cpufreq_transition(struct notifier_block *nb,
120static int tilcdc_unload(struct drm_device *dev) 120static int tilcdc_unload(struct drm_device *dev)
121{ 121{
122 struct tilcdc_drm_private *priv = dev->dev_private; 122 struct tilcdc_drm_private *priv = dev->dev_private;
123 struct tilcdc_module *mod, *cur;
124 123
125 drm_fbdev_cma_fini(priv->fbdev); 124 drm_fbdev_cma_fini(priv->fbdev);
126 drm_kms_helper_poll_fini(dev); 125 drm_kms_helper_poll_fini(dev);
@@ -149,11 +148,6 @@ static int tilcdc_unload(struct drm_device *dev)
149 148
150 pm_runtime_disable(dev->dev); 149 pm_runtime_disable(dev->dev);
151 150
152 list_for_each_entry_safe(mod, cur, &module_list, list) {
153 DBG("destroying module: %s", mod->name);
154 mod->funcs->destroy(mod);
155 }
156
157 kfree(priv); 151 kfree(priv);
158 152
159 return 0; 153 return 0;
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_drv.h b/drivers/gpu/drm/tilcdc/tilcdc_drv.h
index 093803683b25..7596c144a9fb 100644
--- a/drivers/gpu/drm/tilcdc/tilcdc_drv.h
+++ b/drivers/gpu/drm/tilcdc/tilcdc_drv.h
@@ -98,7 +98,6 @@ struct tilcdc_module;
98struct tilcdc_module_ops { 98struct tilcdc_module_ops {
99 /* create appropriate encoders/connectors: */ 99 /* create appropriate encoders/connectors: */
100 int (*modeset_init)(struct tilcdc_module *mod, struct drm_device *dev); 100 int (*modeset_init)(struct tilcdc_module *mod, struct drm_device *dev);
101 void (*destroy)(struct tilcdc_module *mod);
102#ifdef CONFIG_DEBUG_FS 101#ifdef CONFIG_DEBUG_FS
103 /* create debugfs nodes (can be NULL): */ 102 /* create debugfs nodes (can be NULL): */
104 int (*debugfs_init)(struct tilcdc_module *mod, struct drm_minor *minor); 103 int (*debugfs_init)(struct tilcdc_module *mod, struct drm_minor *minor);
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_panel.c b/drivers/gpu/drm/tilcdc/tilcdc_panel.c
index b0b9396f41a6..8ff72c8ad06b 100644
--- a/drivers/gpu/drm/tilcdc/tilcdc_panel.c
+++ b/drivers/gpu/drm/tilcdc/tilcdc_panel.c
@@ -282,21 +282,8 @@ static int panel_modeset_init(struct tilcdc_module *mod, struct drm_device *dev)
282 return 0; 282 return 0;
283} 283}
284 284
285static void panel_destroy(struct tilcdc_module *mod)
286{
287 struct panel_module *panel_mod = to_panel_module(mod);
288
289 if (panel_mod->timings)
290 display_timings_release(panel_mod->timings);
291
292 tilcdc_module_cleanup(mod);
293 kfree(panel_mod->info);
294 kfree(panel_mod);
295}
296
297static const struct tilcdc_module_ops panel_module_ops = { 285static const struct tilcdc_module_ops panel_module_ops = {
298 .modeset_init = panel_modeset_init, 286 .modeset_init = panel_modeset_init,
299 .destroy = panel_destroy,
300}; 287};
301 288
302/* 289/*
@@ -372,6 +359,7 @@ static int panel_probe(struct platform_device *pdev)
372 return -ENOMEM; 359 return -ENOMEM;
373 360
374 mod = &panel_mod->base; 361 mod = &panel_mod->base;
362 pdev->dev.platform_data = mod;
375 363
376 tilcdc_module_init(mod, "panel", &panel_module_ops); 364 tilcdc_module_init(mod, "panel", &panel_module_ops);
377 365
@@ -379,17 +367,16 @@ static int panel_probe(struct platform_device *pdev)
379 if (IS_ERR(pinctrl)) 367 if (IS_ERR(pinctrl))
380 dev_warn(&pdev->dev, "pins are not configured\n"); 368 dev_warn(&pdev->dev, "pins are not configured\n");
381 369
382
383 panel_mod->timings = of_get_display_timings(node); 370 panel_mod->timings = of_get_display_timings(node);
384 if (!panel_mod->timings) { 371 if (!panel_mod->timings) {
385 dev_err(&pdev->dev, "could not get panel timings\n"); 372 dev_err(&pdev->dev, "could not get panel timings\n");
386 goto fail; 373 goto fail_free;
387 } 374 }
388 375
389 panel_mod->info = of_get_panel_info(node); 376 panel_mod->info = of_get_panel_info(node);
390 if (!panel_mod->info) { 377 if (!panel_mod->info) {
391 dev_err(&pdev->dev, "could not get panel info\n"); 378 dev_err(&pdev->dev, "could not get panel info\n");
392 goto fail; 379 goto fail_timings;
393 } 380 }
394 381
395 mod->preferred_bpp = panel_mod->info->bpp; 382 mod->preferred_bpp = panel_mod->info->bpp;
@@ -400,13 +387,26 @@ static int panel_probe(struct platform_device *pdev)
400 387
401 return 0; 388 return 0;
402 389
403fail: 390fail_timings:
404 panel_destroy(mod); 391 display_timings_release(panel_mod->timings);
392
393fail_free:
394 kfree(panel_mod);
395 tilcdc_module_cleanup(mod);
405 return ret; 396 return ret;
406} 397}
407 398
408static int panel_remove(struct platform_device *pdev) 399static int panel_remove(struct platform_device *pdev)
409{ 400{
401 struct tilcdc_module *mod = dev_get_platdata(&pdev->dev);
402 struct panel_module *panel_mod = to_panel_module(mod);
403
404 display_timings_release(panel_mod->timings);
405
406 tilcdc_module_cleanup(mod);
407 kfree(panel_mod->info);
408 kfree(panel_mod);
409
410 return 0; 410 return 0;
411} 411}
412 412
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_slave.c b/drivers/gpu/drm/tilcdc/tilcdc_slave.c
index a5a22454acad..f02cb7c02f7f 100644
--- a/drivers/gpu/drm/tilcdc/tilcdc_slave.c
+++ b/drivers/gpu/drm/tilcdc/tilcdc_slave.c
@@ -296,17 +296,8 @@ static int slave_modeset_init(struct tilcdc_module *mod, struct drm_device *dev)
296 return 0; 296 return 0;
297} 297}
298 298
299static void slave_destroy(struct tilcdc_module *mod)
300{
301 struct slave_module *slave_mod = to_slave_module(mod);
302
303 tilcdc_module_cleanup(mod);
304 kfree(slave_mod);
305}
306
307static const struct tilcdc_module_ops slave_module_ops = { 299static const struct tilcdc_module_ops slave_module_ops = {
308 .modeset_init = slave_modeset_init, 300 .modeset_init = slave_modeset_init,
309 .destroy = slave_destroy,
310}; 301};
311 302
312/* 303/*
@@ -356,10 +347,13 @@ static int slave_probe(struct platform_device *pdev)
356 } 347 }
357 348
358 slave_mod = kzalloc(sizeof(*slave_mod), GFP_KERNEL); 349 slave_mod = kzalloc(sizeof(*slave_mod), GFP_KERNEL);
359 if (!slave_mod) 350 if (!slave_mod) {
360 return -ENOMEM; 351 ret = -ENOMEM;
352 goto fail_adapter;
353 }
361 354
362 mod = &slave_mod->base; 355 mod = &slave_mod->base;
356 pdev->dev.platform_data = mod;
363 357
364 mod->preferred_bpp = slave_info.bpp; 358 mod->preferred_bpp = slave_info.bpp;
365 359
@@ -374,10 +368,20 @@ static int slave_probe(struct platform_device *pdev)
374 tilcdc_slave_probedefer(false); 368 tilcdc_slave_probedefer(false);
375 369
376 return 0; 370 return 0;
371
372fail_adapter:
373 i2c_put_adapter(slavei2c);
374 return ret;
377} 375}
378 376
379static int slave_remove(struct platform_device *pdev) 377static int slave_remove(struct platform_device *pdev)
380{ 378{
379 struct tilcdc_module *mod = dev_get_platdata(&pdev->dev);
380 struct slave_module *slave_mod = to_slave_module(mod);
381
382 tilcdc_module_cleanup(mod);
383 kfree(slave_mod);
384
381 return 0; 385 return 0;
382} 386}
383 387
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_tfp410.c b/drivers/gpu/drm/tilcdc/tilcdc_tfp410.c
index 630360621bac..82fb5204565f 100644
--- a/drivers/gpu/drm/tilcdc/tilcdc_tfp410.c
+++ b/drivers/gpu/drm/tilcdc/tilcdc_tfp410.c
@@ -296,23 +296,8 @@ static int tfp410_modeset_init(struct tilcdc_module *mod, struct drm_device *dev
296 return 0; 296 return 0;
297} 297}
298 298
299static void tfp410_destroy(struct tilcdc_module *mod)
300{
301 struct tfp410_module *tfp410_mod = to_tfp410_module(mod);
302
303 if (tfp410_mod->i2c)
304 i2c_put_adapter(tfp410_mod->i2c);
305
306 if (!IS_ERR_VALUE(tfp410_mod->gpio))
307 gpio_free(tfp410_mod->gpio);
308
309 tilcdc_module_cleanup(mod);
310 kfree(tfp410_mod);
311}
312
313static const struct tilcdc_module_ops tfp410_module_ops = { 299static const struct tilcdc_module_ops tfp410_module_ops = {
314 .modeset_init = tfp410_modeset_init, 300 .modeset_init = tfp410_modeset_init,
315 .destroy = tfp410_destroy,
316}; 301};
317 302
318/* 303/*
@@ -342,6 +327,7 @@ static int tfp410_probe(struct platform_device *pdev)
342 return -ENOMEM; 327 return -ENOMEM;
343 328
344 mod = &tfp410_mod->base; 329 mod = &tfp410_mod->base;
330 pdev->dev.platform_data = mod;
345 331
346 tilcdc_module_init(mod, "tfp410", &tfp410_module_ops); 332 tilcdc_module_init(mod, "tfp410", &tfp410_module_ops);
347 333
@@ -365,6 +351,7 @@ static int tfp410_probe(struct platform_device *pdev)
365 tfp410_mod->i2c = of_find_i2c_adapter_by_node(i2c_node); 351 tfp410_mod->i2c = of_find_i2c_adapter_by_node(i2c_node);
366 if (!tfp410_mod->i2c) { 352 if (!tfp410_mod->i2c) {
367 dev_err(&pdev->dev, "could not get i2c\n"); 353 dev_err(&pdev->dev, "could not get i2c\n");
354 of_node_put(i2c_node);
368 goto fail; 355 goto fail;
369 } 356 }
370 357
@@ -378,19 +365,32 @@ static int tfp410_probe(struct platform_device *pdev)
378 ret = gpio_request(tfp410_mod->gpio, "DVI_PDn"); 365 ret = gpio_request(tfp410_mod->gpio, "DVI_PDn");
379 if (ret) { 366 if (ret) {
380 dev_err(&pdev->dev, "could not get DVI_PDn gpio\n"); 367 dev_err(&pdev->dev, "could not get DVI_PDn gpio\n");
381 goto fail; 368 goto fail_adapter;
382 } 369 }
383 } 370 }
384 371
385 return 0; 372 return 0;
386 373
374fail_adapter:
375 i2c_put_adapter(tfp410_mod->i2c);
376
387fail: 377fail:
388 tfp410_destroy(mod); 378 kfree(tfp410_mod);
379 tilcdc_module_cleanup(mod);
389 return ret; 380 return ret;
390} 381}
391 382
392static int tfp410_remove(struct platform_device *pdev) 383static int tfp410_remove(struct platform_device *pdev)
393{ 384{
385 struct tilcdc_module *mod = dev_get_platdata(&pdev->dev);
386 struct tfp410_module *tfp410_mod = to_tfp410_module(mod);
387
388 i2c_put_adapter(tfp410_mod->i2c);
389 gpio_free(tfp410_mod->gpio);
390
391 tilcdc_module_cleanup(mod);
392 kfree(tfp410_mod);
393
394 return 0; 394 return 0;
395} 395}
396 396