xref: /linux/drivers/auxdisplay/ht16k33.c (revision 0e2b2a76278153d1ac312b0691cb65dabb9aef3e)
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 
11 #include <linux/kernel.h>
12 #include <linux/module.h>
13 #include <linux/interrupt.h>
14 #include <linux/i2c.h>
15 #include <linux/property.h>
16 #include <linux/fb.h>
17 #include <linux/backlight.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 
24 #include <linux/map_to_7segment.h>
25 #include <linux/map_to_14segment.h>
26 
27 #include <asm/unaligned.h>
28 
29 #include "line-display.h"
30 
31 /* Registers */
32 #define REG_SYSTEM_SETUP		0x20
33 #define REG_SYSTEM_SETUP_OSC_ON		BIT(0)
34 
35 #define REG_DISPLAY_SETUP		0x80
36 #define REG_DISPLAY_SETUP_ON		BIT(0)
37 #define REG_DISPLAY_SETUP_BLINK_OFF	(0 << 1)
38 #define REG_DISPLAY_SETUP_BLINK_2HZ	(1 << 1)
39 #define REG_DISPLAY_SETUP_BLINK_1HZ	(2 << 1)
40 #define REG_DISPLAY_SETUP_BLINK_0HZ5	(3 << 1)
41 
42 #define REG_ROWINT_SET			0xA0
43 #define REG_ROWINT_SET_INT_EN		BIT(0)
44 #define REG_ROWINT_SET_INT_ACT_HIGH	BIT(1)
45 
46 #define REG_BRIGHTNESS			0xE0
47 
48 /* Defines */
49 #define DRIVER_NAME			"ht16k33"
50 
51 #define MIN_BRIGHTNESS			0x1
52 #define MAX_BRIGHTNESS			0x10
53 
54 #define HT16K33_MATRIX_LED_MAX_COLS	8
55 #define HT16K33_MATRIX_LED_MAX_ROWS	16
56 #define HT16K33_MATRIX_KEYPAD_MAX_COLS	3
57 #define HT16K33_MATRIX_KEYPAD_MAX_ROWS	12
58 
59 #define BYTES_PER_ROW		(HT16K33_MATRIX_LED_MAX_ROWS / 8)
60 #define HT16K33_FB_SIZE		(HT16K33_MATRIX_LED_MAX_COLS * BYTES_PER_ROW)
61 
62 enum display_type {
63 	DISP_MATRIX = 0,
64 	DISP_QUAD_7SEG,
65 	DISP_QUAD_14SEG,
66 };
67 
68 struct ht16k33_keypad {
69 	struct i2c_client *client;
70 	struct input_dev *dev;
71 	uint32_t cols;
72 	uint32_t rows;
73 	uint32_t row_shift;
74 	uint32_t debounce_ms;
75 	uint16_t last_key_state[HT16K33_MATRIX_KEYPAD_MAX_COLS];
76 
77 	wait_queue_head_t wait;
78 	bool stopped;
79 };
80 
81 struct ht16k33_fbdev {
82 	struct fb_info *info;
83 	uint32_t refresh_rate;
84 	uint8_t *buffer;
85 	uint8_t *cache;
86 };
87 
88 struct ht16k33_seg {
89 	struct linedisp linedisp;
90 	union {
91 		struct seg7_conversion_map seg7;
92 		struct seg14_conversion_map seg14;
93 	} map;
94 	unsigned int map_size;
95 	char curr[4];
96 };
97 
98 struct ht16k33_priv {
99 	struct i2c_client *client;
100 	struct delayed_work work;
101 	struct led_classdev led;
102 	struct ht16k33_keypad keypad;
103 	union {
104 		struct ht16k33_fbdev fbdev;
105 		struct ht16k33_seg seg;
106 	};
107 	enum display_type type;
108 	uint8_t blink;
109 };
110 
111 static const struct fb_fix_screeninfo ht16k33_fb_fix = {
112 	.id		= DRIVER_NAME,
113 	.type		= FB_TYPE_PACKED_PIXELS,
114 	.visual		= FB_VISUAL_MONO10,
115 	.xpanstep	= 0,
116 	.ypanstep	= 0,
117 	.ywrapstep	= 0,
118 	.line_length	= HT16K33_MATRIX_LED_MAX_ROWS,
119 	.accel		= FB_ACCEL_NONE,
120 };
121 
122 static const struct fb_var_screeninfo ht16k33_fb_var = {
123 	.xres = HT16K33_MATRIX_LED_MAX_ROWS,
124 	.yres = HT16K33_MATRIX_LED_MAX_COLS,
125 	.xres_virtual = HT16K33_MATRIX_LED_MAX_ROWS,
126 	.yres_virtual = HT16K33_MATRIX_LED_MAX_COLS,
127 	.bits_per_pixel = 1,
128 	.red = { 0, 1, 0 },
129 	.green = { 0, 1, 0 },
130 	.blue = { 0, 1, 0 },
131 	.left_margin = 0,
132 	.right_margin = 0,
133 	.upper_margin = 0,
134 	.lower_margin = 0,
135 	.vmode = FB_VMODE_NONINTERLACED,
136 };
137 
138 static const SEG7_DEFAULT_MAP(initial_map_seg7);
139 static const SEG14_DEFAULT_MAP(initial_map_seg14);
140 
141 static ssize_t map_seg_show(struct device *dev, struct device_attribute *attr,
142 			    char *buf)
143 {
144 	struct ht16k33_priv *priv = dev_get_drvdata(dev);
145 
146 	memcpy(buf, &priv->seg.map, priv->seg.map_size);
147 	return priv->seg.map_size;
148 }
149 
150 static ssize_t map_seg_store(struct device *dev, struct device_attribute *attr,
151 			     const char *buf, size_t cnt)
152 {
153 	struct ht16k33_priv *priv = dev_get_drvdata(dev);
154 
155 	if (cnt != priv->seg.map_size)
156 		return -EINVAL;
157 
158 	memcpy(&priv->seg.map, buf, cnt);
159 	return cnt;
160 }
161 
162 static DEVICE_ATTR(map_seg7, 0644, map_seg_show, map_seg_store);
163 static DEVICE_ATTR(map_seg14, 0644, map_seg_show, map_seg_store);
164 
165 static int ht16k33_display_on(struct ht16k33_priv *priv)
166 {
167 	uint8_t data = REG_DISPLAY_SETUP | REG_DISPLAY_SETUP_ON | priv->blink;
168 
169 	return i2c_smbus_write_byte(priv->client, data);
170 }
171 
172 static int ht16k33_display_off(struct ht16k33_priv *priv)
173 {
174 	return i2c_smbus_write_byte(priv->client, REG_DISPLAY_SETUP);
175 }
176 
177 static int ht16k33_brightness_set(struct ht16k33_priv *priv,
178 				  unsigned int brightness)
179 {
180 	int err;
181 
182 	if (brightness == 0) {
183 		priv->blink = REG_DISPLAY_SETUP_BLINK_OFF;
184 		return ht16k33_display_off(priv);
185 	}
186 
187 	err = ht16k33_display_on(priv);
188 	if (err)
189 		return err;
190 
191 	return i2c_smbus_write_byte(priv->client,
192 				    REG_BRIGHTNESS | (brightness - 1));
193 }
194 
195 static int ht16k33_brightness_set_blocking(struct led_classdev *led_cdev,
196 					   enum led_brightness brightness)
197 {
198 	struct ht16k33_priv *priv = container_of(led_cdev, struct ht16k33_priv,
199 						 led);
200 
201 	return ht16k33_brightness_set(priv, brightness);
202 }
203 
204 static int ht16k33_blink_set(struct led_classdev *led_cdev,
205 			     unsigned long *delay_on, unsigned long *delay_off)
206 {
207 	struct ht16k33_priv *priv = container_of(led_cdev, struct ht16k33_priv,
208 						 led);
209 	unsigned int delay;
210 	uint8_t blink;
211 	int err;
212 
213 	if (!*delay_on && !*delay_off) {
214 		blink = REG_DISPLAY_SETUP_BLINK_1HZ;
215 		delay = 1000;
216 	} else if (*delay_on <= 750) {
217 		blink = REG_DISPLAY_SETUP_BLINK_2HZ;
218 		delay = 500;
219 	} else if (*delay_on <= 1500) {
220 		blink = REG_DISPLAY_SETUP_BLINK_1HZ;
221 		delay = 1000;
222 	} else {
223 		blink = REG_DISPLAY_SETUP_BLINK_0HZ5;
224 		delay = 2000;
225 	}
226 
227 	err = i2c_smbus_write_byte(priv->client,
228 				   REG_DISPLAY_SETUP | REG_DISPLAY_SETUP_ON |
229 				   blink);
230 	if (err)
231 		return err;
232 
233 	priv->blink = blink;
234 	*delay_on = *delay_off = delay;
235 	return 0;
236 }
237 
238 static void ht16k33_fb_queue(struct ht16k33_priv *priv)
239 {
240 	struct ht16k33_fbdev *fbdev = &priv->fbdev;
241 
242 	schedule_delayed_work(&priv->work, HZ / fbdev->refresh_rate);
243 }
244 
245 /*
246  * This gets the fb data from cache and copies it to ht16k33 display RAM
247  */
248 static void ht16k33_fb_update(struct work_struct *work)
249 {
250 	struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
251 						 work.work);
252 	struct ht16k33_fbdev *fbdev = &priv->fbdev;
253 
254 	uint8_t *p1, *p2;
255 	int len, pos = 0, first = -1;
256 
257 	p1 = fbdev->cache;
258 	p2 = fbdev->buffer;
259 
260 	/* Search for the first byte with changes */
261 	while (pos < HT16K33_FB_SIZE && first < 0) {
262 		if (*(p1++) - *(p2++))
263 			first = pos;
264 		pos++;
265 	}
266 
267 	/* No changes found */
268 	if (first < 0)
269 		goto requeue;
270 
271 	len = HT16K33_FB_SIZE - first;
272 	p1 = fbdev->cache + HT16K33_FB_SIZE - 1;
273 	p2 = fbdev->buffer + HT16K33_FB_SIZE - 1;
274 
275 	/* Determine i2c transfer length */
276 	while (len > 1) {
277 		if (*(p1--) - *(p2--))
278 			break;
279 		len--;
280 	}
281 
282 	p1 = fbdev->cache + first;
283 	p2 = fbdev->buffer + first;
284 	if (!i2c_smbus_write_i2c_block_data(priv->client, first, len, p2))
285 		memcpy(p1, p2, len);
286 requeue:
287 	ht16k33_fb_queue(priv);
288 }
289 
290 static int ht16k33_initialize(struct ht16k33_priv *priv)
291 {
292 	uint8_t data[HT16K33_FB_SIZE];
293 	uint8_t byte;
294 	int err;
295 
296 	/* Clear RAM (8 * 16 bits) */
297 	memset(data, 0, sizeof(data));
298 	err = i2c_smbus_write_block_data(priv->client, 0, sizeof(data), data);
299 	if (err)
300 		return err;
301 
302 	/* Turn on internal oscillator */
303 	byte = REG_SYSTEM_SETUP_OSC_ON | REG_SYSTEM_SETUP;
304 	err = i2c_smbus_write_byte(priv->client, byte);
305 	if (err)
306 		return err;
307 
308 	/* Configure INT pin */
309 	byte = REG_ROWINT_SET | REG_ROWINT_SET_INT_ACT_HIGH;
310 	if (priv->client->irq > 0)
311 		byte |= REG_ROWINT_SET_INT_EN;
312 	return i2c_smbus_write_byte(priv->client, byte);
313 }
314 
315 static int ht16k33_bl_update_status(struct backlight_device *bl)
316 {
317 	int brightness = bl->props.brightness;
318 	struct ht16k33_priv *priv = bl_get_data(bl);
319 
320 	if (bl->props.power != FB_BLANK_UNBLANK ||
321 	    bl->props.fb_blank != FB_BLANK_UNBLANK ||
322 	    bl->props.state & BL_CORE_FBBLANK)
323 		brightness = 0;
324 
325 	return ht16k33_brightness_set(priv, brightness);
326 }
327 
328 static int ht16k33_bl_check_fb(struct backlight_device *bl, struct fb_info *fi)
329 {
330 	struct ht16k33_priv *priv = bl_get_data(bl);
331 
332 	return (fi == NULL) || (fi->par == priv);
333 }
334 
335 static const struct backlight_ops ht16k33_bl_ops = {
336 	.update_status	= ht16k33_bl_update_status,
337 	.check_fb	= ht16k33_bl_check_fb,
338 };
339 
340 /*
341  * Blank events will be passed to the actual device handling the backlight when
342  * we return zero here.
343  */
344 static int ht16k33_blank(int blank, struct fb_info *info)
345 {
346 	return 0;
347 }
348 
349 static int ht16k33_mmap(struct fb_info *info, struct vm_area_struct *vma)
350 {
351 	struct ht16k33_priv *priv = info->par;
352 	struct page *pages = virt_to_page(priv->fbdev.buffer);
353 
354 	return vm_map_pages_zero(vma, &pages, 1);
355 }
356 
357 static const struct fb_ops ht16k33_fb_ops = {
358 	.owner = THIS_MODULE,
359 	.fb_read = fb_sys_read,
360 	.fb_write = fb_sys_write,
361 	.fb_blank = ht16k33_blank,
362 	.fb_fillrect = sys_fillrect,
363 	.fb_copyarea = sys_copyarea,
364 	.fb_imageblit = sys_imageblit,
365 	.fb_mmap = ht16k33_mmap,
366 };
367 
368 /*
369  * This gets the keys from keypad and reports it to input subsystem.
370  * Returns true if a key is pressed.
371  */
372 static bool ht16k33_keypad_scan(struct ht16k33_keypad *keypad)
373 {
374 	const unsigned short *keycodes = keypad->dev->keycode;
375 	u16 new_state[HT16K33_MATRIX_KEYPAD_MAX_COLS];
376 	__le16 data[HT16K33_MATRIX_KEYPAD_MAX_COLS];
377 	unsigned long bits_changed;
378 	int row, col, code;
379 	int rc;
380 	bool pressed = false;
381 
382 	rc = i2c_smbus_read_i2c_block_data(keypad->client, 0x40,
383 					   sizeof(data), (u8 *)data);
384 	if (rc != sizeof(data)) {
385 		dev_err(&keypad->client->dev,
386 			"Failed to read key data, rc=%d\n", rc);
387 		return false;
388 	}
389 
390 	for (col = 0; col < keypad->cols; col++) {
391 		new_state[col] = le16_to_cpu(data[col]);
392 		if (new_state[col])
393 			pressed = true;
394 		bits_changed = keypad->last_key_state[col] ^ new_state[col];
395 
396 		for_each_set_bit(row, &bits_changed, BITS_PER_LONG) {
397 			code = MATRIX_SCAN_CODE(row, col, keypad->row_shift);
398 			input_event(keypad->dev, EV_MSC, MSC_SCAN, code);
399 			input_report_key(keypad->dev, keycodes[code],
400 					 new_state[col] & BIT(row));
401 		}
402 	}
403 	input_sync(keypad->dev);
404 	memcpy(keypad->last_key_state, new_state, sizeof(u16) * keypad->cols);
405 
406 	return pressed;
407 }
408 
409 static irqreturn_t ht16k33_keypad_irq_thread(int irq, void *dev)
410 {
411 	struct ht16k33_keypad *keypad = dev;
412 
413 	do {
414 		wait_event_timeout(keypad->wait, keypad->stopped,
415 				    msecs_to_jiffies(keypad->debounce_ms));
416 		if (keypad->stopped)
417 			break;
418 	} while (ht16k33_keypad_scan(keypad));
419 
420 	return IRQ_HANDLED;
421 }
422 
423 static int ht16k33_keypad_start(struct input_dev *dev)
424 {
425 	struct ht16k33_keypad *keypad = input_get_drvdata(dev);
426 
427 	keypad->stopped = false;
428 	mb();
429 	enable_irq(keypad->client->irq);
430 
431 	return 0;
432 }
433 
434 static void ht16k33_keypad_stop(struct input_dev *dev)
435 {
436 	struct ht16k33_keypad *keypad = input_get_drvdata(dev);
437 
438 	keypad->stopped = true;
439 	mb();
440 	wake_up(&keypad->wait);
441 	disable_irq(keypad->client->irq);
442 }
443 
444 static void ht16k33_linedisp_update(struct linedisp *linedisp)
445 {
446 	struct ht16k33_priv *priv = container_of(linedisp, struct ht16k33_priv,
447 						 seg.linedisp);
448 
449 	schedule_delayed_work(&priv->work, 0);
450 }
451 
452 static void ht16k33_seg7_update(struct work_struct *work)
453 {
454 	struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
455 						 work.work);
456 	struct ht16k33_seg *seg = &priv->seg;
457 	char *s = seg->curr;
458 	uint8_t buf[9];
459 
460 	buf[0] = map_to_seg7(&seg->map.seg7, *s++);
461 	buf[1] = 0;
462 	buf[2] = map_to_seg7(&seg->map.seg7, *s++);
463 	buf[3] = 0;
464 	buf[4] = 0;
465 	buf[5] = 0;
466 	buf[6] = map_to_seg7(&seg->map.seg7, *s++);
467 	buf[7] = 0;
468 	buf[8] = map_to_seg7(&seg->map.seg7, *s++);
469 
470 	i2c_smbus_write_i2c_block_data(priv->client, 0, ARRAY_SIZE(buf), buf);
471 }
472 
473 static void ht16k33_seg14_update(struct work_struct *work)
474 {
475 	struct ht16k33_priv *priv = container_of(work, struct ht16k33_priv,
476 						 work.work);
477 	struct ht16k33_seg *seg = &priv->seg;
478 	char *s = seg->curr;
479 	uint8_t buf[8];
480 
481 	put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf);
482 	put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf + 2);
483 	put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf + 4);
484 	put_unaligned_le16(map_to_seg14(&seg->map.seg14, *s++), buf + 6);
485 
486 	i2c_smbus_write_i2c_block_data(priv->client, 0, ARRAY_SIZE(buf), buf);
487 }
488 
489 static int ht16k33_led_probe(struct device *dev, struct led_classdev *led,
490 			     unsigned int brightness)
491 {
492 	struct led_init_data init_data = {};
493 	int err;
494 
495 	/* The LED is optional */
496 	init_data.fwnode = device_get_named_child_node(dev, "led");
497 	if (!init_data.fwnode)
498 		return 0;
499 
500 	init_data.devicename = "auxdisplay";
501 	init_data.devname_mandatory = true;
502 
503 	led->brightness_set_blocking = ht16k33_brightness_set_blocking;
504 	led->blink_set = ht16k33_blink_set;
505 	led->flags = LED_CORE_SUSPENDRESUME;
506 	led->brightness = brightness;
507 	led->max_brightness = MAX_BRIGHTNESS;
508 
509 	err = devm_led_classdev_register_ext(dev, led, &init_data);
510 	if (err)
511 		dev_err(dev, "Failed to register LED\n");
512 
513 	return err;
514 }
515 
516 static int ht16k33_keypad_probe(struct i2c_client *client,
517 				struct ht16k33_keypad *keypad)
518 {
519 	struct device *dev = &client->dev;
520 	u32 rows = HT16K33_MATRIX_KEYPAD_MAX_ROWS;
521 	u32 cols = HT16K33_MATRIX_KEYPAD_MAX_COLS;
522 	int err;
523 
524 	keypad->client = client;
525 	init_waitqueue_head(&keypad->wait);
526 
527 	keypad->dev = devm_input_allocate_device(dev);
528 	if (!keypad->dev)
529 		return -ENOMEM;
530 
531 	input_set_drvdata(keypad->dev, keypad);
532 
533 	keypad->dev->name = DRIVER_NAME"-keypad";
534 	keypad->dev->id.bustype = BUS_I2C;
535 	keypad->dev->open = ht16k33_keypad_start;
536 	keypad->dev->close = ht16k33_keypad_stop;
537 
538 	if (!device_property_read_bool(dev, "linux,no-autorepeat"))
539 		__set_bit(EV_REP, keypad->dev->evbit);
540 
541 	err = device_property_read_u32(dev, "debounce-delay-ms",
542 				       &keypad->debounce_ms);
543 	if (err) {
544 		dev_err(dev, "key debounce delay not specified\n");
545 		return err;
546 	}
547 
548 	err = matrix_keypad_parse_properties(dev, &rows, &cols);
549 	if (err)
550 		return err;
551 	if (rows > HT16K33_MATRIX_KEYPAD_MAX_ROWS ||
552 	    cols > HT16K33_MATRIX_KEYPAD_MAX_COLS) {
553 		dev_err(dev, "%u rows or %u cols out of range in DT\n", rows,
554 			cols);
555 		return -ERANGE;
556 	}
557 
558 	keypad->rows = rows;
559 	keypad->cols = cols;
560 	keypad->row_shift = get_count_order(cols);
561 
562 	err = matrix_keypad_build_keymap(NULL, NULL, rows, cols, NULL,
563 					 keypad->dev);
564 	if (err) {
565 		dev_err(dev, "failed to build keymap\n");
566 		return err;
567 	}
568 
569 	err = devm_request_threaded_irq(dev, client->irq, NULL,
570 					ht16k33_keypad_irq_thread,
571 					IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
572 					DRIVER_NAME, keypad);
573 	if (err) {
574 		dev_err(dev, "irq request failed %d, error %d\n", client->irq,
575 			err);
576 		return err;
577 	}
578 
579 	ht16k33_keypad_stop(keypad->dev);
580 
581 	return input_register_device(keypad->dev);
582 }
583 
584 static int ht16k33_fbdev_probe(struct device *dev, struct ht16k33_priv *priv,
585 			       uint32_t brightness)
586 {
587 	struct ht16k33_fbdev *fbdev = &priv->fbdev;
588 	struct backlight_device *bl = NULL;
589 	int err;
590 
591 	if (priv->led.dev) {
592 		err = ht16k33_brightness_set(priv, brightness);
593 		if (err)
594 			return err;
595 	} else {
596 		/* backwards compatibility with DT lacking an led subnode */
597 		struct backlight_properties bl_props;
598 
599 		memset(&bl_props, 0, sizeof(struct backlight_properties));
600 		bl_props.type = BACKLIGHT_RAW;
601 		bl_props.max_brightness = MAX_BRIGHTNESS;
602 
603 		bl = devm_backlight_device_register(dev, DRIVER_NAME"-bl", dev,
604 						    priv, &ht16k33_bl_ops,
605 						    &bl_props);
606 		if (IS_ERR(bl)) {
607 			dev_err(dev, "failed to register backlight\n");
608 			return PTR_ERR(bl);
609 		}
610 
611 		bl->props.brightness = brightness;
612 		ht16k33_bl_update_status(bl);
613 	}
614 
615 	/* Framebuffer (2 bytes per column) */
616 	BUILD_BUG_ON(PAGE_SIZE < HT16K33_FB_SIZE);
617 	fbdev->buffer = (unsigned char *) get_zeroed_page(GFP_KERNEL);
618 	if (!fbdev->buffer)
619 		return -ENOMEM;
620 
621 	fbdev->cache = devm_kmalloc(dev, HT16K33_FB_SIZE, GFP_KERNEL);
622 	if (!fbdev->cache) {
623 		err = -ENOMEM;
624 		goto err_fbdev_buffer;
625 	}
626 
627 	fbdev->info = framebuffer_alloc(0, dev);
628 	if (!fbdev->info) {
629 		err = -ENOMEM;
630 		goto err_fbdev_buffer;
631 	}
632 
633 	err = device_property_read_u32(dev, "refresh-rate-hz",
634 				       &fbdev->refresh_rate);
635 	if (err) {
636 		dev_err(dev, "refresh rate not specified\n");
637 		goto err_fbdev_info;
638 	}
639 	fb_bl_default_curve(fbdev->info, 0, MIN_BRIGHTNESS, MAX_BRIGHTNESS);
640 
641 	INIT_DELAYED_WORK(&priv->work, ht16k33_fb_update);
642 	fbdev->info->fbops = &ht16k33_fb_ops;
643 	fbdev->info->screen_buffer = fbdev->buffer;
644 	fbdev->info->screen_size = HT16K33_FB_SIZE;
645 	fbdev->info->fix = ht16k33_fb_fix;
646 	fbdev->info->var = ht16k33_fb_var;
647 	fbdev->info->bl_dev = bl;
648 	fbdev->info->pseudo_palette = NULL;
649 	fbdev->info->flags = FBINFO_FLAG_DEFAULT;
650 	fbdev->info->par = priv;
651 
652 	err = register_framebuffer(fbdev->info);
653 	if (err)
654 		goto err_fbdev_info;
655 
656 	ht16k33_fb_queue(priv);
657 	return 0;
658 
659 err_fbdev_info:
660 	framebuffer_release(fbdev->info);
661 err_fbdev_buffer:
662 	free_page((unsigned long) fbdev->buffer);
663 
664 	return err;
665 }
666 
667 static int ht16k33_seg_probe(struct device *dev, struct ht16k33_priv *priv,
668 			     uint32_t brightness)
669 {
670 	struct ht16k33_seg *seg = &priv->seg;
671 	int err;
672 
673 	err = ht16k33_brightness_set(priv, brightness);
674 	if (err)
675 		return err;
676 
677 	switch (priv->type) {
678 	case DISP_MATRIX:
679 		/* not handled here */
680 		err = -EINVAL;
681 		break;
682 
683 	case DISP_QUAD_7SEG:
684 		INIT_DELAYED_WORK(&priv->work, ht16k33_seg7_update);
685 		seg->map.seg7 = initial_map_seg7;
686 		seg->map_size = sizeof(seg->map.seg7);
687 		err = device_create_file(dev, &dev_attr_map_seg7);
688 		break;
689 
690 	case DISP_QUAD_14SEG:
691 		INIT_DELAYED_WORK(&priv->work, ht16k33_seg14_update);
692 		seg->map.seg14 = initial_map_seg14;
693 		seg->map_size = sizeof(seg->map.seg14);
694 		err = device_create_file(dev, &dev_attr_map_seg14);
695 		break;
696 	}
697 	if (err)
698 		return err;
699 
700 	err = linedisp_register(&seg->linedisp, dev, 4, seg->curr,
701 				ht16k33_linedisp_update);
702 	if (err)
703 		goto err_remove_map_file;
704 
705 	return 0;
706 
707 err_remove_map_file:
708 	device_remove_file(dev, &dev_attr_map_seg7);
709 	device_remove_file(dev, &dev_attr_map_seg14);
710 	return err;
711 }
712 
713 static int ht16k33_probe(struct i2c_client *client)
714 {
715 	struct device *dev = &client->dev;
716 	const struct of_device_id *id;
717 	struct ht16k33_priv *priv;
718 	uint32_t dft_brightness;
719 	int err;
720 
721 	if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
722 		dev_err(dev, "i2c_check_functionality error\n");
723 		return -EIO;
724 	}
725 
726 	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
727 	if (!priv)
728 		return -ENOMEM;
729 
730 	priv->client = client;
731 	id = i2c_of_match_device(dev->driver->of_match_table, client);
732 	if (id)
733 		priv->type = (uintptr_t)id->data;
734 	i2c_set_clientdata(client, priv);
735 
736 	err = ht16k33_initialize(priv);
737 	if (err)
738 		return err;
739 
740 	err = device_property_read_u32(dev, "default-brightness-level",
741 				       &dft_brightness);
742 	if (err) {
743 		dft_brightness = MAX_BRIGHTNESS;
744 	} else if (dft_brightness > MAX_BRIGHTNESS) {
745 		dev_warn(dev,
746 			 "invalid default brightness level: %u, using %u\n",
747 			 dft_brightness, MAX_BRIGHTNESS);
748 		dft_brightness = MAX_BRIGHTNESS;
749 	}
750 
751 	/* LED */
752 	err = ht16k33_led_probe(dev, &priv->led, dft_brightness);
753 	if (err)
754 		return err;
755 
756 	/* Keypad */
757 	if (client->irq > 0) {
758 		err = ht16k33_keypad_probe(client, &priv->keypad);
759 		if (err)
760 			return err;
761 	}
762 
763 	switch (priv->type) {
764 	case DISP_MATRIX:
765 		/* Frame Buffer Display */
766 		err = ht16k33_fbdev_probe(dev, priv, dft_brightness);
767 		break;
768 
769 	case DISP_QUAD_7SEG:
770 	case DISP_QUAD_14SEG:
771 		/* Segment Display */
772 		err = ht16k33_seg_probe(dev, priv, dft_brightness);
773 		break;
774 	}
775 	return err;
776 }
777 
778 static void ht16k33_remove(struct i2c_client *client)
779 {
780 	struct ht16k33_priv *priv = i2c_get_clientdata(client);
781 	struct ht16k33_fbdev *fbdev = &priv->fbdev;
782 
783 	cancel_delayed_work_sync(&priv->work);
784 
785 	switch (priv->type) {
786 	case DISP_MATRIX:
787 		unregister_framebuffer(fbdev->info);
788 		framebuffer_release(fbdev->info);
789 		free_page((unsigned long)fbdev->buffer);
790 		break;
791 
792 	case DISP_QUAD_7SEG:
793 	case DISP_QUAD_14SEG:
794 		linedisp_unregister(&priv->seg.linedisp);
795 		device_remove_file(&client->dev, &dev_attr_map_seg7);
796 		device_remove_file(&client->dev, &dev_attr_map_seg14);
797 		break;
798 	}
799 }
800 
801 static const struct i2c_device_id ht16k33_i2c_match[] = {
802 	{ "ht16k33", 0 },
803 	{ }
804 };
805 MODULE_DEVICE_TABLE(i2c, ht16k33_i2c_match);
806 
807 static const struct of_device_id ht16k33_of_match[] = {
808 	{
809 		/* 0.56" 4-Digit 7-Segment FeatherWing Display (Red) */
810 		.compatible = "adafruit,3108", .data = (void *)DISP_QUAD_7SEG,
811 	}, {
812 		/* 0.54" Quad Alphanumeric FeatherWing Display (Red) */
813 		.compatible = "adafruit,3130", .data = (void *)DISP_QUAD_14SEG,
814 	}, {
815 		/* Generic, assumed Dot-Matrix Display */
816 		.compatible = "holtek,ht16k33", .data = (void *)DISP_MATRIX,
817 	},
818 	{ }
819 };
820 MODULE_DEVICE_TABLE(of, ht16k33_of_match);
821 
822 static struct i2c_driver ht16k33_driver = {
823 	.probe		= ht16k33_probe,
824 	.remove		= ht16k33_remove,
825 	.driver		= {
826 		.name		= DRIVER_NAME,
827 		.of_match_table	= ht16k33_of_match,
828 	},
829 	.id_table = ht16k33_i2c_match,
830 };
831 module_i2c_driver(ht16k33_driver);
832 
833 MODULE_DESCRIPTION("Holtek HT16K33 driver");
834 MODULE_LICENSE("GPL");
835 MODULE_AUTHOR("Robin van der Gracht <robin@protonic.nl>");
836