hd44780.c (66ce7d5c1e124b497f45aead50df1dc3c2873382) | hd44780.c (718e05ed92ecac0d9d3954bcc8064527c3ce7565) |
---|---|
1// SPDX-License-Identifier: GPL-2.0+ 2/* 3 * HD44780 Character LCD driver for Linux 4 * 5 * Copyright (C) 2000-2008, Willy Tarreau <w@1wt.eu> 6 * Copyright (C) 2016-2017 Glider bvba 7 */ 8 9#include <linux/delay.h> 10#include <linux/gpio/consumer.h> 11#include <linux/module.h> 12#include <linux/mod_devicetable.h> 13#include <linux/platform_device.h> 14#include <linux/property.h> 15#include <linux/slab.h> 16 17#include "charlcd.h" | 1// SPDX-License-Identifier: GPL-2.0+ 2/* 3 * HD44780 Character LCD driver for Linux 4 * 5 * Copyright (C) 2000-2008, Willy Tarreau <w@1wt.eu> 6 * Copyright (C) 2016-2017 Glider bvba 7 */ 8 9#include <linux/delay.h> 10#include <linux/gpio/consumer.h> 11#include <linux/module.h> 12#include <linux/mod_devicetable.h> 13#include <linux/platform_device.h> 14#include <linux/property.h> 15#include <linux/slab.h> 16 17#include "charlcd.h" |
18#include "hd44780_common.h" |
|
18 19enum hd44780_pin { 20 /* Order does matter due to writing to GPIO array subsets! */ 21 PIN_DATA0, /* Optional */ 22 PIN_DATA1, /* Optional */ 23 PIN_DATA2, /* Optional */ 24 PIN_DATA3, /* Optional */ 25 PIN_DATA4, --- 148 unchanged lines hidden (view full) --- 174 .backlight = hd44780_backlight, 175}; 176 177static int hd44780_probe(struct platform_device *pdev) 178{ 179 struct device *dev = &pdev->dev; 180 unsigned int i, base; 181 struct charlcd *lcd; | 19 20enum hd44780_pin { 21 /* Order does matter due to writing to GPIO array subsets! */ 22 PIN_DATA0, /* Optional */ 23 PIN_DATA1, /* Optional */ 24 PIN_DATA2, /* Optional */ 25 PIN_DATA3, /* Optional */ 26 PIN_DATA4, --- 148 unchanged lines hidden (view full) --- 175 .backlight = hd44780_backlight, 176}; 177 178static int hd44780_probe(struct platform_device *pdev) 179{ 180 struct device *dev = &pdev->dev; 181 unsigned int i, base; 182 struct charlcd *lcd; |
183 struct hd44780_common *hdc; |
|
182 struct hd44780 *hd; | 184 struct hd44780 *hd; |
183 int ifwidth, ret; | 185 int ifwidth, ret = -ENOMEM; |
184 185 /* Required pins */ 186 ifwidth = gpiod_count(dev, "data"); 187 if (ifwidth < 0) 188 return ifwidth; 189 190 switch (ifwidth) { 191 case 4: 192 base = PIN_DATA4; 193 break; 194 case 8: 195 base = PIN_DATA0; 196 break; 197 default: 198 return -EINVAL; 199 } 200 | 186 187 /* Required pins */ 188 ifwidth = gpiod_count(dev, "data"); 189 if (ifwidth < 0) 190 return ifwidth; 191 192 switch (ifwidth) { 193 case 4: 194 base = PIN_DATA4; 195 break; 196 case 8: 197 base = PIN_DATA0; 198 break; 199 default: 200 return -EINVAL; 201 } 202 |
203 hdc = hd44780_common_alloc(); 204 if (!hdc) 205 return -ENOMEM; 206 |
|
201 lcd = charlcd_alloc(sizeof(struct hd44780)); 202 if (!lcd) | 207 lcd = charlcd_alloc(sizeof(struct hd44780)); 208 if (!lcd) |
203 return -ENOMEM; | 209 goto fail1; |
204 | 210 |
205 hd = lcd->drvdata; | 211 hd = kzalloc(sizeof(struct hd44780), GFP_KERNEL); 212 if (!hd) 213 goto fail2; |
206 | 214 |
215 hdc->hd44780 = hd; 216 lcd->drvdata = hdc; |
|
207 for (i = 0; i < ifwidth; i++) { 208 hd->pins[base + i] = devm_gpiod_get_index(dev, "data", i, 209 GPIOD_OUT_LOW); 210 if (IS_ERR(hd->pins[base + i])) { 211 ret = PTR_ERR(hd->pins[base + i]); | 217 for (i = 0; i < ifwidth; i++) { 218 hd->pins[base + i] = devm_gpiod_get_index(dev, "data", i, 219 GPIOD_OUT_LOW); 220 if (IS_ERR(hd->pins[base + i])) { 221 ret = PTR_ERR(hd->pins[base + i]); |
212 goto fail; | 222 goto fail3; |
213 } 214 } 215 216 hd->pins[PIN_CTRL_E] = devm_gpiod_get(dev, "enable", GPIOD_OUT_LOW); 217 if (IS_ERR(hd->pins[PIN_CTRL_E])) { 218 ret = PTR_ERR(hd->pins[PIN_CTRL_E]); | 223 } 224 } 225 226 hd->pins[PIN_CTRL_E] = devm_gpiod_get(dev, "enable", GPIOD_OUT_LOW); 227 if (IS_ERR(hd->pins[PIN_CTRL_E])) { 228 ret = PTR_ERR(hd->pins[PIN_CTRL_E]); |
219 goto fail; | 229 goto fail3; |
220 } 221 222 hd->pins[PIN_CTRL_RS] = devm_gpiod_get(dev, "rs", GPIOD_OUT_HIGH); 223 if (IS_ERR(hd->pins[PIN_CTRL_RS])) { 224 ret = PTR_ERR(hd->pins[PIN_CTRL_RS]); | 230 } 231 232 hd->pins[PIN_CTRL_RS] = devm_gpiod_get(dev, "rs", GPIOD_OUT_HIGH); 233 if (IS_ERR(hd->pins[PIN_CTRL_RS])) { 234 ret = PTR_ERR(hd->pins[PIN_CTRL_RS]); |
225 goto fail; | 235 goto fail3; |
226 } 227 228 /* Optional pins */ 229 hd->pins[PIN_CTRL_RW] = devm_gpiod_get_optional(dev, "rw", 230 GPIOD_OUT_LOW); 231 if (IS_ERR(hd->pins[PIN_CTRL_RW])) { 232 ret = PTR_ERR(hd->pins[PIN_CTRL_RW]); | 236 } 237 238 /* Optional pins */ 239 hd->pins[PIN_CTRL_RW] = devm_gpiod_get_optional(dev, "rw", 240 GPIOD_OUT_LOW); 241 if (IS_ERR(hd->pins[PIN_CTRL_RW])) { 242 ret = PTR_ERR(hd->pins[PIN_CTRL_RW]); |
233 goto fail; | 243 goto fail3; |
234 } 235 236 hd->pins[PIN_CTRL_BL] = devm_gpiod_get_optional(dev, "backlight", 237 GPIOD_OUT_LOW); 238 if (IS_ERR(hd->pins[PIN_CTRL_BL])) { 239 ret = PTR_ERR(hd->pins[PIN_CTRL_BL]); | 244 } 245 246 hd->pins[PIN_CTRL_BL] = devm_gpiod_get_optional(dev, "backlight", 247 GPIOD_OUT_LOW); 248 if (IS_ERR(hd->pins[PIN_CTRL_BL])) { 249 ret = PTR_ERR(hd->pins[PIN_CTRL_BL]); |
240 goto fail; | 250 goto fail3; |
241 } 242 243 /* Required properties */ 244 ret = device_property_read_u32(dev, "display-height-chars", 245 &lcd->height); 246 if (ret) | 251 } 252 253 /* Required properties */ 254 ret = device_property_read_u32(dev, "display-height-chars", 255 &lcd->height); 256 if (ret) |
247 goto fail; | 257 goto fail3; |
248 ret = device_property_read_u32(dev, "display-width-chars", &lcd->width); 249 if (ret) | 258 ret = device_property_read_u32(dev, "display-width-chars", &lcd->width); 259 if (ret) |
250 goto fail; | 260 goto fail3; |
251 252 /* 253 * On displays with more than two rows, the internal buffer width is 254 * usually equal to the display width 255 */ 256 if (lcd->height > 2) 257 lcd->bwidth = lcd->width; 258 259 /* Optional properties */ 260 device_property_read_u32(dev, "internal-buffer-width", &lcd->bwidth); 261 262 lcd->ifwidth = ifwidth; 263 lcd->ops = ifwidth == 8 ? &hd44780_ops_gpio8 : &hd44780_ops_gpio4; 264 265 ret = charlcd_register(lcd); 266 if (ret) | 261 262 /* 263 * On displays with more than two rows, the internal buffer width is 264 * usually equal to the display width 265 */ 266 if (lcd->height > 2) 267 lcd->bwidth = lcd->width; 268 269 /* Optional properties */ 270 device_property_read_u32(dev, "internal-buffer-width", &lcd->bwidth); 271 272 lcd->ifwidth = ifwidth; 273 lcd->ops = ifwidth == 8 ? &hd44780_ops_gpio8 : &hd44780_ops_gpio4; 274 275 ret = charlcd_register(lcd); 276 if (ret) |
267 goto fail; | 277 goto fail3; |
268 269 platform_set_drvdata(pdev, lcd); 270 return 0; 271 | 278 279 platform_set_drvdata(pdev, lcd); 280 return 0; 281 |
272fail: 273 charlcd_free(lcd); | 282fail3: 283 kfree(hd); 284fail2: 285 kfree(lcd); 286fail1: 287 kfree(hdc); |
274 return ret; 275} 276 277static int hd44780_remove(struct platform_device *pdev) 278{ 279 struct charlcd *lcd = platform_get_drvdata(pdev); 280 | 288 return ret; 289} 290 291static int hd44780_remove(struct platform_device *pdev) 292{ 293 struct charlcd *lcd = platform_get_drvdata(pdev); 294 |
295 kfree(lcd->drvdata); |
|
281 charlcd_unregister(lcd); 282 | 296 charlcd_unregister(lcd); 297 |
283 charlcd_free(lcd); | 298 kfree(lcd); |
284 return 0; 285} 286 287static const struct of_device_id hd44780_of_match[] = { 288 { .compatible = "hit,hd44780" }, 289 { /* sentinel */ } 290}; 291MODULE_DEVICE_TABLE(of, hd44780_of_match); --- 14 unchanged lines hidden --- | 299 return 0; 300} 301 302static const struct of_device_id hd44780_of_match[] = { 303 { .compatible = "hit,hd44780" }, 304 { /* sentinel */ } 305}; 306MODULE_DEVICE_TABLE(of, hd44780_of_match); --- 14 unchanged lines hidden --- |