1 /* drivers/video/backlight/platform_lcd.c
3 * Copyright 2008 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
6 * Generic platform-device LCD power control interface.
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
14 #include <linux/module.h>
15 #include <linux/platform_device.h>
17 #include <linux/backlight.h>
18 #include <linux/lcd.h>
20 #include <linux/slab.h>
22 #include <video/platform_lcd.h>
26 struct lcd_device
*lcd
;
27 struct plat_lcd_data
*pdata
;
30 unsigned int suspended
:1;
33 static inline struct platform_lcd
*to_our_lcd(struct lcd_device
*lcd
)
35 return lcd_get_data(lcd
);
38 static int platform_lcd_get_power(struct lcd_device
*lcd
)
40 struct platform_lcd
*plcd
= to_our_lcd(lcd
);
45 static int platform_lcd_set_power(struct lcd_device
*lcd
, int power
)
47 struct platform_lcd
*plcd
= to_our_lcd(lcd
);
50 if (power
== FB_BLANK_POWERDOWN
|| plcd
->suspended
)
53 plcd
->pdata
->set_power(plcd
->pdata
, lcd_power
);
59 static int platform_lcd_match(struct lcd_device
*lcd
, struct fb_info
*info
)
61 struct platform_lcd
*plcd
= to_our_lcd(lcd
);
62 struct plat_lcd_data
*pdata
= plcd
->pdata
;
65 return pdata
->match_fb(pdata
, info
);
67 return plcd
->us
->parent
== info
->device
;
70 static struct lcd_ops platform_lcd_ops
= {
71 .get_power
= platform_lcd_get_power
,
72 .set_power
= platform_lcd_set_power
,
73 .check_fb
= platform_lcd_match
,
76 static int platform_lcd_probe(struct platform_device
*pdev
)
78 struct plat_lcd_data
*pdata
;
79 struct platform_lcd
*plcd
;
80 struct device
*dev
= &pdev
->dev
;
83 pdata
= dev_get_platdata(&pdev
->dev
);
85 dev_err(dev
, "no platform data supplied\n");
90 err
= pdata
->probe(pdata
);
95 plcd
= devm_kzalloc(&pdev
->dev
, sizeof(struct platform_lcd
),
98 dev_err(dev
, "no memory for state\n");
104 plcd
->lcd
= devm_lcd_device_register(&pdev
->dev
, dev_name(dev
), dev
,
105 plcd
, &platform_lcd_ops
);
106 if (IS_ERR(plcd
->lcd
)) {
107 dev_err(dev
, "cannot register lcd device\n");
108 return PTR_ERR(plcd
->lcd
);
111 platform_set_drvdata(pdev
, plcd
);
112 platform_lcd_set_power(plcd
->lcd
, FB_BLANK_NORMAL
);
117 #ifdef CONFIG_PM_SLEEP
118 static int platform_lcd_suspend(struct device
*dev
)
120 struct platform_lcd
*plcd
= dev_get_drvdata(dev
);
123 platform_lcd_set_power(plcd
->lcd
, plcd
->power
);
128 static int platform_lcd_resume(struct device
*dev
)
130 struct platform_lcd
*plcd
= dev_get_drvdata(dev
);
133 platform_lcd_set_power(plcd
->lcd
, plcd
->power
);
139 static SIMPLE_DEV_PM_OPS(platform_lcd_pm_ops
, platform_lcd_suspend
,
140 platform_lcd_resume
);
143 static const struct of_device_id platform_lcd_of_match
[] = {
144 { .compatible
= "platform-lcd" },
147 MODULE_DEVICE_TABLE(of
, platform_lcd_of_match
);
150 static struct platform_driver platform_lcd_driver
= {
152 .name
= "platform-lcd",
153 .owner
= THIS_MODULE
,
154 .pm
= &platform_lcd_pm_ops
,
155 .of_match_table
= of_match_ptr(platform_lcd_of_match
),
157 .probe
= platform_lcd_probe
,
160 module_platform_driver(platform_lcd_driver
);
162 MODULE_AUTHOR("Ben Dooks <ben-linux@fluff.org>");
163 MODULE_LICENSE("GPL v2");
164 MODULE_ALIAS("platform:platform-lcd");