ht16k33.c 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * HT16K33 driver
  4. *
  5. * Author: Robin van der Gracht <robin@protonic.nl>
  6. *
  7. * Copyright: (C) 2016 Protonic Holland.
  8. * Copyright (C) 2021 Glider bv
  9. */
  10. #include <linux/kernel.h>
  11. #include <linux/module.h>
  12. #include <linux/interrupt.h>
  13. #include <linux/i2c.h>
  14. #include <linux/property.h>
  15. #include <linux/fb.h>
  16. #include <linux/backlight.h>
  17. #include <linux/container_of.h>
  18. #include <linux/input.h>
  19. #include <linux/input/matrix_keypad.h>
  20. #include <linux/leds.h>
  21. #include <linux/workqueue.h>
  22. #include <linux/mm.h>
  23. #include <linux/map_to_7segment.h>
  24. #include <linux/map_to_14segment.h>
  25. #include <linux/unaligned.h>
  26. #include "line-display.h"
  27. /* Registers */
  28. #define REG_SYSTEM_SETUP 0x20
  29. #define REG_SYSTEM_SETUP_OSC_ON BIT(0)
  30. #define REG_DISPLAY_SETUP 0x80
  31. #define REG_DISPLAY_SETUP_ON BIT(0)
  32. #define REG_DISPLAY_SETUP_BLINK_OFF (0 << 1)
  33. #define REG_DISPLAY_SETUP_BLINK_2HZ (1 << 1)
  34. #define REG_DISPLAY_SETUP_BLINK_1HZ (2 << 1)
  35. #define REG_DISPLAY_SETUP_BLINK_0HZ5 (3 << 1)
  36. #define REG_ROWINT_SET 0xA0
  37. #define REG_ROWINT_SET_INT_EN BIT(0)
  38. #define REG_ROWINT_SET_INT_ACT_HIGH BIT(1)
  39. #define REG_BRIGHTNESS 0xE0
  40. /* Defines */
  41. #define DRIVER_NAME "ht16k33"
  42. #define MIN_BRIGHTNESS 0x1
  43. #define MAX_BRIGHTNESS 0x10
  44. #define HT16K33_MATRIX_LED_MAX_COLS 8
  45. #define HT16K33_MATRIX_LED_MAX_ROWS 16
  46. #define HT16K33_MATRIX_KEYPAD_MAX_COLS 3
  47. #define HT16K33_MATRIX_KEYPAD_MAX_ROWS 12
  48. #define BYTES_PER_ROW (HT16K33_MATRIX_LED_MAX_ROWS / 8)
  49. #define HT16K33_FB_SIZE (HT16K33_MATRIX_LED_MAX_COLS * BYTES_PER_ROW)
  50. enum display_type {
  51. DISP_MATRIX = 0,
  52. DISP_QUAD_7SEG,
  53. DISP_QUAD_14SEG,
  54. };
  55. struct ht16k33_keypad {
  56. struct i2c_client *client;
  57. struct input_dev *dev;
  58. uint32_t cols;
  59. uint32_t rows;
  60. uint32_t row_shift;
  61. uint32_t debounce_ms;
  62. uint16_t last_key_state[HT16K33_MATRIX_KEYPAD_MAX_COLS];
  63. wait_queue_head_t wait;
  64. bool stopped;
  65. };
  66. struct ht16k33_fbdev {
  67. struct fb_info *info;
  68. uint32_t refresh_rate;
  69. uint8_t *buffer;
  70. uint8_t *cache;
  71. };
  72. struct ht16k33_priv {
  73. struct i2c_client *client;
  74. struct delayed_work work;
  75. struct led_classdev led;
  76. struct ht16k33_keypad keypad;
  77. union {
  78. struct ht16k33_fbdev fbdev;
  79. struct linedisp linedisp;
  80. };
  81. enum display_type type;
  82. uint8_t blink;
  83. };
  84. #define ht16k33_work_to_priv(p) \
  85. container_of(p, struct ht16k33_priv, work.work)
  86. #define ht16k33_led_to_priv(p) \
  87. container_of(p, struct ht16k33_priv, led)
  88. #define ht16k33_linedisp_to_priv(p) \
  89. container_of(p, struct ht16k33_priv, linedisp)
  90. static const struct fb_fix_screeninfo ht16k33_fb_fix = {
  91. .id = DRIVER_NAME,
  92. .type = FB_TYPE_PACKED_PIXELS,
  93. .visual = FB_VISUAL_MONO10,
  94. .xpanstep = 0,
  95. .ypanstep = 0,
  96. .ywrapstep = 0,
  97. .line_length = HT16K33_MATRIX_LED_MAX_ROWS,
  98. .accel = FB_ACCEL_NONE,
  99. };
  100. static const struct fb_var_screeninfo ht16k33_fb_var = {
  101. .xres = HT16K33_MATRIX_LED_MAX_ROWS,
  102. .yres = HT16K33_MATRIX_LED_MAX_COLS,
  103. .xres_virtual = HT16K33_MATRIX_LED_MAX_ROWS,
  104. .yres_virtual = HT16K33_MATRIX_LED_MAX_COLS,
  105. .bits_per_pixel = 1,
  106. .red = { 0, 1, 0 },
  107. .green = { 0, 1, 0 },
  108. .blue = { 0, 1, 0 },
  109. .left_margin = 0,
  110. .right_margin = 0,
  111. .upper_margin = 0,
  112. .lower_margin = 0,
  113. .vmode = FB_VMODE_NONINTERLACED,
  114. };
  115. static int ht16k33_display_on(struct ht16k33_priv *priv)
  116. {
  117. uint8_t data = REG_DISPLAY_SETUP | REG_DISPLAY_SETUP_ON | priv->blink;
  118. return i2c_smbus_write_byte(priv->client, data);
  119. }
  120. static int ht16k33_display_off(struct ht16k33_priv *priv)
  121. {
  122. return i2c_smbus_write_byte(priv->client, REG_DISPLAY_SETUP);
  123. }
  124. static int ht16k33_brightness_set(struct ht16k33_priv *priv,
  125. unsigned int brightness)
  126. {
  127. int err;
  128. if (brightness == 0) {
  129. priv->blink = REG_DISPLAY_SETUP_BLINK_OFF;
  130. return ht16k33_display_off(priv);
  131. }
  132. err = ht16k33_display_on(priv);
  133. if (err)
  134. return err;
  135. return i2c_smbus_write_byte(priv->client,
  136. REG_BRIGHTNESS | (brightness - 1));
  137. }
  138. static int ht16k33_brightness_set_blocking(struct led_classdev *led_cdev,
  139. enum led_brightness brightness)
  140. {
  141. struct ht16k33_priv *priv = ht16k33_led_to_priv(led_cdev);
  142. return ht16k33_brightness_set(priv, brightness);
  143. }
  144. static int ht16k33_blink_set(struct led_classdev *led_cdev,
  145. unsigned long *delay_on, unsigned long *delay_off)
  146. {
  147. struct ht16k33_priv *priv = ht16k33_led_to_priv(led_cdev);
  148. unsigned int delay;
  149. uint8_t blink;
  150. int err;
  151. if (!*delay_on && !*delay_off) {
  152. blink = REG_DISPLAY_SETUP_BLINK_1HZ;
  153. delay = 1000;
  154. } else if (*delay_on <= 750) {
  155. blink = REG_DISPLAY_SETUP_BLINK_2HZ;
  156. delay = 500;
  157. } else if (*delay_on <= 1500) {
  158. blink = REG_DISPLAY_SETUP_BLINK_1HZ;
  159. delay = 1000;
  160. } else {
  161. blink = REG_DISPLAY_SETUP_BLINK_0HZ5;
  162. delay = 2000;
  163. }
  164. err = i2c_smbus_write_byte(priv->client,
  165. REG_DISPLAY_SETUP | REG_DISPLAY_SETUP_ON |
  166. blink);
  167. if (err)
  168. return err;
  169. priv->blink = blink;
  170. *delay_on = *delay_off = delay;
  171. return 0;
  172. }
  173. static void ht16k33_fb_queue(struct ht16k33_priv *priv)
  174. {
  175. struct ht16k33_fbdev *fbdev = &priv->fbdev;
  176. schedule_delayed_work(&priv->work, HZ / fbdev->refresh_rate);
  177. }
  178. /*
  179. * This gets the fb data from cache and copies it to ht16k33 display RAM
  180. */
  181. static void ht16k33_fb_update(struct work_struct *work)
  182. {
  183. struct ht16k33_priv *priv = ht16k33_work_to_priv(work);
  184. struct ht16k33_fbdev *fbdev = &priv->fbdev;
  185. uint8_t *p1, *p2;
  186. int len, pos = 0, first = -1;
  187. p1 = fbdev->cache;
  188. p2 = fbdev->buffer;
  189. /* Search for the first byte with changes */
  190. while (pos < HT16K33_FB_SIZE && first < 0) {
  191. if (*(p1++) - *(p2++))
  192. first = pos;
  193. pos++;
  194. }
  195. /* No changes found */
  196. if (first < 0)
  197. goto requeue;
  198. len = HT16K33_FB_SIZE - first;
  199. p1 = fbdev->cache + HT16K33_FB_SIZE - 1;
  200. p2 = fbdev->buffer + HT16K33_FB_SIZE - 1;
  201. /* Determine i2c transfer length */
  202. while (len > 1) {
  203. if (*(p1--) - *(p2--))
  204. break;
  205. len--;
  206. }
  207. p1 = fbdev->cache + first;
  208. p2 = fbdev->buffer + first;
  209. if (!i2c_smbus_write_i2c_block_data(priv->client, first, len, p2))
  210. memcpy(p1, p2, len);
  211. requeue:
  212. ht16k33_fb_queue(priv);
  213. }
  214. static int ht16k33_initialize(struct ht16k33_priv *priv)
  215. {
  216. uint8_t data[HT16K33_FB_SIZE];
  217. uint8_t byte;
  218. int err;
  219. /* Clear RAM (8 * 16 bits) */
  220. memset(data, 0, sizeof(data));
  221. err = i2c_smbus_write_block_data(priv->client, 0, sizeof(data), data);
  222. if (err)
  223. return err;
  224. /* Turn on internal oscillator */
  225. byte = REG_SYSTEM_SETUP_OSC_ON | REG_SYSTEM_SETUP;
  226. err = i2c_smbus_write_byte(priv->client, byte);
  227. if (err)
  228. return err;
  229. /* Configure INT pin */
  230. byte = REG_ROWINT_SET | REG_ROWINT_SET_INT_ACT_HIGH;
  231. if (priv->client->irq > 0)
  232. byte |= REG_ROWINT_SET_INT_EN;
  233. return i2c_smbus_write_byte(priv->client, byte);
  234. }
  235. static int ht16k33_bl_update_status(struct backlight_device *bl)
  236. {
  237. const int brightness = backlight_get_brightness(bl);
  238. struct ht16k33_priv *priv = bl_get_data(bl);
  239. return ht16k33_brightness_set(priv, brightness);
  240. }
  241. static const struct backlight_ops ht16k33_bl_ops = {
  242. .update_status = ht16k33_bl_update_status,
  243. };
  244. /*
  245. * Blank events will be passed to the actual device handling the backlight when
  246. * we return zero here.
  247. */
  248. static int ht16k33_blank(int blank, struct fb_info *info)
  249. {
  250. return 0;
  251. }
  252. static int ht16k33_mmap(struct fb_info *info, struct vm_area_struct *vma)
  253. {
  254. struct ht16k33_priv *priv = info->par;
  255. struct page *pages = virt_to_page(priv->fbdev.buffer);
  256. vma->vm_page_prot = pgprot_decrypted(vma->vm_page_prot);
  257. return vm_map_pages_zero(vma, &pages, 1);
  258. }
  259. static const struct fb_ops ht16k33_fb_ops = {
  260. .owner = THIS_MODULE,
  261. __FB_DEFAULT_SYSMEM_OPS_RDWR,
  262. .fb_blank = ht16k33_blank,
  263. __FB_DEFAULT_SYSMEM_OPS_DRAW,
  264. .fb_mmap = ht16k33_mmap,
  265. };
  266. /*
  267. * This gets the keys from keypad and reports it to input subsystem.
  268. * Returns true if a key is pressed.
  269. */
  270. static bool ht16k33_keypad_scan(struct ht16k33_keypad *keypad)
  271. {
  272. const unsigned short *keycodes = keypad->dev->keycode;
  273. u16 new_state[HT16K33_MATRIX_KEYPAD_MAX_COLS];
  274. __le16 data[HT16K33_MATRIX_KEYPAD_MAX_COLS];
  275. unsigned long bits_changed;
  276. int row, col, code;
  277. int rc;
  278. bool pressed = false;
  279. rc = i2c_smbus_read_i2c_block_data(keypad->client, 0x40,
  280. sizeof(data), (u8 *)data);
  281. if (rc != sizeof(data)) {
  282. dev_err(&keypad->client->dev,
  283. "Failed to read key data, rc=%d\n", rc);
  284. return false;
  285. }
  286. for (col = 0; col < keypad->cols; col++) {
  287. new_state[col] = le16_to_cpu(data[col]);
  288. if (new_state[col])
  289. pressed = true;
  290. bits_changed = keypad->last_key_state[col] ^ new_state[col];
  291. for_each_set_bit(row, &bits_changed, BITS_PER_LONG) {
  292. code = MATRIX_SCAN_CODE(row, col, keypad->row_shift);
  293. input_event(keypad->dev, EV_MSC, MSC_SCAN, code);
  294. input_report_key(keypad->dev, keycodes[code],
  295. new_state[col] & BIT(row));
  296. }
  297. }
  298. input_sync(keypad->dev);
  299. memcpy(keypad->last_key_state, new_state, sizeof(u16) * keypad->cols);
  300. return pressed;
  301. }
  302. static irqreturn_t ht16k33_keypad_irq_thread(int irq, void *dev)
  303. {
  304. struct ht16k33_keypad *keypad = dev;
  305. do {
  306. wait_event_timeout(keypad->wait, keypad->stopped,
  307. msecs_to_jiffies(keypad->debounce_ms));
  308. if (keypad->stopped)
  309. break;
  310. } while (ht16k33_keypad_scan(keypad));
  311. return IRQ_HANDLED;
  312. }
  313. static int ht16k33_keypad_start(struct input_dev *dev)
  314. {
  315. struct ht16k33_keypad *keypad = input_get_drvdata(dev);
  316. keypad->stopped = false;
  317. mb();
  318. enable_irq(keypad->client->irq);
  319. return 0;
  320. }
  321. static void ht16k33_keypad_stop(struct input_dev *dev)
  322. {
  323. struct ht16k33_keypad *keypad = input_get_drvdata(dev);
  324. keypad->stopped = true;
  325. mb();
  326. wake_up(&keypad->wait);
  327. disable_irq(keypad->client->irq);
  328. }
  329. static void ht16k33_seg7_update(struct work_struct *work)
  330. {
  331. struct ht16k33_priv *priv = ht16k33_work_to_priv(work);
  332. struct linedisp_map *map = priv->linedisp.map;
  333. char *s = priv->linedisp.buf;
  334. uint8_t buf[9];
  335. buf[0] = map_to_seg7(&map->map.seg7, *s++);
  336. buf[1] = 0;
  337. buf[2] = map_to_seg7(&map->map.seg7, *s++);
  338. buf[3] = 0;
  339. buf[4] = 0;
  340. buf[5] = 0;
  341. buf[6] = map_to_seg7(&map->map.seg7, *s++);
  342. buf[7] = 0;
  343. buf[8] = map_to_seg7(&map->map.seg7, *s++);
  344. i2c_smbus_write_i2c_block_data(priv->client, 0, ARRAY_SIZE(buf), buf);
  345. }
  346. static void ht16k33_seg14_update(struct work_struct *work)
  347. {
  348. struct ht16k33_priv *priv = ht16k33_work_to_priv(work);
  349. struct linedisp_map *map = priv->linedisp.map;
  350. char *s = priv->linedisp.buf;
  351. uint8_t buf[8];
  352. put_unaligned_le16(map_to_seg14(&map->map.seg14, *s++), buf + 0);
  353. put_unaligned_le16(map_to_seg14(&map->map.seg14, *s++), buf + 2);
  354. put_unaligned_le16(map_to_seg14(&map->map.seg14, *s++), buf + 4);
  355. put_unaligned_le16(map_to_seg14(&map->map.seg14, *s++), buf + 6);
  356. i2c_smbus_write_i2c_block_data(priv->client, 0, ARRAY_SIZE(buf), buf);
  357. }
  358. static int ht16k33_linedisp_get_map_type(struct linedisp *linedisp)
  359. {
  360. struct ht16k33_priv *priv = ht16k33_linedisp_to_priv(linedisp);
  361. switch (priv->type) {
  362. case DISP_QUAD_7SEG:
  363. INIT_DELAYED_WORK(&priv->work, ht16k33_seg7_update);
  364. return LINEDISP_MAP_SEG7;
  365. case DISP_QUAD_14SEG:
  366. INIT_DELAYED_WORK(&priv->work, ht16k33_seg14_update);
  367. return LINEDISP_MAP_SEG14;
  368. default:
  369. return -EINVAL;
  370. }
  371. }
  372. static void ht16k33_linedisp_update(struct linedisp *linedisp)
  373. {
  374. struct ht16k33_priv *priv = ht16k33_linedisp_to_priv(linedisp);
  375. schedule_delayed_work(&priv->work, 0);
  376. }
  377. static const struct linedisp_ops ht16k33_linedisp_ops = {
  378. .get_map_type = ht16k33_linedisp_get_map_type,
  379. .update = ht16k33_linedisp_update,
  380. };
  381. static int ht16k33_led_probe(struct device *dev, struct led_classdev *led,
  382. unsigned int brightness)
  383. {
  384. struct led_init_data init_data = {};
  385. int err;
  386. /* The LED is optional */
  387. init_data.fwnode = device_get_named_child_node(dev, "led");
  388. if (!init_data.fwnode)
  389. return 0;
  390. init_data.devicename = "auxdisplay";
  391. init_data.devname_mandatory = true;
  392. led->brightness_set_blocking = ht16k33_brightness_set_blocking;
  393. led->blink_set = ht16k33_blink_set;
  394. led->flags = LED_CORE_SUSPENDRESUME;
  395. led->brightness = brightness;
  396. led->max_brightness = MAX_BRIGHTNESS;
  397. err = devm_led_classdev_register_ext(dev, led, &init_data);
  398. fwnode_handle_put(init_data.fwnode);
  399. if (err)
  400. dev_err(dev, "Failed to register LED\n");
  401. return err;
  402. }
  403. static int ht16k33_keypad_probe(struct i2c_client *client,
  404. struct ht16k33_keypad *keypad)
  405. {
  406. struct device *dev = &client->dev;
  407. u32 rows = HT16K33_MATRIX_KEYPAD_MAX_ROWS;
  408. u32 cols = HT16K33_MATRIX_KEYPAD_MAX_COLS;
  409. int err;
  410. keypad->client = client;
  411. init_waitqueue_head(&keypad->wait);
  412. keypad->dev = devm_input_allocate_device(dev);
  413. if (!keypad->dev)
  414. return -ENOMEM;
  415. input_set_drvdata(keypad->dev, keypad);
  416. keypad->dev->name = DRIVER_NAME"-keypad";
  417. keypad->dev->id.bustype = BUS_I2C;
  418. keypad->dev->open = ht16k33_keypad_start;
  419. keypad->dev->close = ht16k33_keypad_stop;
  420. if (!device_property_read_bool(dev, "linux,no-autorepeat"))
  421. __set_bit(EV_REP, keypad->dev->evbit);
  422. err = device_property_read_u32(dev, "debounce-delay-ms",
  423. &keypad->debounce_ms);
  424. if (err) {
  425. dev_err(dev, "key debounce delay not specified\n");
  426. return err;
  427. }
  428. err = matrix_keypad_parse_properties(dev, &rows, &cols);
  429. if (err)
  430. return err;
  431. if (rows > HT16K33_MATRIX_KEYPAD_MAX_ROWS ||
  432. cols > HT16K33_MATRIX_KEYPAD_MAX_COLS) {
  433. dev_err(dev, "%u rows or %u cols out of range in DT\n", rows,
  434. cols);
  435. return -ERANGE;
  436. }
  437. keypad->rows = rows;
  438. keypad->cols = cols;
  439. keypad->row_shift = get_count_order(cols);
  440. err = matrix_keypad_build_keymap(NULL, NULL, rows, cols, NULL,
  441. keypad->dev);
  442. if (err) {
  443. dev_err(dev, "failed to build keymap\n");
  444. return err;
  445. }
  446. err = devm_request_threaded_irq(dev, client->irq, NULL,
  447. ht16k33_keypad_irq_thread,
  448. IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
  449. DRIVER_NAME, keypad);
  450. if (err) {
  451. dev_err(dev, "irq request failed %d, error %d\n", client->irq,
  452. err);
  453. return err;
  454. }
  455. ht16k33_keypad_stop(keypad->dev);
  456. return input_register_device(keypad->dev);
  457. }
  458. static int ht16k33_fbdev_probe(struct device *dev, struct ht16k33_priv *priv,
  459. uint32_t brightness)
  460. {
  461. struct ht16k33_fbdev *fbdev = &priv->fbdev;
  462. struct backlight_device *bl = NULL;
  463. int err;
  464. if (priv->led.dev) {
  465. err = ht16k33_brightness_set(priv, brightness);
  466. if (err)
  467. return err;
  468. } else {
  469. /* backwards compatibility with DT lacking an led subnode */
  470. struct backlight_properties bl_props;
  471. memset(&bl_props, 0, sizeof(struct backlight_properties));
  472. bl_props.type = BACKLIGHT_RAW;
  473. bl_props.max_brightness = MAX_BRIGHTNESS;
  474. bl = devm_backlight_device_register(dev, DRIVER_NAME"-bl", dev,
  475. priv, &ht16k33_bl_ops,
  476. &bl_props);
  477. if (IS_ERR(bl)) {
  478. dev_err(dev, "failed to register backlight\n");
  479. return PTR_ERR(bl);
  480. }
  481. bl->props.brightness = brightness;
  482. ht16k33_bl_update_status(bl);
  483. }
  484. /* Framebuffer (2 bytes per column) */
  485. BUILD_BUG_ON(PAGE_SIZE < HT16K33_FB_SIZE);
  486. fbdev->buffer = (unsigned char *) get_zeroed_page(GFP_KERNEL);
  487. if (!fbdev->buffer)
  488. return -ENOMEM;
  489. fbdev->cache = devm_kmalloc(dev, HT16K33_FB_SIZE, GFP_KERNEL);
  490. if (!fbdev->cache) {
  491. err = -ENOMEM;
  492. goto err_fbdev_buffer;
  493. }
  494. fbdev->info = framebuffer_alloc(0, dev);
  495. if (!fbdev->info) {
  496. err = -ENOMEM;
  497. goto err_fbdev_buffer;
  498. }
  499. err = device_property_read_u32(dev, "refresh-rate-hz",
  500. &fbdev->refresh_rate);
  501. if (err) {
  502. dev_err(dev, "refresh rate not specified\n");
  503. goto err_fbdev_info;
  504. }
  505. fb_bl_default_curve(fbdev->info, 0, MIN_BRIGHTNESS, MAX_BRIGHTNESS);
  506. INIT_DELAYED_WORK(&priv->work, ht16k33_fb_update);
  507. fbdev->info->fbops = &ht16k33_fb_ops;
  508. fbdev->info->flags |= FBINFO_VIRTFB;
  509. fbdev->info->screen_buffer = fbdev->buffer;
  510. fbdev->info->screen_size = HT16K33_FB_SIZE;
  511. fbdev->info->fix = ht16k33_fb_fix;
  512. fbdev->info->var = ht16k33_fb_var;
  513. fbdev->info->bl_dev = bl;
  514. fbdev->info->pseudo_palette = NULL;
  515. fbdev->info->par = priv;
  516. err = register_framebuffer(fbdev->info);
  517. if (err)
  518. goto err_fbdev_info;
  519. ht16k33_fb_queue(priv);
  520. return 0;
  521. err_fbdev_info:
  522. framebuffer_release(fbdev->info);
  523. err_fbdev_buffer:
  524. free_page((unsigned long) fbdev->buffer);
  525. return err;
  526. }
  527. static int ht16k33_seg_probe(struct device *dev, struct ht16k33_priv *priv,
  528. uint32_t brightness)
  529. {
  530. struct linedisp *linedisp = &priv->linedisp;
  531. int err;
  532. err = ht16k33_brightness_set(priv, brightness);
  533. if (err)
  534. return err;
  535. return linedisp_register(linedisp, dev, 4, &ht16k33_linedisp_ops);
  536. }
  537. static int ht16k33_probe(struct i2c_client *client)
  538. {
  539. struct device *dev = &client->dev;
  540. struct ht16k33_priv *priv;
  541. uint32_t dft_brightness;
  542. int err;
  543. if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
  544. dev_err(dev, "i2c_check_functionality error\n");
  545. return -EIO;
  546. }
  547. priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
  548. if (!priv)
  549. return -ENOMEM;
  550. priv->client = client;
  551. priv->type = (uintptr_t)i2c_get_match_data(client);
  552. i2c_set_clientdata(client, priv);
  553. err = ht16k33_initialize(priv);
  554. if (err)
  555. return err;
  556. err = device_property_read_u32(dev, "default-brightness-level",
  557. &dft_brightness);
  558. if (err) {
  559. dft_brightness = MAX_BRIGHTNESS;
  560. } else if (dft_brightness > MAX_BRIGHTNESS) {
  561. dev_warn(dev,
  562. "invalid default brightness level: %u, using %u\n",
  563. dft_brightness, MAX_BRIGHTNESS);
  564. dft_brightness = MAX_BRIGHTNESS;
  565. }
  566. /* LED */
  567. err = ht16k33_led_probe(dev, &priv->led, dft_brightness);
  568. if (err)
  569. return err;
  570. /* Keypad */
  571. if (client->irq > 0) {
  572. err = ht16k33_keypad_probe(client, &priv->keypad);
  573. if (err)
  574. return err;
  575. }
  576. switch (priv->type) {
  577. case DISP_MATRIX:
  578. /* Frame Buffer Display */
  579. err = ht16k33_fbdev_probe(dev, priv, dft_brightness);
  580. break;
  581. case DISP_QUAD_7SEG:
  582. case DISP_QUAD_14SEG:
  583. /* Segment Display */
  584. err = ht16k33_seg_probe(dev, priv, dft_brightness);
  585. break;
  586. default:
  587. return -EINVAL;
  588. }
  589. return err;
  590. }
  591. static void ht16k33_remove(struct i2c_client *client)
  592. {
  593. struct ht16k33_priv *priv = i2c_get_clientdata(client);
  594. struct ht16k33_fbdev *fbdev = &priv->fbdev;
  595. cancel_delayed_work_sync(&priv->work);
  596. switch (priv->type) {
  597. case DISP_MATRIX:
  598. unregister_framebuffer(fbdev->info);
  599. framebuffer_release(fbdev->info);
  600. free_page((unsigned long)fbdev->buffer);
  601. break;
  602. case DISP_QUAD_7SEG:
  603. case DISP_QUAD_14SEG:
  604. linedisp_unregister(&priv->linedisp);
  605. break;
  606. default:
  607. break;
  608. }
  609. }
  610. static const struct i2c_device_id ht16k33_i2c_match[] = {
  611. { "3108", DISP_QUAD_7SEG },
  612. { "3130", DISP_QUAD_14SEG },
  613. { "ht16k33", DISP_MATRIX },
  614. { }
  615. };
  616. MODULE_DEVICE_TABLE(i2c, ht16k33_i2c_match);
  617. static const struct of_device_id ht16k33_of_match[] = {
  618. {
  619. /* 0.56" 4-Digit 7-Segment FeatherWing Display (Red) */
  620. .compatible = "adafruit,3108", .data = (void *)DISP_QUAD_7SEG,
  621. }, {
  622. /* 0.54" Quad Alphanumeric FeatherWing Display (Red) */
  623. .compatible = "adafruit,3130", .data = (void *)DISP_QUAD_14SEG,
  624. }, {
  625. /* Generic, assumed Dot-Matrix Display */
  626. .compatible = "holtek,ht16k33", .data = (void *)DISP_MATRIX,
  627. },
  628. { }
  629. };
  630. MODULE_DEVICE_TABLE(of, ht16k33_of_match);
  631. static struct i2c_driver ht16k33_driver = {
  632. .probe = ht16k33_probe,
  633. .remove = ht16k33_remove,
  634. .driver = {
  635. .name = DRIVER_NAME,
  636. .of_match_table = ht16k33_of_match,
  637. },
  638. .id_table = ht16k33_i2c_match,
  639. };
  640. module_i2c_driver(ht16k33_driver);
  641. MODULE_DESCRIPTION("Holtek HT16K33 driver");
  642. MODULE_LICENSE("GPL");
  643. MODULE_IMPORT_NS("LINEDISP");
  644. MODULE_AUTHOR("Robin van der Gracht <robin@protonic.nl>");