mail archive of the barebox mailing list
 help / color / mirror / Atom feed
* [PATCH] input core
@ 2016-01-13 15:37 Sascha Hauer
  2016-01-13 15:37 ` [PATCH 01/15] poller: Fix async poller Sascha Hauer
                   ` (14 more replies)
  0 siblings, 15 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

This series adds an input driver core and ports some input driver over
to it.

Currently the input drivers are written as console drivers. The problem
with this is that we can only generate a character when a key is
pressed, but we can't ask for the current state of a key. One very
common usecase for buttons in a bootloader is to ask if the user is
holding a button while booting to go into a recovery mode or boot from
alternative sources. We should support this usecase and with this input
core we can.
A nice side effect is that the input driver get simpler since the input
core handles stuff like key repetition and fifos for the keys.

Sascha

----------------------------------------------------------------
Sascha Hauer (15):
      poller: Fix async poller
      keymap: Fix braces
      keymap: remove exotic and nonprintable keys
      keymap: Add keypad keys
      keymap: Add apostrophe, backslash and home
      keymap: Add keymap for keys with shift pressed
      input: Add input core
      input: usb keyboard: convert to input framework
      input: imx-keypad: Use dev_* functions
      input: move matrix_keypad_build_keymap() to C file
      input: imx-keypad: convert to input framework
      input: Add device tree parsing support for matrix keymap
      input: imx-keypad: Add device tree support
      input: gpio-keys: Use KEY_* keycodes
      input: gpio-keys: convert to input framework

 arch/arm/boards/archosg9/board.c         |   5 +-
 arch/arm/boards/at91sam9261ek/init.c     |   7 +-
 arch/arm/boards/at91sam9m10g45ek/init.c  |  15 +-
 arch/arm/boards/usb-a926x/init.c         |   9 +-
 arch/arm/mach-imx/include/mach/devices.h |   2 +-
 common/poller.c                          |  26 ++-
 drivers/input/Kconfig                    |   9 +
 drivers/input/Makefile                   |   2 +
 drivers/input/gpio_keys.c                |  71 ++------
 drivers/input/imx_keypad.c               |  92 ++++------
 drivers/input/input.c                    | 202 +++++++++++++++++++++
 drivers/input/keymap.c                   | 173 ++++++++++--------
 drivers/input/matrix-keymap.c            |  89 ++++++++++
 drivers/input/usb_kbd.c                  | 296 ++++++-------------------------
 include/input/input.h                    |  34 ++++
 include/input/keyboard.h                 |   1 +
 include/input/matrix_keypad.h            |  35 ++++
 include/matrix_keypad.h                  |  59 ------
 include/poller.h                         |   4 +
 19 files changed, 628 insertions(+), 503 deletions(-)
 create mode 100644 drivers/input/input.c
 create mode 100644 drivers/input/matrix-keymap.c
 create mode 100644 include/input/input.h
 create mode 100644 include/input/matrix_keypad.h
 delete mode 100644 include/matrix_keypad.h

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 01/15] poller: Fix async poller
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 02/15] keymap: Fix braces Sascha Hauer
                   ` (13 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

The async poller does not work as expected since it can happen that
the async poller is removed from the list of pollers while we are
iterating over the list. Even list_for_each_entry_safe does not help
here since we may remove the next list element, but
list_for_each_entry_safe only allows to remove the current list element.

Rework the async poller so that it is registered with the poller
framework on registration and then is only marked as active with
poller_call_async(). This way we do not have to do list manipulations
while running the pollers.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 common/poller.c  | 26 ++++++++++++++++++++++----
 include/poller.h |  4 ++++
 2 files changed, 26 insertions(+), 4 deletions(-)

diff --git a/common/poller.c b/common/poller.c
index 496636d..32795b6 100644
--- a/common/poller.c
+++ b/common/poller.c
@@ -32,6 +32,7 @@ int poller_unregister(struct poller_struct *poller)
 	if (!poller->registered)
 		return -ENODEV;
 
+
 	list_del(&poller->list);
 	poller->registered = 0;
 
@@ -42,12 +43,14 @@ static void poller_async_callback(struct poller_struct *poller)
 {
 	struct poller_async *pa = container_of(poller, struct poller_async, poller);
 
+	if (!pa->active)
+		return;
+
 	if (get_time_ns() < pa->end)
 		return;
 
+	pa->active = 0;
 	pa->fn(pa->ctx);
-	pa->fn = NULL;
-	poller_unregister(&pa->poller);
 }
 
 /*
@@ -62,7 +65,9 @@ static void poller_async_callback(struct poller_struct *poller)
  */
 int poller_async_cancel(struct poller_async *pa)
 {
-	return poller_unregister(&pa->poller);
+	pa->active = 0;
+
+	return 0;
 }
 
 /*
@@ -80,13 +85,26 @@ int poller_call_async(struct poller_async *pa, uint64_t delay_ns,
 		void (*fn)(void *), void *ctx)
 {
 	pa->ctx = ctx;
-	pa->poller.func = poller_async_callback;
 	pa->end = get_time_ns() + delay_ns;
 	pa->fn = fn;
+	pa->active = 1;
+
+	return 0;
+}
+
+int poller_async_register(struct poller_async *pa)
+{
+	pa->poller.func = poller_async_callback;
+	pa->active = 0;
 
 	return poller_register(&pa->poller);
 }
 
+int poller_async_unregister(struct poller_async *pa)
+{
+	return poller_unregister(&pa->poller);
+}
+
 void poller_call(void)
 {
 	struct poller_struct *poller, *tmp;
diff --git a/include/poller.h b/include/poller.h
index cda5b57..35a2271 100644
--- a/include/poller.h
+++ b/include/poller.h
@@ -26,8 +26,12 @@ struct poller_async {
 	void (*fn)(void *);
 	void *ctx;
 	uint64_t end;
+	int active;
 };
 
+int poller_async_register(struct poller_async *pa);
+int poller_async_unregister(struct poller_async *pa);
+
 int poller_call_async(struct poller_async *pa, uint64_t delay_ns,
 		void (*fn)(void *), void *ctx);
 int poller_async_cancel(struct poller_async *pa);
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 02/15] keymap: Fix braces
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
  2016-01-13 15:37 ` [PATCH 01/15] poller: Fix async poller Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 03/15] keymap: remove exotic and nonprintable keys Sascha Hauer
                   ` (12 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

KEY_LEFTBRACE is the '[' key on an english keyboard and KEY_RIGHTBRACE
is the ']' key.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/keymap.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/input/keymap.c b/drivers/input/keymap.c
index b9fd6a2..eb3d4cf 100644
--- a/drivers/input/keymap.c
+++ b/drivers/input/keymap.c
@@ -31,8 +31,8 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_I] =		'i',
 	[KEY_O] =		'o',
 	[KEY_P] =		'p',
-	[KEY_LEFTBRACE] =	'(',
-	[KEY_RIGHTBRACE] =	')',
+	[KEY_LEFTBRACE] =	'[',
+	[KEY_RIGHTBRACE] =	']',
 	[KEY_ENTER] =		'\n',
 	[KEY_LEFTCTRL] =	0xff,
 	[KEY_A] =		'a',
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 03/15] keymap: remove exotic and nonprintable keys
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
  2016-01-13 15:37 ` [PATCH 01/15] poller: Fix async poller Sascha Hauer
  2016-01-13 15:37 ` [PATCH 02/15] keymap: Fix braces Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 04/15] keymap: Add keypad keys Sascha Hauer
                   ` (11 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

We do not need these keys and they do not produce a usable result
either.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/keymap.c | 49 -------------------------------------------------
 1 file changed, 49 deletions(-)

diff --git a/drivers/input/keymap.c b/drivers/input/keymap.c
index eb3d4cf..2e603f4 100644
--- a/drivers/input/keymap.c
+++ b/drivers/input/keymap.c
@@ -34,7 +34,6 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_LEFTBRACE] =	'[',
 	[KEY_RIGHTBRACE] =	']',
 	[KEY_ENTER] =		'\n',
-	[KEY_LEFTCTRL] =	0xff,
 	[KEY_A] =		'a',
 	[KEY_S] =		's',
 	[KEY_D] =		'd',
@@ -47,7 +46,6 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_SEMICOLON] =	';',
 	[KEY_APOSTROPHE] =	0xff,
 	[KEY_GRAVE] =		'^',
-	[KEY_LEFTSHIFT] =	0xff,
 	[KEY_BACKSLASH] =	0xff,
 	[KEY_Z] =		'z',
 	[KEY_X] =		'x',
@@ -59,23 +57,7 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_COMMA] =		',',
 	[KEY_DOT] =		'.',
 	[KEY_SLASH] =		'/',
-	[KEY_RIGHTSHIFT] =	0xff,
-	[KEY_KPASTERISK] =	0xff,
-	[KEY_LEFTALT] =		0xff,
 	[KEY_SPACE] =		' ',
-	[KEY_CAPSLOCK] =	0xff,
-	[KEY_F1] =		0xff,
-	[KEY_F2] =		0xff,
-	[KEY_F3] =		0xff,
-	[KEY_F4] =		0xff,
-	[KEY_F5] =		0xff,
-	[KEY_F6] =		0xff,
-	[KEY_F7] =		0xff,
-	[KEY_F8] =		0xff,
-	[KEY_F9] =		0xff,
-	[KEY_F10] =		0xff,
-	[KEY_NUMLOCK] =		0xff,
-	[KEY_SCROLLLOCK] =	0xff,
 	[KEY_KP7] =		0xff,
 	[KEY_KP8] =		0xff,
 	[KEY_KP9] =		0xff,
@@ -89,23 +71,7 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_KP3] =		0xff,
 	[KEY_KP0] =		0xff,
 	[KEY_KPDOT] =		0xff,
-	[KEY_ZENKAKUHANKAKU] =	0xff,
-	[KEY_102ND] =		0xff,
-	[KEY_F11] =		0xff,
-	[KEY_F12] =		0xff,
-	[KEY_RO] =		0xff,
-	[KEY_KATAKANA] =	0xff,
-	[KEY_HIRAGANA] =	0xff,
-	[KEY_HENKAN] =		0xff,
-	[KEY_KATAKANAHIRAGANA] =0xff,
-	[KEY_MUHENKAN] =	0xff,
-	[KEY_KPJPCOMMA] =	0xff,
 	[KEY_KPENTER] =		0xff,
-	[KEY_RIGHTCTRL] =	0xff,
-	[KEY_KPSLASH] =		0xff,
-	[KEY_SYSRQ] =		0xff,
-	[KEY_RIGHTALT] =	0xff,
-	[KEY_LINEFEED] =	0xff,
 	[KEY_HOME] =		0xff,
 	[KEY_UP] =		BB_KEY_UP,
 	[KEY_PAGEUP] =		BB_KEY_PAGEUP,
@@ -116,21 +82,6 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_PAGEDOWN] =	BB_KEY_PAGEDOWN,
 	[KEY_INSERT] =		BB_KEY_INSERT,
 	[KEY_DELETE] =		BB_KEY_DEL7,
-	[KEY_MACRO] =		0xff,
-	[KEY_MUTE] =		0xff,
-	[KEY_VOLUMEDOWN] =	0xff,
-	[KEY_VOLUMEUP] =	0xff,
-	[KEY_POWER] =		0xff,
 	[KEY_KPEQUAL] =		0xff,
-	[KEY_KPPLUSMINUS] =	0xff,
-	[KEY_PAUSE] =		0xff,
-	[KEY_SCALE] =		0xff,
 	[KEY_KPCOMMA] =		0xff,
-	[KEY_HANGEUL] =		0xff,
-	[KEY_HANGUEL] =		KEY_HANGEUL,
-	[KEY_HANJA] =		0xff,
-	[KEY_YEN] =		0xff,
-	[KEY_LEFTMETA] =	0xff,
-	[KEY_RIGHTMETA] =	0xff,
-	[KEY_COMPOSE] =		0xff,
 };
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 04/15] keymap: Add keypad keys
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (2 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 03/15] keymap: remove exotic and nonprintable keys Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 05/15] keymap: Add apostrophe, backslash and home Sascha Hauer
                   ` (10 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Allow to use the number keypad keys.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/keymap.c | 32 ++++++++++++++++----------------
 1 file changed, 16 insertions(+), 16 deletions(-)

diff --git a/drivers/input/keymap.c b/drivers/input/keymap.c
index 2e603f4..fdc04f7 100644
--- a/drivers/input/keymap.c
+++ b/drivers/input/keymap.c
@@ -58,20 +58,20 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_DOT] =		'.',
 	[KEY_SLASH] =		'/',
 	[KEY_SPACE] =		' ',
-	[KEY_KP7] =		0xff,
-	[KEY_KP8] =		0xff,
-	[KEY_KP9] =		0xff,
-	[KEY_KPMINUS] =		0xff,
-	[KEY_KP4] =		0xff,
-	[KEY_KP5] =		0xff,
-	[KEY_KP6] =		0xff,
-	[KEY_KPPLUS] =		0xff,
-	[KEY_KP1] =		0xff,
-	[KEY_KP2] =		0xff,
-	[KEY_KP3] =		0xff,
-	[KEY_KP0] =		0xff,
-	[KEY_KPDOT] =		0xff,
-	[KEY_KPENTER] =		0xff,
+	[KEY_KP7] =		'7',
+	[KEY_KP8] =		'8',
+	[KEY_KP9] =		'9',
+	[KEY_KPMINUS] =		'-',
+	[KEY_KP4] =		'4',
+	[KEY_KP5] =		'5',
+	[KEY_KP6] =		'6',
+	[KEY_KPPLUS] =		'+',
+	[KEY_KP1] =		'1',
+	[KEY_KP2] =		'2',
+	[KEY_KP3] =		'3',
+	[KEY_KP0] =		'0',
+	[KEY_KPDOT] =		'.',
+	[KEY_KPENTER] =		'\n',
 	[KEY_HOME] =		0xff,
 	[KEY_UP] =		BB_KEY_UP,
 	[KEY_PAGEUP] =		BB_KEY_PAGEUP,
@@ -82,6 +82,6 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_PAGEDOWN] =	BB_KEY_PAGEDOWN,
 	[KEY_INSERT] =		BB_KEY_INSERT,
 	[KEY_DELETE] =		BB_KEY_DEL7,
-	[KEY_KPEQUAL] =		0xff,
-	[KEY_KPCOMMA] =		0xff,
+	[KEY_KPEQUAL] =		'=',
+	[KEY_KPCOMMA] =		',',
 };
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 05/15] keymap: Add apostrophe, backslash and home
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (3 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 04/15] keymap: Add keypad keys Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 06/15] keymap: Add keymap for keys with shift pressed Sascha Hauer
                   ` (9 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Add some previously undefined keys.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/keymap.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/input/keymap.c b/drivers/input/keymap.c
index fdc04f7..73dd112 100644
--- a/drivers/input/keymap.c
+++ b/drivers/input/keymap.c
@@ -44,9 +44,9 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_K] =		'k',
 	[KEY_L] =		'l',
 	[KEY_SEMICOLON] =	';',
-	[KEY_APOSTROPHE] =	0xff,
+	[KEY_APOSTROPHE] =	'`',
 	[KEY_GRAVE] =		'^',
-	[KEY_BACKSLASH] =	0xff,
+	[KEY_BACKSLASH] =	'\\',
 	[KEY_Z] =		'z',
 	[KEY_X] =		'x',
 	[KEY_C] =		'c',
@@ -72,7 +72,7 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_KP0] =		'0',
 	[KEY_KPDOT] =		'.',
 	[KEY_KPENTER] =		'\n',
-	[KEY_HOME] =		0xff,
+	[KEY_HOME] =		BB_KEY_HOME,
 	[KEY_UP] =		BB_KEY_UP,
 	[KEY_PAGEUP] =		BB_KEY_PAGEUP,
 	[KEY_LEFT] =		BB_KEY_LEFT,
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 06/15] keymap: Add keymap for keys with shift pressed
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (4 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 05/15] keymap: Add apostrophe, backslash and home Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 07/15] input: Add input core Sascha Hauer
                   ` (8 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

When converting keys to ascii for the console we also need the
keymap with shift pressed.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/keymap.c   | 82 ++++++++++++++++++++++++++++++++++++++++++++++++
 include/input/keyboard.h |  1 +
 2 files changed, 83 insertions(+)

diff --git a/drivers/input/keymap.c b/drivers/input/keymap.c
index 73dd112..a07b3a8 100644
--- a/drivers/input/keymap.c
+++ b/drivers/input/keymap.c
@@ -81,6 +81,88 @@ uint8_t keycode_bb_keys[NR_KEYS] = {
 	[KEY_DOWN] =		BB_KEY_DOWN,
 	[KEY_PAGEDOWN] =	BB_KEY_PAGEDOWN,
 	[KEY_INSERT] =		BB_KEY_INSERT,
+	[KEY_DELETE] =		BB_KEY_DEL,
+	[KEY_KPEQUAL] =		'=',
+	[KEY_KPCOMMA] =		',',
+};
+
+uint8_t keycode_bb_shift_keys[NR_KEYS] = {
+	[KEY_RESERVED] =	0xff,
+	[KEY_ESC] =		0x1b,
+	[KEY_1] =		'!',
+	[KEY_2] =		'@',
+	[KEY_3] =		'#',
+	[KEY_4] =		'$',
+	[KEY_5] =		'%',
+	[KEY_6] =		'^',
+	[KEY_7] =		'&',
+	[KEY_8] =		'*',
+	[KEY_9] =		'(',
+	[KEY_0] =		')',
+	[KEY_MINUS] =		'_',
+	[KEY_EQUAL] =		'+',
+	[KEY_BACKSPACE] =	0xff,
+	[KEY_TAB] =		'\t',
+	[KEY_Q] =		'Q',
+	[KEY_W] =		'W',
+	[KEY_E] =		'E',
+	[KEY_R] =		'R',
+	[KEY_T] =		'T',
+	[KEY_Y] =		'Y',
+	[KEY_U] =		'U',
+	[KEY_I] =		'I',
+	[KEY_O] =		'O',
+	[KEY_P] =		'P',
+	[KEY_LEFTBRACE] =	'{',
+	[KEY_RIGHTBRACE] =	'}',
+	[KEY_ENTER] =		'\n',
+	[KEY_A] =		'A',
+	[KEY_S] =		'S',
+	[KEY_D] =		'D',
+	[KEY_F] =		'F',
+	[KEY_G] =		'G',
+	[KEY_H] =		'H',
+	[KEY_J] =		'J',
+	[KEY_K] =		'K',
+	[KEY_L] =		'L',
+	[KEY_SEMICOLON] =	':',
+	[KEY_APOSTROPHE] =	'~',
+	[KEY_GRAVE] =		'^',
+	[KEY_BACKSLASH] =	'|',
+	[KEY_Z] =		'Z',
+	[KEY_X] =		'X',
+	[KEY_C] =		'C',
+	[KEY_V] =		'V',
+	[KEY_B] =		'B',
+	[KEY_N] =		'N',
+	[KEY_M] =		'M',
+	[KEY_COMMA] =		'<',
+	[KEY_DOT] =		'>',
+	[KEY_SLASH] =		'?',
+	[KEY_SPACE] =		' ',
+	[KEY_KP7] =		'7',
+	[KEY_KP8] =		'8',
+	[KEY_KP9] =		'9',
+	[KEY_KP4] =		'4',
+	[KEY_KP5] =		'5',
+	[KEY_KP6] =		'6',
+	[KEY_KPPLUS] =		'+',
+	[KEY_KP1] =		'1',
+	[KEY_KP2] =		'2',
+	[KEY_KP3] =		'3',
+	[KEY_KP0] =		'4',
+	[KEY_KPDOT] =		'.',
+	[KEY_KPENTER] =		'\n',
+	[KEY_KPSLASH] =		'/',
+	[KEY_HOME] =		BB_KEY_HOME,
+	[KEY_UP] =		BB_KEY_UP,
+	[KEY_PAGEUP] =		BB_KEY_PAGEUP,
+	[KEY_LEFT] =		BB_KEY_LEFT,
+	[KEY_RIGHT] =		BB_KEY_RIGHT,
+	[KEY_END] =		BB_KEY_END,
+	[KEY_DOWN] =		BB_KEY_DOWN,
+	[KEY_PAGEDOWN] =	BB_KEY_PAGEDOWN,
+	[KEY_INSERT] =		BB_KEY_INSERT,
 	[KEY_DELETE] =		BB_KEY_DEL7,
 	[KEY_KPEQUAL] =		'=',
 	[KEY_KPCOMMA] =		',',
diff --git a/include/input/keyboard.h b/include/input/keyboard.h
index dd04690..d1f5bf5 100644
--- a/include/input/keyboard.h
+++ b/include/input/keyboard.h
@@ -6,5 +6,6 @@
 #define NR_KEYS	256
 
 extern uint8_t keycode_bb_keys[NR_KEYS];
+extern uint8_t keycode_bb_shift_keys[NR_KEYS];
 
 #endif
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 07/15] input: Add input core
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (5 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 06/15] keymap: Add keymap for keys with shift pressed Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2017-05-05 10:05   ` Antony Pavlov
  2016-01-13 15:37 ` [PATCH 08/15] input: usb keyboard: convert to input framework Sascha Hauer
                   ` (7 subsequent siblings)
  14 siblings, 1 reply; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Currently all input driver register themselves as consoles. Consoles are
fine for typing text, but they do not allow to ask for the current
pressed state of buttons or keypads. They also do not support non
printable keys like the function keys.

This patch adds a simple input core. On the driver side it supports
input_report_key_event() to report events (button presses and releases).
On the consumer side it allows getting the current button status via
input_key_get_status(). Also an event driven interface is available
which calls a callback whenever an input event is received.
The input core also registers a console for all registered input
devices which handles passing events to the console and stuff like key
repetition, so this can be removed from the drivers once they are
converted to the input core.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/Kconfig  |   3 +
 drivers/input/Makefile |   1 +
 drivers/input/input.c  | 202 +++++++++++++++++++++++++++++++++++++++++++++++++
 include/input/input.h  |  34 +++++++++
 4 files changed, 240 insertions(+)
 create mode 100644 drivers/input/input.c
 create mode 100644 include/input/input.h

diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig
index 336b9f5..e0368b2 100644
--- a/drivers/input/Kconfig
+++ b/drivers/input/Kconfig
@@ -5,6 +5,9 @@
 menu "Input device support"
 	depends on !CONSOLE_NONE
 
+config INPUT
+	bool
+
 config KEYBOARD_GPIO
 	bool "GPIO Buttons"
 	depends on GENERIC_GPIO
diff --git a/drivers/input/Makefile b/drivers/input/Makefile
index 40b898c..b9e5a5d 100644
--- a/drivers/input/Makefile
+++ b/drivers/input/Makefile
@@ -1,3 +1,4 @@
+obj-$(CONFIG_INPUT) += input.o
 obj-$(CONFIG_KEYBOARD_USB) += usb_kbd.o
 obj-$(CONFIG_KEYBOARD_GPIO) += gpio_keys.o
 obj-$(CONFIG_KEYBOARD_TWL6030) += twl6030_pwrbtn.o
diff --git a/drivers/input/input.c b/drivers/input/input.c
new file mode 100644
index 0000000..ad7400f
--- /dev/null
+++ b/drivers/input/input.c
@@ -0,0 +1,202 @@
+/*
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; version 2.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ */
+
+#include <common.h>
+#include <init.h>
+#include <kfifo.h>
+#include <poller.h>
+#include <clock.h>
+#include <input/input.h>
+#include <linux/bitmap.h>
+#include <input/keyboard.h>
+#include <dt-bindings/input/linux-event-codes.h>
+
+static LIST_HEAD(input_consumers);
+
+int input_register_notfier(struct input_notifier *in)
+{
+	list_add_tail(&in->list, &input_consumers);
+
+	return 0;
+}
+
+void input_unregister_notfier(struct input_notifier *in)
+{
+	list_del(&in->list);
+}
+
+void input_report_key_event(struct input_device *idev, unsigned int code, int value)
+{
+	struct input_event event;
+	struct input_notifier *in;
+
+	if (code > KEY_MAX)
+		return;
+
+	if (value)
+		set_bit(code, &idev->keys);
+	else
+		clear_bit(code, &idev->keys);
+
+	event.code = code;
+	event.value = value;
+
+	list_for_each_entry(in, &input_consumers, list)
+		in->notify(in, &event);
+}
+
+static LIST_HEAD(input_devices);
+
+int input_device_register(struct input_device *idev)
+{
+	list_add_tail(&idev->list, &input_devices);
+
+	return 0;
+}
+
+void input_device_unregister(struct input_device *idev)
+{
+	list_del(&idev->list);
+}
+
+void input_key_get_status(unsigned long *keys, int bits)
+{
+	struct input_device *idev;
+
+	bitmap_zero(keys, bits);
+
+	if (bits > KEY_MAX)
+		bits = KEY_MAX;
+
+	list_for_each_entry(idev, &input_devices, list)
+		bitmap_or(keys, keys, idev->keys, bits);
+}
+
+struct input_console {
+	struct console_device console;
+	struct input_notifier notifier;
+	struct kfifo *fifo;
+	struct poller_async poller;
+	uint8_t current_key;
+	uint8_t modstate[6];
+};
+
+static int input_console_tstc(struct console_device *cdev)
+{
+	struct input_console *ic = container_of(cdev, struct input_console, console);
+
+	return kfifo_len(ic->fifo) ? 1 : 0;
+}
+
+static int input_console_getc(struct console_device *cdev)
+{
+	struct input_console *ic = container_of(cdev, struct input_console, console);
+	uint8_t c;
+
+	kfifo_getc(ic->fifo, &c);
+
+	return c;
+}
+
+static void input_console_repeat(void *ctx)
+{
+	struct input_console *ic = ctx;
+
+	if (ic->current_key) {
+		kfifo_putc(ic->fifo, ic->current_key);
+		poller_call_async(&ic->poller, 40 * MSECOND,
+				  input_console_repeat, ic);
+	}
+}
+
+struct keycode {
+	unsigned char key;
+	unsigned char ascii;
+};
+
+static void input_console_notify(struct input_notifier *in,
+				 struct input_event *ev)
+{
+	struct input_console *ic = container_of(in, struct input_console, notifier);
+	uint8_t modstate = 0;
+	unsigned char ascii;
+
+	switch (ev->code) {
+	case KEY_LEFTSHIFT:
+		ic->modstate[0] = ev->value;
+		return;
+	case KEY_RIGHTSHIFT:
+		ic->modstate[1] = ev->value;
+		return;
+	case KEY_LEFTCTRL:
+		ic->modstate[2] = ev->value;
+		return;
+	case KEY_RIGHTCTRL:
+		ic->modstate[3] = ev->value;
+		return;
+	case KEY_LEFTALT:
+		ic->modstate[4] = ev->value;
+		return;
+	case KEY_RIGHTALT:
+		ic->modstate[5] = ev->value;
+		return;
+	case KEY_LEFTMETA:
+	case KEY_RIGHTMETA:
+		return;
+	default:
+		break;
+	}
+
+	if (ic->modstate[0] || ic->modstate[1])
+		modstate |= 1 << 0;
+
+	if (ic->modstate[2] || ic->modstate[3])
+		modstate |= 1 << 1;
+
+	if (ic->modstate[4] || ic->modstate[5])
+		modstate |= 1 << 2;
+
+	if (modstate & (1 << 0))
+		ascii = keycode_bb_shift_keys[ev->code];
+	else
+		ascii = keycode_bb_keys[ev->code];
+
+	pr_debug("map %02x KEY: 0x%04x code: %d\n", modstate, ascii, ev->code);
+
+	if (ev->value) {
+		kfifo_putc(ic->fifo, ascii);
+		ic->current_key = ascii;
+		poller_call_async(&ic->poller, 400 * MSECOND,
+				  input_console_repeat, ic);
+	} else {
+		ic->current_key = 0;
+		poller_async_cancel(&ic->poller);
+	}
+}
+
+static struct input_console input_console;
+
+static int input_init(void)
+{
+	struct input_console *ic = &input_console;
+
+	ic->console.tstc = input_console_tstc;
+	ic->console.getc = input_console_getc;
+	ic->console.f_active = CONSOLE_STDIN;
+
+	ic->fifo = kfifo_alloc(32);
+	ic->notifier.notify = input_console_notify;
+	input_register_notfier(&ic->notifier);
+	poller_async_register(&ic->poller);
+
+	return console_register(&ic->console);
+}
+console_initcall(input_init);
diff --git a/include/input/input.h b/include/input/input.h
new file mode 100644
index 0000000..dbf3e7f
--- /dev/null
+++ b/include/input/input.h
@@ -0,0 +1,34 @@
+#ifndef __INPUT_H
+#define __INPUT_H
+
+#include <linux/types.h>
+#include <linux/list.h>
+#include <dt-bindings/input/linux-event-codes.h>
+
+struct input_event {
+	uint16_t code;
+	uint16_t value;
+};
+
+struct input_device {
+	struct list_head list;
+	DECLARE_BITMAP(keys, KEY_CNT);
+};
+
+void input_report_key_event(struct input_device *idev, unsigned int code, int value);
+
+int input_device_register(struct input_device *);
+void input_device_unregister(struct input_device *);
+
+void input_key_get_status(unsigned long *keys, int bits);
+
+struct input_notifier {
+	void (*notify)(struct input_notifier *in, struct input_event *event);
+	struct list_head list;
+};
+
+int input_register_notfier(struct input_notifier *in);
+void input_unregister_notfier(struct input_notifier *in);
+
+#endif /* __INPUT_H */
+
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 08/15] input: usb keyboard: convert to input framework
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (6 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 07/15] input: Add input core Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 09/15] input: imx-keypad: Use dev_* functions Sascha Hauer
                   ` (6 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Conert the USB keyboard over to the new input core as a first user.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/Kconfig   |   1 +
 drivers/input/usb_kbd.c | 296 +++++++++---------------------------------------
 2 files changed, 55 insertions(+), 242 deletions(-)

diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig
index e0368b2..b840df2 100644
--- a/drivers/input/Kconfig
+++ b/drivers/input/Kconfig
@@ -54,6 +54,7 @@ config KEYBOARD_USB
 	depends on USB_HOST
 	depends on CONSOLE_FULL
 	select POLLER
+	select INPUT
 	help
 	  This driver implements support for usb keyboard.
 
diff --git a/drivers/input/usb_kbd.c b/drivers/input/usb_kbd.c
index 655d0c7..74bc11f 100644
--- a/drivers/input/usb_kbd.c
+++ b/drivers/input/usb_kbd.c
@@ -23,56 +23,7 @@
 #include <usb/usb.h>
 #include <string.h>
 #include <dma.h>
-#include <kfifo.h>
-
-#define USB_KBD_FIFO_SIZE	50
-
-#define REPEAT_RATE	40		/* 40msec -> 25cps */
-#define REPEAT_DELAY	10		/* 10 x REPEAT_RATE = 400msec */
-
-#define NUM_LOCK	0x53
-#define CAPS_LOCK	0x39
-#define SCROLL_LOCK	0x47
-
-/* Modifier bits */
-#define LEFT_CNTR	(1 << 0)
-#define LEFT_SHIFT	(1 << 1)
-#define LEFT_ALT	(1 << 2)
-#define LEFT_GUI	(1 << 3)
-#define RIGHT_CNTR	(1 << 4)
-#define RIGHT_SHIFT	(1 << 5)
-#define RIGHT_ALT	(1 << 6)
-#define RIGHT_GUI	(1 << 7)
-
-/* Size of the keyboard buffer */
-#define USB_KBD_BUFFER_LEN	0x20
-
-/* Keyboard maps */
-static const unsigned char usb_kbd_numkey[] = {
-	'1', '2', '3', '4', '5', '6', '7', '8', '9', '0',
-	'\r', 0x1b, '\b', '\t', ' ', '-', '=', '[', ']',
-	'\\', '#', ';', '\'', '`', ',', '.', '/'
-};
-static const unsigned char usb_kbd_numkey_shifted[] = {
-	'!', '@', '#', '$', '%', '^', '&', '*', '(', ')',
-	'\r', 0x1b, '\b', '\t', ' ', '_', '+', '{', '}',
-	'|', '~', ':', '"', '~', '<', '>', '?'
-};
-
-static const unsigned char usb_kbd_num_keypad[] = {
-	'/', '*', '-', '+', '\r',
-	'1', '2', '3', '4', '5', '6', '7', '8', '9', '0',
-	'.', 0, 0, 0, '='
-};
-
-/*
- * map arrow keys to ^F/^B ^N/^P, can't really use the proper
- * ANSI sequence for arrow keys because the queuing code breaks
- * when a single keypress expands to 3 queue elements
- */
-static const unsigned char usb_kbd_arrow[] = {
-	0x6, 0x2, 0xe, 0x10
-};
+#include <input/input.h>
 
 /*
  * NOTE: It's important for the NUM, CAPS, SCROLL-lock bits to be in this
@@ -96,21 +47,18 @@ struct usb_kbd_pdata;
 
 struct usb_kbd_pdata {
 	uint64_t	last_report;
-	uint64_t	last_poll;
 	uint8_t		*new;
 	uint8_t		old[USB_KBD_BOOT_REPORT_SIZE];
-	uint32_t	repeat_delay;
 	uint8_t		flags;
 	struct poller_struct	poller;
 	struct usb_device	*usbdev;
-	struct console_device	cdev;
-	struct kfifo		*recv_fifo;
 	int		lock;
 	unsigned long	intpipe;
 	int		intpktsize;
 	int		intinterval;
 	struct usb_endpoint_descriptor *ep;
 	int (*do_poll)(struct usb_kbd_pdata *);
+	struct input_device input;
 };
 
 static int usb_kbd_int_poll(struct usb_kbd_pdata *data)
@@ -127,162 +75,36 @@ static int usb_kbd_cnt_poll(struct usb_kbd_pdata *data)
 			      1, 0, data->new, USB_KBD_BOOT_REPORT_SIZE);
 }
 
-#define CAPITAL_MASK	0x20
-/* Translate the scancode in ASCII */
-static int usb_kbd_translate(struct usb_kbd_pdata *data, unsigned char scancode,
-				unsigned char modifier, int pressed)
-{
-	int keycode = 0;
-
-	/* Key released */
-	if (pressed == 0) {
-		data->repeat_delay = 0;
-		return 0;
-	}
-
-	if (pressed == 2) {
-		data->repeat_delay++;
-		if (data->repeat_delay < REPEAT_DELAY)
-			return 0;
-
-		data->repeat_delay = REPEAT_DELAY;
-	}
-
-	/* Alphanumeric values */
-	if ((scancode > 3) && (scancode <= 0x1d)) {
-		keycode = scancode - 4 + 'a';
-
-		if (data->flags & USB_KBD_CAPSLOCK)
-			keycode &= ~CAPITAL_MASK;
-
-		if (modifier & (LEFT_SHIFT | RIGHT_SHIFT)) {
-			/* Handle CAPSLock + Shift pressed simultaneously */
-			if (keycode & CAPITAL_MASK)
-				keycode &= ~CAPITAL_MASK;
-			else
-				keycode |= CAPITAL_MASK;
-		}
-	}
-
-	if ((scancode > 0x1d) && (scancode < 0x3a)) {
-		/* Shift pressed */
-		if (modifier & (LEFT_SHIFT | RIGHT_SHIFT))
-			keycode = usb_kbd_numkey_shifted[scancode - 0x1e];
-		else
-			keycode = usb_kbd_numkey[scancode - 0x1e];
-	}
-
-	/* Arrow keys */
-	if ((scancode >= 0x4f) && (scancode <= 0x52))
-		keycode = usb_kbd_arrow[scancode - 0x4f];
-
-	/* Numeric keypad */
-	if ((scancode >= 0x54) && (scancode <= 0x67))
-		keycode = usb_kbd_num_keypad[scancode - 0x54];
-
-	if (data->flags & USB_KBD_CTRL)
-		keycode = scancode - 0x3;
-
-	if (pressed == 1) {
-		if (scancode == NUM_LOCK) {
-			data->flags ^= USB_KBD_NUMLOCK;
-			return 1;
-		}
-
-		if (scancode == CAPS_LOCK) {
-			data->flags ^= USB_KBD_CAPSLOCK;
-			return 1;
-		}
-		if (scancode == SCROLL_LOCK) {
-			data->flags ^= USB_KBD_SCROLLLOCK;
-			return 1;
-		}
-	}
-
-	/* Report keycode if any */
-	if (keycode) {
-		pr_debug("%s: key pressed: '%c'\n", __FUNCTION__, keycode);
-		kfifo_put(data->recv_fifo, (u_char*)&keycode, sizeof(keycode));
-	}
-
-	return 0;
-}
-
-static uint32_t usb_kbd_service_key(struct usb_kbd_pdata *data, int i, int up)
-{
-	uint32_t res = 0;
-	uint8_t *new;
-	uint8_t *old;
-
-	if (up) {
-		new = data->old;
-		old = data->new;
-	} else {
-		new = data->new;
-		old = data->old;
-	}
-
-	if ((old[i] > 3) &&
-	    (memscan(new + 2, old[i], USB_KBD_BOOT_REPORT_SIZE - 2) ==
-			new + USB_KBD_BOOT_REPORT_SIZE)) {
-		res |= usb_kbd_translate(data, old[i], data->new[0], up);
-	}
-
-	return res;
-}
-
-static void usb_kbd_setled(struct usb_kbd_pdata *data)
-{
-	struct usb_device *usbdev = data->usbdev;
-	struct usb_interface *iface = &usbdev->config.interface[0];
-	uint8_t leds = (uint8_t)(data->flags & USB_KBD_LEDMASK);
-
-	usb_control_msg(usbdev, usb_sndctrlpipe(usbdev, 0),
-		USB_REQ_SET_REPORT, USB_TYPE_CLASS | USB_RECIP_INTERFACE,
-		0x200, iface->desc.bInterfaceNumber, &leds, 1, USB_CNTL_TIMEOUT);
-}
-
-
-static int usb_kbd_process(struct usb_kbd_pdata *data)
-{
-	int i, res = 0;
-
-	/* No combo key pressed */
-	if (data->new[0] == 0x00)
-		data->flags &= ~USB_KBD_CTRL;
-	/* Left or Right Ctrl pressed */
-	else if ((data->new[0] == LEFT_CNTR) || (data->new[0] == RIGHT_CNTR))
-		data->flags |= USB_KBD_CTRL;
-
-	for (i = 2; i < USB_KBD_BOOT_REPORT_SIZE; i++) {
-		res |= usb_kbd_service_key(data, i, 0);
-		res |= usb_kbd_service_key(data, i, 1);
-	}
-
-	/* Key is still pressed */
-	if ((data->new[2] > 3) && (data->old[2] == data->new[2]))
-		res |= usb_kbd_translate(data, data->new[2], data->new[0], 2);
-
-	if (res == 1)
-		usb_kbd_setled(data);
-
-	return 1;
-}
+static const unsigned char usb_kbd_keycode[256] = {
+	  0,  0,  0,  0, 30, 48, 46, 32, 18, 33, 34, 35, 23, 36, 37, 38,
+	 50, 49, 24, 25, 16, 19, 31, 20, 22, 47, 17, 45, 21, 44,  2,  3,
+	  4,  5,  6,  7,  8,  9, 10, 11, 28,  1, 14, 15, 57, 12, 13, 26,
+	 27, 43, 43, 39, 40, 41, 51, 52, 53, 58, 59, 60, 61, 62, 63, 64,
+	 65, 66, 67, 68, 87, 88, 99, 70,119,110,102,104,111,107,109,106,
+	105,108,103, 69, 98, 55, 74, 78, 96, 79, 80, 81, 75, 76, 77, 71,
+	 72, 73, 82, 83, 86,127,116,117,183,184,185,186,187,188,189,190,
+	191,192,193,194,134,138,130,132,128,129,131,137,133,135,136,113,
+	115,114,  0,  0,  0,121,  0, 89, 93,124, 92, 94, 95,  0,  0,  0,
+	122,123, 90, 91, 85,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
+	  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
+	  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
+	  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
+	  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
+	 29, 42, 56,125, 97, 54,100,126,164,166,165,163,161,115,114,113,
+	150,158,159,128,136,177,178,176,142,152,173,140
+};
 
 static void usb_kbd_poll(struct poller_struct *poller)
 {
 	struct usb_kbd_pdata *data = container_of(poller,
 						  struct usb_kbd_pdata, poller);
 	struct usb_device *usbdev = data->usbdev;
-	int diff, tout, ret;
+	int ret, i;
 
 	if (data->lock)
 		return;
-	data->lock = 1;
 
-	if (!is_timeout_non_interruptible(data->last_poll, REPEAT_RATE * MSECOND / 2))
-		goto exit;
-	data->last_poll = get_time_ns();
+	data->lock = 1;
 
 	ret = data->do_poll(data);
 	if (ret == -EAGAIN)
@@ -293,40 +115,40 @@ static void usb_kbd_poll(struct poller_struct *poller)
 			"usb_submit_int_msg() failed. Keyboard disconnect?\n");
 		return;
 	}
-	diff = memcmp(data->old, data->new, USB_KBD_BOOT_REPORT_SIZE);
-	tout = get_time_ns() > data->last_report + REPEAT_RATE * MSECOND;
-	if (diff || tout) {
-		data->last_report = get_time_ns();
-		if (diff) {
-			pr_debug("%s: old report: %016llx\n",
-				__func__,
-				*((volatile uint64_t *)data->old));
-			pr_debug("%s: new report: %016llx\n\n",
-				__func__,
-				*((volatile uint64_t *)data->new));
-		}
-		usb_kbd_process(data);
-		memcpy(data->old, data->new, USB_KBD_BOOT_REPORT_SIZE);
-	}
 
-exit:
-	data->lock = 0;
-}
+	if (!memcmp(data->old, data->new, USB_KBD_BOOT_REPORT_SIZE))
+		goto exit;
 
-static int usb_kbd_getc(struct console_device *cdev)
-{
-	int code = 0;
-	struct usb_kbd_pdata *data = container_of(cdev, struct usb_kbd_pdata, cdev);
+	pr_debug("%s: new report: %016llx\n", __func__, *((volatile uint64_t *)data->new));
 
-	kfifo_get(data->recv_fifo, (u_char*)&code, sizeof(int));
-	return code;
-}
+	for (i = 0; i < 8; i++)
+		input_report_key_event(&data->input, usb_kbd_keycode[i + 224], (data->new[0] >> i) & 1);
 
-static int usb_kbd_tstc(struct console_device *cdev)
-{
-	struct usb_kbd_pdata *data = container_of(cdev, struct usb_kbd_pdata, cdev);
+	for (i = 2; i < 8; i++) {
+
+		if (data->old[i] > 3 && memscan(data->new + 2, data->old[i], 6) == data->new + 8) {
+			if (usb_kbd_keycode[data->old[i]])
+				input_report_key_event(&data->input, usb_kbd_keycode[data->old[i]], 0);
+			else
+				dev_err(&usbdev->dev,
+					 "Unknown key (scancode %#x) released.\n",
+					 data->old[i]);
+		}
+
+		if (data->new[i] > 3 && memscan(data->old + 2, data->new[i], 6) == data->old + 8) {
+			if (usb_kbd_keycode[data->new[i]])
+				input_report_key_event(&data->input, usb_kbd_keycode[data->new[i]], 1);
+			else
+				dev_err(&usbdev->dev,
+					 "Unknown key (scancode %#x) pressed.\n",
+					 data->new[i]);
+		}
+	}
 
-	return (kfifo_len(data->recv_fifo) == 0) ? 0 : 1;
+	memcpy(data->old, data->new, 8);
+
+exit:
+	data->lock = 0;
 }
 
 static int usb_kbd_probe(struct usb_device *usbdev,
@@ -335,7 +157,6 @@ static int usb_kbd_probe(struct usb_device *usbdev,
 	int ret;
 	struct usb_interface *iface = &usbdev->config.interface[0];
 	struct usb_kbd_pdata *data;
-	struct console_device *cdev;
 
 	dev_info(&usbdev->dev, "USB keyboard found\n");
 	dev_dbg(&usbdev->dev, "Debug enabled\n");
@@ -349,7 +170,6 @@ static int usb_kbd_probe(struct usb_device *usbdev,
 
 	data = xzalloc(sizeof(struct usb_kbd_pdata));
 	usbdev->drv_data = data;
-	data->recv_fifo = kfifo_alloc(USB_KBD_FIFO_SIZE);
 	data->new = dma_alloc(USB_KBD_BOOT_REPORT_SIZE);
 
 	data->usbdev = usbdev;
@@ -371,7 +191,6 @@ static int usb_kbd_probe(struct usb_device *usbdev,
 		ret = data->do_poll(data);
 		if (ret < 0) {
 			/* no luck */
-			kfifo_free(data->recv_fifo);
 			dma_free(data->new);
 			free(data);
 			return ret;
@@ -380,16 +199,10 @@ static int usb_kbd_probe(struct usb_device *usbdev,
 	} else
 		dev_dbg(&usbdev->dev, "poll keyboard via int ep\n");
 
-	cdev = &data->cdev;
-	usbdev->dev.type_data = cdev;
-	cdev->dev = &usbdev->dev;
-	cdev->tstc = usb_kbd_tstc;
-	cdev->getc = usb_kbd_getc;
-
-	console_register(cdev);
-	console_set_active(cdev, CONSOLE_STDIN);
+	input_device_register(&data->input);
 
 	data->poller.func = usb_kbd_poll;
+
 	return poller_register(&data->poller);
 }
 
@@ -398,8 +211,7 @@ static void usb_kbd_disconnect(struct usb_device *usbdev)
 	struct usb_kbd_pdata *data = usbdev->drv_data;
 
 	poller_unregister(&data->poller);
-	console_unregister(&data->cdev);
-	kfifo_free(data->recv_fifo);
+	input_device_unregister(&data->input);
 	dma_free(data->new);
 	free(data);
 }
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 09/15] input: imx-keypad: Use dev_* functions
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (7 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 08/15] input: usb keyboard: convert to input framework Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 10/15] input: move matrix_keypad_build_keymap() to C file Sascha Hauer
                   ` (5 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

driver should use dev_* rather than pr_*

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/imx_keypad.c | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/drivers/input/imx_keypad.c b/drivers/input/imx_keypad.c
index 331eadd..272b836 100644
--- a/drivers/input/imx_keypad.c
+++ b/drivers/input/imx_keypad.c
@@ -228,7 +228,7 @@ static void imx_keypad_fire_events(struct imx_keypad *keypad,
 
 			kfifo_put(keypad->recv_fifo, (u_char*)(&keypad->keycodes[code]), sizeof(int));
 
-			pr_debug("Event code: %d, val: %d",
+			dev_dbg(keypad->dev, "Event code: %d, val: %d",
 				keypad->keycodes[code],
 				matrix_volatile_state[col] & (1 << row));
 		}
@@ -394,7 +394,7 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	int i;
 
 	if (!keymap_data) {
-		pr_err("no keymap defined\n");
+		dev_err(dev, "no keymap defined\n");
 		return -ENODEV;
 	}
 
@@ -418,12 +418,13 @@ static int __init imx_keypad_probe(struct device_d *dev)
 
 	if (keypad->rows_en_mask > ((1 << MAX_MATRIX_KEY_ROWS) - 1) ||
 	   keypad->cols_en_mask > ((1 << MAX_MATRIX_KEY_COLS) - 1)) {
-		pr_err("invalid key data (too many rows or colums)\n");
+		dev_err(dev, "invalid key data (too many rows or colums)\n");
 		free(keypad);
 		return -EINVAL;
 	}
-	pr_debug("enabled rows mask: %x\n", keypad->rows_en_mask);
-	pr_debug("enabled cols mask: %x\n", keypad->cols_en_mask);
+
+	dev_dbg(dev, "enabled rows mask: %x\n", keypad->rows_en_mask);
+	dev_dbg(dev, "enabled cols mask: %x\n", keypad->cols_en_mask);
 
 	matrix_keypad_build_keymap(keymap_data, MATRIX_ROW_SHIFT,
 				keypad->keycodes);
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 10/15] input: move matrix_keypad_build_keymap() to C file
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (8 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 09/15] input: imx-keypad: Use dev_* functions Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 11/15] input: imx-keypad: convert to input framework Sascha Hauer
                   ` (4 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Future additions will make the function too big to live as a static
inline function. Move to a C file and while at it, move matrix_keypad.h
to include/input/ where it belongs to.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 arch/arm/mach-imx/include/mach/devices.h |  2 +-
 drivers/input/Kconfig                    |  4 +++
 drivers/input/Makefile                   |  1 +
 drivers/input/imx_keypad.c               |  2 +-
 drivers/input/matrix-keymap.c            | 42 +++++++++++++++++++++++
 include/input/matrix_keypad.h            | 35 +++++++++++++++++++
 include/matrix_keypad.h                  | 59 --------------------------------
 7 files changed, 84 insertions(+), 61 deletions(-)
 create mode 100644 drivers/input/matrix-keymap.c
 create mode 100644 include/input/matrix_keypad.h
 delete mode 100644 include/matrix_keypad.h

diff --git a/arch/arm/mach-imx/include/mach/devices.h b/arch/arm/mach-imx/include/mach/devices.h
index 4c07f46..45bb0a5 100644
--- a/arch/arm/mach-imx/include/mach/devices.h
+++ b/arch/arm/mach-imx/include/mach/devices.h
@@ -1,6 +1,6 @@
 
 #include <fec.h>
-#include <matrix_keypad.h>
+#include <input/matrix_keypad.h>
 #include <i2c/i2c.h>
 #include <mach/spi.h>
 #include <mach/imx-nand.h>
diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig
index b840df2..24c3bd7 100644
--- a/drivers/input/Kconfig
+++ b/drivers/input/Kconfig
@@ -8,6 +8,9 @@ menu "Input device support"
 config INPUT
 	bool
 
+config INPUT_MATRIXKMAP
+	bool
+
 config KEYBOARD_GPIO
 	bool "GPIO Buttons"
 	depends on GENERIC_GPIO
@@ -24,6 +27,7 @@ config KEYBOARD_GPIO
 config KEYBOARD_IMX_KEYPAD
 	bool "IMX Keypad"
 	depends on ARCH_IMX
+	select INPUT_MATRIXKMAP
 	select POLLER
 	help
 	  This driver implements support for buttons connected
diff --git a/drivers/input/Makefile b/drivers/input/Makefile
index b9e5a5d..7d2c194 100644
--- a/drivers/input/Makefile
+++ b/drivers/input/Makefile
@@ -1,4 +1,5 @@
 obj-$(CONFIG_INPUT) += input.o
+obj-$(CONFIG_INPUT_MATRIXKMAP) += matrix-keymap.o
 obj-$(CONFIG_KEYBOARD_USB) += usb_kbd.o
 obj-$(CONFIG_KEYBOARD_GPIO) += gpio_keys.o
 obj-$(CONFIG_KEYBOARD_TWL6030) += twl6030_pwrbtn.o
diff --git a/drivers/input/imx_keypad.c b/drivers/input/imx_keypad.c
index 272b836..b0282f2 100644
--- a/drivers/input/imx_keypad.c
+++ b/drivers/input/imx_keypad.c
@@ -46,7 +46,7 @@
 #include <poller.h>
 #include <kfifo.h>
 #include <malloc.h>
-#include <matrix_keypad.h>
+#include <input/matrix_keypad.h>
 #include <linux/err.h>
 
 /*
diff --git a/drivers/input/matrix-keymap.c b/drivers/input/matrix-keymap.c
new file mode 100644
index 0000000..d56eccc
--- /dev/null
+++ b/drivers/input/matrix-keymap.c
@@ -0,0 +1,42 @@
+/*
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; version 2.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ */
+
+#include <common.h>
+#include <input/matrix_keypad.h>
+
+/**
+ * matrix_keypad_build_keymap - convert platform keymap into matrix keymap
+ * @keymap_data: keymap supplied by the platform code
+ * @row_shift: number of bits to shift row value by to advance to the next
+ * line in the keymap
+ * @keymap: expanded version of keymap that is suitable for use by
+ * matrix keyboad driver
+ * This function converts platform keymap (encoded with KEY() macro) into
+ * an array of keycodes that is suitable for using in a standard matrix
+ * keyboard driver that uses row and col as indices.
+ */
+int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
+			   unsigned int row_shift,
+			   unsigned short *keymap)
+{
+	int i;
+
+	for (i = 0; i < keymap_data->keymap_size; i++) {
+		unsigned int key = keymap_data->keymap[i];
+		unsigned int row = KEY_ROW(key);
+		unsigned int col = KEY_COL(key);
+		unsigned short code = KEY_VAL(key);
+
+		keymap[MATRIX_SCAN_CODE(row, col, row_shift)] = code;
+	}
+
+	return 0;
+}
diff --git a/include/input/matrix_keypad.h b/include/input/matrix_keypad.h
new file mode 100644
index 0000000..77b00c0
--- /dev/null
+++ b/include/input/matrix_keypad.h
@@ -0,0 +1,35 @@
+#ifndef _MATRIX_KEYPAD_H
+#define _MATRIX_KEYPAD_H
+
+#define MATRIX_MAX_ROWS		32
+#define MATRIX_MAX_COLS		32
+
+#define KEY(row, col, val)	((((row) & (MATRIX_MAX_ROWS - 1)) << 24) |\
+				 (((col) & (MATRIX_MAX_COLS - 1)) << 16) |\
+				 ((val) & 0xffff))
+
+#define KEY_ROW(k)		(((k) >> 24) & 0xff)
+#define KEY_COL(k)		(((k) >> 16) & 0xff)
+#define KEY_VAL(k)		((k) & 0xffff)
+
+#define MATRIX_SCAN_CODE(row, col, row_shift)	(((row) << (row_shift)) + (col))
+
+/**
+ * struct matrix_keymap_data - keymap for matrix keyboards
+ * @keymap: pointer to array of uint32 values encoded with KEY() macro
+ *	representing keymap
+ * @keymap_size: number of entries (initialized) in this keymap
+ *
+ * This structure is supposed to be used by platform code to supply
+ * keymaps to drivers that implement matrix-like keypads/keyboards.
+ */
+struct matrix_keymap_data {
+	const uint32_t *keymap;
+	unsigned int	keymap_size;
+};
+
+int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
+			   unsigned int row_shift,
+			   unsigned short *keymap);
+
+#endif /* _MATRIX_KEYPAD_H */
diff --git a/include/matrix_keypad.h b/include/matrix_keypad.h
deleted file mode 100644
index 60de428..0000000
--- a/include/matrix_keypad.h
+++ /dev/null
@@ -1,59 +0,0 @@
-#ifndef _MATRIX_KEYPAD_H
-#define _MATRIX_KEYPAD_H
-
-#define MATRIX_MAX_ROWS		32
-#define MATRIX_MAX_COLS		32
-
-#define KEY(row, col, val)	((((row) & (MATRIX_MAX_ROWS - 1)) << 24) |\
-				 (((col) & (MATRIX_MAX_COLS - 1)) << 16) |\
-				 ((val) & 0xffff))
-
-#define KEY_ROW(k)		(((k) >> 24) & 0xff)
-#define KEY_COL(k)		(((k) >> 16) & 0xff)
-#define KEY_VAL(k)		((k) & 0xffff)
-
-#define MATRIX_SCAN_CODE(row, col, row_shift)	(((row) << (row_shift)) + (col))
-
-/**
- * struct matrix_keymap_data - keymap for matrix keyboards
- * @keymap: pointer to array of uint32 values encoded with KEY() macro
- *	representing keymap
- * @keymap_size: number of entries (initialized) in this keymap
- *
- * This structure is supposed to be used by platform code to supply
- * keymaps to drivers that implement matrix-like keypads/keyboards.
- */
-struct matrix_keymap_data {
-	const uint32_t *keymap;
-	unsigned int	keymap_size;
-};
-
-/**
- * matrix_keypad_build_keymap - convert platform keymap into matrix keymap
- * @keymap_data: keymap supplied by the platform code
- * @row_shift: number of bits to shift row value by to advance to the next
- * line in the keymap
- * @keymap: expanded version of keymap that is suitable for use by
- * matrix keyboad driver
- * This function converts platform keymap (encoded with KEY() macro) into
- * an array of keycodes that is suitable for using in a standard matrix
- * keyboard driver that uses row and col as indices.
- */
-static inline void
-matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
-			   unsigned int row_shift,
-			   unsigned short *keymap)
-{
-	int i;
-
-	for (i = 0; i < keymap_data->keymap_size; i++) {
-		unsigned int key = keymap_data->keymap[i];
-		unsigned int row = KEY_ROW(key);
-		unsigned int col = KEY_COL(key);
-		unsigned short code = KEY_VAL(key);
-
-		keymap[MATRIX_SCAN_CODE(row, col, row_shift)] = code;
-	}
-}
-
-#endif /* _MATRIX_KEYPAD_H */
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 11/15] input: imx-keypad: convert to input framework
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (9 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 10/15] input: move matrix_keypad_build_keymap() to C file Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 12/15] input: Add device tree parsing support for matrix keymap Sascha Hauer
                   ` (3 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

To make it possible to ask for the button state.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/Kconfig      |  1 +
 drivers/input/imx_keypad.c | 55 ++++++++++------------------------------------
 2 files changed, 13 insertions(+), 43 deletions(-)

diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig
index 24c3bd7..7cc98f2 100644
--- a/drivers/input/Kconfig
+++ b/drivers/input/Kconfig
@@ -29,6 +29,7 @@ config KEYBOARD_IMX_KEYPAD
 	depends on ARCH_IMX
 	select INPUT_MATRIXKMAP
 	select POLLER
+	select INPUT
 	help
 	  This driver implements support for buttons connected
 	  to the IMX keypad matrix.
diff --git a/drivers/input/imx_keypad.c b/drivers/input/imx_keypad.c
index b0282f2..bc74d7d 100644
--- a/drivers/input/imx_keypad.c
+++ b/drivers/input/imx_keypad.c
@@ -48,6 +48,7 @@
 #include <malloc.h>
 #include <input/matrix_keypad.h>
 #include <linux/err.h>
+#include <input/input.h>
 
 /*
  * Keypad Controller registers (halfword)
@@ -73,15 +74,11 @@
 #define MAX_MATRIX_KEY_NUM	(MAX_MATRIX_KEY_ROWS * MAX_MATRIX_KEY_COLS)
 
 struct imx_keypad {
+	struct input_device input;
 	struct clk *clk;
 	struct device_d *dev;
-	struct console_device cdev;
 	void __iomem *mmio_base;
 
-	/* optional */
-	int fifo_size;
-
-	struct kfifo *recv_fifo;
 	struct poller_struct poller;
 
 	/*
@@ -112,28 +109,6 @@ poller_to_imx_kp_pdata(struct poller_struct *poller)
 	return container_of(poller, struct imx_keypad, poller);
 }
 
-static inline struct imx_keypad *
-cdev_to_imx_kp_pdata(struct console_device *cdev)
-{
-	return container_of(cdev, struct imx_keypad, cdev);
-}
-
-static int imx_keypad_tstc(struct console_device *cdev)
-{
-	struct imx_keypad *kp = cdev_to_imx_kp_pdata(cdev);
-
-	return (kfifo_len(kp->recv_fifo) == 0) ? 0 : 1;
-}
-
-static int imx_keypad_getc(struct console_device *cdev)
-{
-	int code = 0;
-	struct imx_keypad *kp = cdev_to_imx_kp_pdata(cdev);
-
-	kfifo_get(kp->recv_fifo, (u_char*)&code, sizeof(int));
-	return code;
-}
-
 /* Scan the matrix and return the new state in *matrix_volatile_state. */
 static void imx_keypad_scan_matrix(struct imx_keypad *keypad,
 				  unsigned short *matrix_volatile_state)
@@ -226,7 +201,8 @@ static void imx_keypad_fire_events(struct imx_keypad *keypad,
 
 			code = MATRIX_SCAN_CODE(row, col, MATRIX_ROW_SHIFT);
 
-			kfifo_put(keypad->recv_fifo, (u_char*)(&keypad->keycodes[code]), sizeof(int));
+			input_report_key_event(&keypad->input, keypad->keycodes[code],
+					       matrix_volatile_state[col] & (1 << row));
 
 			dev_dbg(keypad->dev, "Event code: %d, val: %d",
 				keypad->keycodes[code],
@@ -390,8 +366,7 @@ static int __init imx_keypad_probe(struct device_d *dev)
 {
 	struct imx_keypad *keypad;
 	const struct matrix_keymap_data *keymap_data = dev->platform_data;
-	struct console_device *cdev;
-	int i;
+	int i, ret;
 
 	if (!keymap_data) {
 		dev_err(dev, "no keymap defined\n");
@@ -405,11 +380,6 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	if (IS_ERR(keypad->mmio_base))
 		return PTR_ERR(keypad->mmio_base);
 
-	if(!keypad->fifo_size)
-		keypad->fifo_size = 50;
-
-	keypad->recv_fifo = kfifo_alloc(keypad->fifo_size);
-
 	/* Search for rows and cols enabled */
 	for (i = 0; i < keymap_data->keymap_size; i++) {
 		keypad->rows_en_mask |= 1 << KEY_ROW(keymap_data->keymap[i]);
@@ -436,16 +406,15 @@ static int __init imx_keypad_probe(struct device_d *dev)
 
 	keypad->poller.func = imx_keypad_check_for_events;
 
-	cdev = &keypad->cdev;
-	dev->type_data = cdev;
-	cdev->dev = dev;
-	cdev->tstc = imx_keypad_tstc;
-	cdev->getc = imx_keypad_getc;
-	cdev->f_active = CONSOLE_STDIN;
+	ret = poller_register(&keypad->poller);
+	if (ret)
+		return ret;
 
-	console_register(&keypad->cdev);
+	ret = input_device_register(&keypad->input);
+	if (ret)
+		return ret;
 
-	return poller_register(&keypad->poller);
+	return 0;
 }
 
 static struct driver_d imx_keypad_driver = {
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 12/15] input: Add device tree parsing support for matrix keymap
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (10 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 11/15] input: imx-keypad: convert to input framework Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 13/15] input: imx-keypad: Add device tree support Sascha Hauer
                   ` (2 subsequent siblings)
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

Add support for parsing the "linux,keymap" property.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/imx_keypad.c    |  4 +++-
 drivers/input/matrix-keymap.c | 49 ++++++++++++++++++++++++++++++++++++++++++-
 include/input/matrix_keypad.h |  6 +++---
 3 files changed, 54 insertions(+), 5 deletions(-)

diff --git a/drivers/input/imx_keypad.c b/drivers/input/imx_keypad.c
index bc74d7d..d3b5a85 100644
--- a/drivers/input/imx_keypad.c
+++ b/drivers/input/imx_keypad.c
@@ -396,8 +396,10 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	dev_dbg(dev, "enabled rows mask: %x\n", keypad->rows_en_mask);
 	dev_dbg(dev, "enabled cols mask: %x\n", keypad->cols_en_mask);
 
-	matrix_keypad_build_keymap(keymap_data, MATRIX_ROW_SHIFT,
+	ret = matrix_keypad_build_keymap(dev, keymap_data, MATRIX_ROW_SHIFT,
 				keypad->keycodes);
+	if (ret)
+		return ret;
 
 	imx_keypad_config(keypad);
 
diff --git a/drivers/input/matrix-keymap.c b/drivers/input/matrix-keymap.c
index d56eccc..288b6a4 100644
--- a/drivers/input/matrix-keymap.c
+++ b/drivers/input/matrix-keymap.c
@@ -12,6 +12,47 @@
 #include <common.h>
 #include <input/matrix_keypad.h>
 
+static int matrix_keypad_parse_of_keymap(struct device_d *dev,
+					 unsigned int row_shift,
+					 unsigned short *keymap)
+{
+	unsigned int proplen, i, size;
+	const __be32 *prop;
+	struct device_node *np = dev->device_node;
+	const char *propname = "linux,keymap";
+
+	prop = of_get_property(np, propname, &proplen);
+	if (!prop) {
+		dev_err(dev, "OF: %s property not defined in %s\n",
+			propname, np->full_name);
+		return -ENOENT;
+	}
+
+	if (proplen % sizeof(u32)) {
+		dev_err(dev, "OF: Malformed keycode property %s in %s\n",
+			propname, np->full_name);
+		return -EINVAL;
+	}
+
+	size = proplen / sizeof(u32);
+
+	for (i = 0; i < size; i++) {
+		unsigned int key = be32_to_cpup(prop + i);
+
+		unsigned int row = KEY_ROW(key);
+		unsigned int col = KEY_COL(key);
+		unsigned short code = KEY_VAL(key);
+
+		if (row >= MATRIX_MAX_ROWS || col >= MATRIX_MAX_COLS) {
+			dev_err(dev, "rows/cols out of range\n");
+			continue;
+		}
+
+		keymap[MATRIX_SCAN_CODE(row, col, row_shift)] = code;
+	}
+
+	return 0;
+}
 /**
  * matrix_keypad_build_keymap - convert platform keymap into matrix keymap
  * @keymap_data: keymap supplied by the platform code
@@ -23,12 +64,18 @@
  * an array of keycodes that is suitable for using in a standard matrix
  * keyboard driver that uses row and col as indices.
  */
-int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
+int matrix_keypad_build_keymap(struct device_d *dev, const struct matrix_keymap_data *keymap_data,
 			   unsigned int row_shift,
 			   unsigned short *keymap)
 {
 	int i;
 
+	if (IS_ENABLED(CONFIG_OFDEVICE) && dev->device_node)
+		return matrix_keypad_parse_of_keymap(dev, row_shift, keymap);
+
+	if (!keymap_data)
+		return -EINVAL;
+
 	for (i = 0; i < keymap_data->keymap_size; i++) {
 		unsigned int key = keymap_data->keymap[i];
 		unsigned int row = KEY_ROW(key);
diff --git a/include/input/matrix_keypad.h b/include/input/matrix_keypad.h
index 77b00c0..03d963a 100644
--- a/include/input/matrix_keypad.h
+++ b/include/input/matrix_keypad.h
@@ -28,8 +28,8 @@ struct matrix_keymap_data {
 	unsigned int	keymap_size;
 };
 
-int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
-			   unsigned int row_shift,
-			   unsigned short *keymap);
+int matrix_keypad_build_keymap(struct device_d *dev,
+			       const struct matrix_keymap_data *keymap_data,
+			       unsigned int row_shift, unsigned short *keymap);
 
 #endif /* _MATRIX_KEYPAD_H */
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 13/15] input: imx-keypad: Add device tree support
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (11 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 12/15] input: Add device tree parsing support for matrix keymap Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 14/15] input: gpio-keys: Use KEY_* keycodes Sascha Hauer
  2016-01-13 15:37 ` [PATCH 15/15] input: gpio-keys: convert to input framework Sascha Hauer
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

The preparations are done in previous patches, now we only have
to add the device tree compatible and drio the check for platform_data.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/imx_keypad.c | 34 ++++++++++++++++++++--------------
 1 file changed, 20 insertions(+), 14 deletions(-)

diff --git a/drivers/input/imx_keypad.c b/drivers/input/imx_keypad.c
index d3b5a85..000e176 100644
--- a/drivers/input/imx_keypad.c
+++ b/drivers/input/imx_keypad.c
@@ -366,12 +366,7 @@ static int __init imx_keypad_probe(struct device_d *dev)
 {
 	struct imx_keypad *keypad;
 	const struct matrix_keymap_data *keymap_data = dev->platform_data;
-	int i, ret;
-
-	if (!keymap_data) {
-		dev_err(dev, "no keymap defined\n");
-		return -ENODEV;
-	}
+	int i, ret, row, col;
 
 	keypad = xzalloc(sizeof(struct imx_keypad));
 
@@ -380,10 +375,20 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	if (IS_ERR(keypad->mmio_base))
 		return PTR_ERR(keypad->mmio_base);
 
+	ret = matrix_keypad_build_keymap(dev, keymap_data, MATRIX_ROW_SHIFT,
+				keypad->keycodes);
+	if (ret)
+		return ret;
+
 	/* Search for rows and cols enabled */
-	for (i = 0; i < keymap_data->keymap_size; i++) {
-		keypad->rows_en_mask |= 1 << KEY_ROW(keymap_data->keymap[i]);
-		keypad->cols_en_mask |= 1 << KEY_COL(keymap_data->keymap[i]);
+	for (row = 0; row < MAX_MATRIX_KEY_ROWS; row++) {
+		for (col = 0; col < MAX_MATRIX_KEY_COLS; col++) {
+			i = MATRIX_SCAN_CODE(row, col, MATRIX_ROW_SHIFT);
+			if (keypad->keycodes[i] != KEY_RESERVED) {
+				keypad->rows_en_mask |= 1 << row;
+				keypad->cols_en_mask |= 1 << col;
+			}
+		}
 	}
 
 	if (keypad->rows_en_mask > ((1 << MAX_MATRIX_KEY_ROWS) - 1) ||
@@ -396,11 +401,6 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	dev_dbg(dev, "enabled rows mask: %x\n", keypad->rows_en_mask);
 	dev_dbg(dev, "enabled cols mask: %x\n", keypad->cols_en_mask);
 
-	ret = matrix_keypad_build_keymap(dev, keymap_data, MATRIX_ROW_SHIFT,
-				keypad->keycodes);
-	if (ret)
-		return ret;
-
 	imx_keypad_config(keypad);
 
 	/* Ensure that the keypad will stay dormant until opened */
@@ -419,8 +419,14 @@ static int __init imx_keypad_probe(struct device_d *dev)
 	return 0;
 }
 
+static __maybe_unused struct of_device_id imx_keypad_dt_ids[] = {
+        { .compatible = "fsl,imx21-kpp", },
+        { }
+};
+
 static struct driver_d imx_keypad_driver = {
 	.name   = "imx-kpp",
 	.probe  = imx_keypad_probe,
+	.of_compatible = DRV_OF_COMPAT(imx_keypad_dt_ids),
 };
 device_platform_driver(imx_keypad_driver);
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 14/15] input: gpio-keys: Use KEY_* keycodes
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (12 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 13/15] input: imx-keypad: Add device tree support Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  2016-01-13 15:37 ` [PATCH 15/15] input: gpio-keys: convert to input framework Sascha Hauer
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

The gpio-keys driver takes ascii key codes from platform_data and Linux
keycodes from device tree. Convert the ascii keys over to Linux
keycodes to get rid of the special cases in the driver.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 arch/arm/boards/archosg9/board.c        |  5 +++--
 arch/arm/boards/at91sam9261ek/init.c    |  7 ++++---
 arch/arm/boards/at91sam9m10g45ek/init.c | 15 ++++++++-------
 arch/arm/boards/usb-a926x/init.c        |  9 +++++----
 drivers/input/gpio_keys.c               |  9 +--------
 5 files changed, 21 insertions(+), 24 deletions(-)

diff --git a/arch/arm/boards/archosg9/board.c b/arch/arm/boards/archosg9/board.c
index f80714e..6f82f5e 100644
--- a/arch/arm/boards/archosg9/board.c
+++ b/arch/arm/boards/archosg9/board.c
@@ -26,6 +26,7 @@
 #include <gpio_keys.h>
 #include <twl6030_pwrbtn.h>
 #include <readkey.h>
+#include <input/input.h>
 #include "archos_features.h"
 
 #define GPIO_LCD_PWON     38
@@ -72,8 +73,8 @@ static struct twl6030_pwrbtn_platform_data pwrbtn_data = {
 	.code = BB_KEY_ENTER
 };
 static struct gpio_keys_button keys[] = {
-	{ .code = BB_KEY_UP  , .gpio = 43, .active_low = 1 },
-	{ .code = BB_KEY_DOWN, .gpio = 44, .active_low = 1 },
+	{ .code = KEY_UP  , .gpio = 43, .active_low = 1 },
+	{ .code = KEY_DOWN, .gpio = 44, .active_low = 1 },
 };
 static struct gpio_keys_platform_data gk_data = {
 	.buttons = keys,
diff --git a/arch/arm/boards/at91sam9261ek/init.c b/arch/arm/boards/at91sam9261ek/init.c
index a0b0219..6cb1701 100644
--- a/arch/arm/boards/at91sam9261ek/init.c
+++ b/arch/arm/boards/at91sam9261ek/init.c
@@ -39,6 +39,7 @@
 #include <readkey.h>
 #include <led.h>
 #include <spi/spi.h>
+#include <input/input.h>
 
 static struct atmel_nand_data nand_pdata = {
 	.ale		= 22,
@@ -235,13 +236,13 @@ static void ek_add_device_lcdc(void) {}
 #ifdef CONFIG_KEYBOARD_GPIO
 struct gpio_keys_button keys[] = {
 	{
-		.code = BB_KEY_UP,
+		.code = KEY_UP,
 		.gpio = AT91_PIN_PA26,
 	}, {
-		.code = BB_KEY_DOWN,
+		.code = KEY_DOWN,
 		.gpio = AT91_PIN_PA25,
 	}, {
-		.code = BB_KEY_ENTER,
+		.code = KEY_ENTER,
 		.gpio = AT91_PIN_PA24,
 	},
 };
diff --git a/arch/arm/boards/at91sam9m10g45ek/init.c b/arch/arm/boards/at91sam9m10g45ek/init.c
index e00908b..fb444d8 100644
--- a/arch/arm/boards/at91sam9m10g45ek/init.c
+++ b/arch/arm/boards/at91sam9m10g45ek/init.c
@@ -40,6 +40,7 @@
 #include <gpio_keys.h>
 #include <readkey.h>
 #include <spi/spi.h>
+#include <input/input.h>
 
 /*
  * board revision encoding
@@ -183,25 +184,25 @@ static void ek_device_add_leds(void) {}
 #ifdef CONFIG_KEYBOARD_GPIO
 struct gpio_keys_button keys[] = {
 	{
-		.code = BB_KEY_HOME,
+		.code = KEY_HOME,
 		.gpio = AT91_PIN_PB6,
 	}, {
-		.code = BB_KEY_RETURN,
+		.code = KEY_ENTER,
 		.gpio = AT91_PIN_PB7,
 	}, {
-		.code = BB_KEY_LEFT,
+		.code = KEY_LEFT,
 		.gpio = AT91_PIN_PB14,
 	}, {
-		.code = BB_KEY_RIGHT,
+		.code = KEY_RIGHT,
 		.gpio = AT91_PIN_PB15,
 	}, {
-		.code = BB_KEY_UP,
+		.code = KEY_UP,
 		.gpio = AT91_PIN_PB16,
 	}, {
-		.code = BB_KEY_DOWN,
+		.code = KEY_DOWN,
 		.gpio = AT91_PIN_PB17,
 	}, {
-		.code = BB_KEY_RETURN,
+		.code = KEY_ENTER,
 		.gpio = AT91_PIN_PB18,
 	},
 };
diff --git a/arch/arm/boards/usb-a926x/init.c b/arch/arm/boards/usb-a926x/init.c
index 958c3c3..a9a0549 100644
--- a/arch/arm/boards/usb-a926x/init.c
+++ b/arch/arm/boards/usb-a926x/init.c
@@ -41,6 +41,7 @@
 #include <gpio_keys.h>
 #include <readkey.h>
 #include <spi/spi.h>
+#include <input/input.h>
 
 static void usb_a9260_set_board_type(void)
 {
@@ -340,16 +341,16 @@ struct gpio_led dab_mmx_leds[] = {
 #ifdef CONFIG_KEYBOARD_GPIO
 struct gpio_keys_button keys[] = {
 	{
-		.code = BB_KEY_UP,
+		.code = KEY_UP,
 		.gpio = AT91_PIN_PB25,
 	}, {
-		.code = BB_KEY_HOME,
+		.code = KEY_HOME,
 		.gpio = AT91_PIN_PB13,
 	}, {
-		.code = BB_KEY_DOWN,
+		.code = KEY_DOWN,
 		.gpio = AT91_PIN_PA26,
 	}, {
-		.code = BB_KEY_ENTER,
+		.code = KEY_ENTER,
 		.gpio = AT91_PIN_PC9,
 	},
 };
diff --git a/drivers/input/gpio_keys.c b/drivers/input/gpio_keys.c
index 5b03fd7..acb9e07 100644
--- a/drivers/input/gpio_keys.c
+++ b/drivers/input/gpio_keys.c
@@ -36,8 +36,6 @@ struct gpio_keys {
 	struct kfifo *recv_fifo;
 	struct poller_struct poller;
 	struct console_device cdev;
-
-	int use_keycodes;
 };
 
 static inline struct gpio_keys *
@@ -91,10 +89,7 @@ static int gpio_keys_getc(struct console_device *cdev)
 
 	kfifo_get(gk->recv_fifo, (u_char*)&code, sizeof(int));
 
-	if (IS_ENABLED(CONFIG_OFDEVICE) && gk->use_keycodes)
-		return keycode_bb_keys[code];
-	else
-		return code;
+	return keycode_bb_keys[code];
 }
 
 static int gpio_keys_probe_pdata(struct gpio_keys *gk, struct device_d *dev)
@@ -162,8 +157,6 @@ static int gpio_keys_probe_dt(struct gpio_keys *gk, struct device_d *dev)
 		i++;
 	}
 
-	gk->use_keycodes = 1;
-
 	return 0;
 }
 
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH 15/15] input: gpio-keys: convert to input framework
  2016-01-13 15:37 [PATCH] input core Sascha Hauer
                   ` (13 preceding siblings ...)
  2016-01-13 15:37 ` [PATCH 14/15] input: gpio-keys: Use KEY_* keycodes Sascha Hauer
@ 2016-01-13 15:37 ` Sascha Hauer
  14 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2016-01-13 15:37 UTC (permalink / raw)
  To: Barebox List

To allow asking for the button states.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/input/gpio_keys.c | 64 +++++++++++++----------------------------------
 1 file changed, 17 insertions(+), 47 deletions(-)

diff --git a/drivers/input/gpio_keys.c b/drivers/input/gpio_keys.c
index acb9e07..38c0f11 100644
--- a/drivers/input/gpio_keys.c
+++ b/drivers/input/gpio_keys.c
@@ -12,7 +12,7 @@
 #include <poller.h>
 #include <gpio.h>
 #include <of_gpio.h>
-#include <input/keyboard.h>
+#include <input/input.h>
 
 struct gpio_key {
 	int code;
@@ -30,12 +30,9 @@ struct gpio_keys {
 	struct gpio_key *buttons;
 	int nbuttons;
 
-	/* optional */
-	int fifo_size;
-
-	struct kfifo *recv_fifo;
 	struct poller_struct poller;
-	struct console_device cdev;
+	struct input_device input;
+	struct device_d *dev;
 };
 
 static inline struct gpio_keys *
@@ -44,12 +41,6 @@ poller_to_gk_pdata(struct poller_struct *poller)
 	return container_of(poller, struct gpio_keys, poller);
 }
 
-static inline struct gpio_keys *
-cdev_to_gk_pdata(struct console_device *cdev)
-{
-	return container_of(cdev, struct gpio_keys, cdev);
-}
-
 static void gpio_key_poller(struct poller_struct *poller)
 {
 	struct gpio_keys *gk = poller_to_gk_pdata(poller);
@@ -65,33 +56,17 @@ static void gpio_key_poller(struct poller_struct *poller)
 			continue;
 
 		if (val != gb->previous_state) {
+			int pressed = val != gb->active_low;
+
 			gb->debounce_start = get_time_ns();
-			if (val != gb->active_low) {
-				kfifo_put(gk->recv_fifo, (u_char*)&gb->code, sizeof(int));
-				debug("pressed gpio(%d) as %d\n", gb->gpio, gb->code);
-			}
+			input_report_key_event(&gk->input, gb->code, pressed);
+			dev_dbg(gk->dev, "%s gpio(%d) as %d\n",
+				pressed ? "pressed" : "released", gb->gpio, gb->code);
 			gb->previous_state = val;
 		}
 	}
 }
 
-static int gpio_keys_tstc(struct console_device *cdev)
-{
-	struct gpio_keys *gk = cdev_to_gk_pdata(cdev);
-
-	return (kfifo_len(gk->recv_fifo) == 0) ? 0 : 1;
-}
-
-static int gpio_keys_getc(struct console_device *cdev)
-{
-	int code = 0;
-	struct gpio_keys *gk = cdev_to_gk_pdata(cdev);
-
-	kfifo_get(gk->recv_fifo, (u_char*)&code, sizeof(int));
-
-	return keycode_bb_keys[code];
-}
-
 static int gpio_keys_probe_pdata(struct gpio_keys *gk, struct device_d *dev)
 {
 	struct gpio_keys_platform_data *pdata;
@@ -105,9 +80,6 @@ static int gpio_keys_probe_pdata(struct gpio_keys *gk, struct device_d *dev)
 		return -ENODEV;
 	}
 
-	if (pdata->fifo_size)
-		gk->fifo_size = pdata->fifo_size;
-
 	gk->buttons = xzalloc(pdata->nbuttons * sizeof(*gk->buttons));
 	gk->nbuttons = pdata->nbuttons;
 
@@ -163,11 +135,11 @@ static int gpio_keys_probe_dt(struct gpio_keys *gk, struct device_d *dev)
 static int __init gpio_keys_probe(struct device_d *dev)
 {
 	int ret, i, gpio;
-	struct console_device *cdev;
 	struct gpio_keys *gk;
 
 	gk = xzalloc(sizeof(*gk));
-	gk->fifo_size = 50;
+
+	gk->dev = dev;
 
 	if (dev->device_node)
 		ret = gpio_keys_probe_dt(gk, dev);
@@ -177,8 +149,6 @@ static int __init gpio_keys_probe(struct device_d *dev)
 	if (ret)
 		return ret;
 
-	gk->recv_fifo = kfifo_alloc(gk->fifo_size);
-
 	for (i = 0; i < gk->nbuttons; i++) {
 		gpio = gk->buttons[i].gpio;
 		ret = gpio_request(gpio, "gpio_keys");
@@ -192,15 +162,15 @@ static int __init gpio_keys_probe(struct device_d *dev)
 
 	gk->poller.func = gpio_key_poller;
 
-	cdev = &gk->cdev;
-	dev->type_data = cdev;
-	cdev->dev = dev;
-	cdev->tstc = gpio_keys_tstc;
-	cdev->getc = gpio_keys_getc;
+	ret = input_device_register(&gk->input);
+	if (ret)
+		return ret;
 
-	console_register(&gk->cdev);
+	ret = poller_register(&gk->poller);
+	if (ret)
+		return ret;
 
-	return poller_register(&gk->poller);
+	return 0;
 }
 
 static struct of_device_id key_gpio_of_ids[] = {
-- 
2.6.4


_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH 07/15] input: Add input core
  2016-01-13 15:37 ` [PATCH 07/15] input: Add input core Sascha Hauer
@ 2017-05-05 10:05   ` Antony Pavlov
  2017-05-05 11:10     ` Sascha Hauer
  0 siblings, 1 reply; 18+ messages in thread
From: Antony Pavlov @ 2017-05-05 10:05 UTC (permalink / raw)
  To: Sascha Hauer; +Cc: Barebox List

On Wed, 13 Jan 2016 16:37:28 +0100
Sascha Hauer <s.hauer@pengutronix.de> wrote:

Hi Sascha!

> Currently all input driver register themselves as consoles. Consoles are
> fine for typing text, but they do not allow to ask for the current
> pressed state of buttons or keypads. They also do not support non
> printable keys like the function keys.
> 
> This patch adds a simple input core. On the driver side it supports
> input_report_key_event() to report events (button presses and releases).
> On the consumer side it allows getting the current button status via
> input_key_get_status(). Also an event driven interface is available

It looks like there is no input_key_get_status() user in barebox-v2017.05.0 ...

> which calls a callback whenever an input event is received.
> The input core also registers a console for all registered input
> devices which handles passing events to the console and stuff like key
> repetition, so this can be removed from the drivers once they are
> converted to the input core.
> 
> Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
> ---
>  drivers/input/Kconfig  |   3 +
>  drivers/input/Makefile |   1 +
>  drivers/input/input.c  | 202 +++++++++++++++++++++++++++++++++++++++++++++++++
>  include/input/input.h  |  34 +++++++++
>  4 files changed, 240 insertions(+)
>  create mode 100644 drivers/input/input.c
>  create mode 100644 include/input/input.h
> 
> diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig
> index 336b9f5..e0368b2 100644
> --- a/drivers/input/Kconfig
> +++ b/drivers/input/Kconfig
> @@ -5,6 +5,9 @@
>  menu "Input device support"
>  	depends on !CONSOLE_NONE
>  
> +config INPUT
> +	bool
> +
>  config KEYBOARD_GPIO
>  	bool "GPIO Buttons"
>  	depends on GENERIC_GPIO
> diff --git a/drivers/input/Makefile b/drivers/input/Makefile
> index 40b898c..b9e5a5d 100644
> --- a/drivers/input/Makefile
> +++ b/drivers/input/Makefile
> @@ -1,3 +1,4 @@
> +obj-$(CONFIG_INPUT) += input.o
>  obj-$(CONFIG_KEYBOARD_USB) += usb_kbd.o
>  obj-$(CONFIG_KEYBOARD_GPIO) += gpio_keys.o
>  obj-$(CONFIG_KEYBOARD_TWL6030) += twl6030_pwrbtn.o
> diff --git a/drivers/input/input.c b/drivers/input/input.c
> new file mode 100644
> index 0000000..ad7400f
> --- /dev/null
> +++ b/drivers/input/input.c
> @@ -0,0 +1,202 @@
> +/*
> + * This program is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU General Public License as
> + * published by the Free Software Foundation; version 2.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
> + * General Public License for more details.
> + */
> +
> +#include <common.h>
> +#include <init.h>
> +#include <kfifo.h>
> +#include <poller.h>
> +#include <clock.h>
> +#include <input/input.h>
> +#include <linux/bitmap.h>
> +#include <input/keyboard.h>
> +#include <dt-bindings/input/linux-event-codes.h>
> +
> +static LIST_HEAD(input_consumers);
> +
> +int input_register_notfier(struct input_notifier *in)
> +{
> +	list_add_tail(&in->list, &input_consumers);
> +
> +	return 0;
> +}
> +
> +void input_unregister_notfier(struct input_notifier *in)
> +{
> +	list_del(&in->list);
> +}
> +
> +void input_report_key_event(struct input_device *idev, unsigned int code, int value)
> +{
> +	struct input_event event;
> +	struct input_notifier *in;
> +
> +	if (code > KEY_MAX)
> +		return;
> +
> +	if (value)
> +		set_bit(code, &idev->keys);
> +	else
> +		clear_bit(code, &idev->keys);
> +
> +	event.code = code;
> +	event.value = value;
> +
> +	list_for_each_entry(in, &input_consumers, list)
> +		in->notify(in, &event);
> +}
> +
> +static LIST_HEAD(input_devices);
> +
> +int input_device_register(struct input_device *idev)
> +{
> +	list_add_tail(&idev->list, &input_devices);
> +
> +	return 0;
> +}
> +
> +void input_device_unregister(struct input_device *idev)
> +{
> +	list_del(&idev->list);
> +}
> +
> +void input_key_get_status(unsigned long *keys, int bits)
> +{
> +	struct input_device *idev;
> +
> +	bitmap_zero(keys, bits);
> +
> +	if (bits > KEY_MAX)
> +		bits = KEY_MAX;
> +
> +	list_for_each_entry(idev, &input_devices, list)
> +		bitmap_or(keys, keys, idev->keys, bits);
> +}
> +
> +struct input_console {
> +	struct console_device console;
> +	struct input_notifier notifier;
> +	struct kfifo *fifo;
> +	struct poller_async poller;
> +	uint8_t current_key;
> +	uint8_t modstate[6];
> +};
> +
> +static int input_console_tstc(struct console_device *cdev)
> +{
> +	struct input_console *ic = container_of(cdev, struct input_console, console);
> +
> +	return kfifo_len(ic->fifo) ? 1 : 0;
> +}
> +
> +static int input_console_getc(struct console_device *cdev)
> +{
> +	struct input_console *ic = container_of(cdev, struct input_console, console);
> +	uint8_t c;
> +
> +	kfifo_getc(ic->fifo, &c);
> +
> +	return c;
> +}
> +
> +static void input_console_repeat(void *ctx)
> +{
> +	struct input_console *ic = ctx;
> +
> +	if (ic->current_key) {
> +		kfifo_putc(ic->fifo, ic->current_key);
> +		poller_call_async(&ic->poller, 40 * MSECOND,
> +				  input_console_repeat, ic);
> +	}
> +}
> +
> +struct keycode {
> +	unsigned char key;
> +	unsigned char ascii;
> +};
> +
> +static void input_console_notify(struct input_notifier *in,
> +				 struct input_event *ev)
> +{
> +	struct input_console *ic = container_of(in, struct input_console, notifier);
> +	uint8_t modstate = 0;
> +	unsigned char ascii;
> +
> +	switch (ev->code) {
> +	case KEY_LEFTSHIFT:
> +		ic->modstate[0] = ev->value;
> +		return;
> +	case KEY_RIGHTSHIFT:
> +		ic->modstate[1] = ev->value;
> +		return;
> +	case KEY_LEFTCTRL:
> +		ic->modstate[2] = ev->value;
> +		return;
> +	case KEY_RIGHTCTRL:
> +		ic->modstate[3] = ev->value;
> +		return;
> +	case KEY_LEFTALT:
> +		ic->modstate[4] = ev->value;
> +		return;
> +	case KEY_RIGHTALT:
> +		ic->modstate[5] = ev->value;
> +		return;
> +	case KEY_LEFTMETA:
> +	case KEY_RIGHTMETA:
> +		return;
> +	default:
> +		break;
> +	}
> +
> +	if (ic->modstate[0] || ic->modstate[1])
> +		modstate |= 1 << 0;
> +
> +	if (ic->modstate[2] || ic->modstate[3])
> +		modstate |= 1 << 1;
> +
> +	if (ic->modstate[4] || ic->modstate[5])
> +		modstate |= 1 << 2;
> +
> +	if (modstate & (1 << 0))
> +		ascii = keycode_bb_shift_keys[ev->code];
> +	else
> +		ascii = keycode_bb_keys[ev->code];
> +
> +	pr_debug("map %02x KEY: 0x%04x code: %d\n", modstate, ascii, ev->code);
> +
> +	if (ev->value) {
> +		kfifo_putc(ic->fifo, ascii);
> +		ic->current_key = ascii;
> +		poller_call_async(&ic->poller, 400 * MSECOND,
> +				  input_console_repeat, ic);
> +	} else {
> +		ic->current_key = 0;
> +		poller_async_cancel(&ic->poller);
> +	}
> +}
> +
> +static struct input_console input_console;
> +
> +static int input_init(void)
> +{
> +	struct input_console *ic = &input_console;
> +
> +	ic->console.tstc = input_console_tstc;
> +	ic->console.getc = input_console_getc;
> +	ic->console.f_active = CONSOLE_STDIN;
> +
> +	ic->fifo = kfifo_alloc(32);
> +	ic->notifier.notify = input_console_notify;
> +	input_register_notfier(&ic->notifier);
> +	poller_async_register(&ic->poller);
> +
> +	return console_register(&ic->console);
> +}
> +console_initcall(input_init);
> diff --git a/include/input/input.h b/include/input/input.h
> new file mode 100644
> index 0000000..dbf3e7f
> --- /dev/null
> +++ b/include/input/input.h
> @@ -0,0 +1,34 @@
> +#ifndef __INPUT_H
> +#define __INPUT_H
> +
> +#include <linux/types.h>
> +#include <linux/list.h>
> +#include <dt-bindings/input/linux-event-codes.h>
> +
> +struct input_event {
> +	uint16_t code;
> +	uint16_t value;
> +};
> +
> +struct input_device {
> +	struct list_head list;
> +	DECLARE_BITMAP(keys, KEY_CNT);
> +};
> +
> +void input_report_key_event(struct input_device *idev, unsigned int code, int value);
> +
> +int input_device_register(struct input_device *);
> +void input_device_unregister(struct input_device *);
> +
> +void input_key_get_status(unsigned long *keys, int bits);
> +
> +struct input_notifier {
> +	void (*notify)(struct input_notifier *in, struct input_event *event);
> +	struct list_head list;
> +};
> +
> +int input_register_notfier(struct input_notifier *in);
> +void input_unregister_notfier(struct input_notifier *in);
> +
> +#endif /* __INPUT_H */
> +
> -- 
> 2.6.4
> 
> 
> _______________________________________________
> barebox mailing list
> barebox@lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/barebox


-- 
Best regards,
  Antony Pavlov

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH 07/15] input: Add input core
  2017-05-05 10:05   ` Antony Pavlov
@ 2017-05-05 11:10     ` Sascha Hauer
  0 siblings, 0 replies; 18+ messages in thread
From: Sascha Hauer @ 2017-05-05 11:10 UTC (permalink / raw)
  To: Antony Pavlov; +Cc: Barebox List

On Fri, May 05, 2017 at 01:05:20PM +0300, Antony Pavlov wrote:
> On Wed, 13 Jan 2016 16:37:28 +0100
> Sascha Hauer <s.hauer@pengutronix.de> wrote:
> 
> Hi Sascha!
> 
> > Currently all input driver register themselves as consoles. Consoles are
> > fine for typing text, but they do not allow to ask for the current
> > pressed state of buttons or keypads. They also do not support non
> > printable keys like the function keys.
> > 
> > This patch adds a simple input core. On the driver side it supports
> > input_report_key_event() to report events (button presses and releases).
> > On the consumer side it allows getting the current button status via
> > input_key_get_status(). Also an event driven interface is available
> 
> It looks like there is no input_key_get_status() user in barebox-v2017.05.0 ...

Indeed not. This interface is for boards which want to check for certain
buttons for alternative boot modes. No board in mainline currently does
this.

Sascha

-- 
Pengutronix e.K.                           |                             |
Industrial Linux Solutions                 | http://www.pengutronix.de/  |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox

^ permalink raw reply	[flat|nested] 18+ messages in thread

end of thread, other threads:[~2017-05-05 11:11 UTC | newest]

Thread overview: 18+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-01-13 15:37 [PATCH] input core Sascha Hauer
2016-01-13 15:37 ` [PATCH 01/15] poller: Fix async poller Sascha Hauer
2016-01-13 15:37 ` [PATCH 02/15] keymap: Fix braces Sascha Hauer
2016-01-13 15:37 ` [PATCH 03/15] keymap: remove exotic and nonprintable keys Sascha Hauer
2016-01-13 15:37 ` [PATCH 04/15] keymap: Add keypad keys Sascha Hauer
2016-01-13 15:37 ` [PATCH 05/15] keymap: Add apostrophe, backslash and home Sascha Hauer
2016-01-13 15:37 ` [PATCH 06/15] keymap: Add keymap for keys with shift pressed Sascha Hauer
2016-01-13 15:37 ` [PATCH 07/15] input: Add input core Sascha Hauer
2017-05-05 10:05   ` Antony Pavlov
2017-05-05 11:10     ` Sascha Hauer
2016-01-13 15:37 ` [PATCH 08/15] input: usb keyboard: convert to input framework Sascha Hauer
2016-01-13 15:37 ` [PATCH 09/15] input: imx-keypad: Use dev_* functions Sascha Hauer
2016-01-13 15:37 ` [PATCH 10/15] input: move matrix_keypad_build_keymap() to C file Sascha Hauer
2016-01-13 15:37 ` [PATCH 11/15] input: imx-keypad: convert to input framework Sascha Hauer
2016-01-13 15:37 ` [PATCH 12/15] input: Add device tree parsing support for matrix keymap Sascha Hauer
2016-01-13 15:37 ` [PATCH 13/15] input: imx-keypad: Add device tree support Sascha Hauer
2016-01-13 15:37 ` [PATCH 14/15] input: gpio-keys: Use KEY_* keycodes Sascha Hauer
2016-01-13 15:37 ` [PATCH 15/15] input: gpio-keys: convert to input framework Sascha Hauer

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox