]> git.ipfire.org Git - thirdparty/grub.git/commitdiff
Dirty cros keyboard
authorVladimir Serbinenko <phcoder@gmail.com>
Mon, 22 Feb 2016 18:28:40 +0000 (19:28 +0100)
committerVladimir Serbinenko <phcoder@gmail.com>
Mon, 22 Feb 2016 18:29:08 +0000 (19:29 +0100)
grub-core/Makefile.core.def
grub-core/kern/arm/coreboot/init.c
grub-core/term/arm/cros.c [new file with mode: 0644]
include/grub/arm/coreboot/kernel.h

index 8ad6718191a9cf4f2eab17688f6de18ddcc74b67..b1f2e57d1cf7975d3f77b3848ec6598ed56397c3 100644 (file)
@@ -162,6 +162,8 @@ kernel = {
   arm_coreboot = bus/fdt.c;
   arm_coreboot = term/ps2.c;
   arm_coreboot = term/arm/pl050.c;
+  arm_coreboot = term/arm/cros.c;
+  arm_coreboot = term/arm/cros_ec.c;
   arm_coreboot = commands/keylayouts.c;
   arm_coreboot = kern/arm/coreboot/dma.c;
 
index 1e8dfc2a21f4dc30cec57d0d424632cdef449af1..0c021697f091baa06b28c13c0202f22de130603b 100644 (file)
@@ -153,7 +153,7 @@ grub_machine_init (void)
   grub_fdtbus_init (dtb, dtb_size);
 
   grub_machine_timer_init ();
-
+  grub_cros_init ();
   grub_pl050_init ();
 }
 
diff --git a/grub-core/term/arm/cros.c b/grub-core/term/arm/cros.c
new file mode 100644 (file)
index 0000000..de6c3ea
--- /dev/null
@@ -0,0 +1,102 @@
+/*
+ *  GRUB  --  GRand Unified Bootloader
+ *
+ *  Copyright (C) 2012  Google Inc.
+ *  Copyright (C) 2016  Free Software Foundation, Inc.
+ *
+ *  GRUB 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, either version 3 of the License, or
+ *  (at your option) any later version.
+ *
+ *  GRUB 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.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <grub/ps2.h>
+#include <grub/fdtbus.h>
+#include <grub/err.h>
+#include <grub/machine/kernel.h>
+#include <grub/misc.h>
+#include <grub/term.h>
+#include <grub/time.h>
+#include <grub/fdtbus.h>
+#include "cros_ec.h"
+
+struct grub_ps2_state ps2_state;
+
+struct cros_ec_keyscan old_scan;
+
+static grub_uint8_t map_code[CROS_EC_KEYSCAN_COLS][CROS_EC_KEYSCAN_ROWS];
+
+/* If there is a character pending, return it;
+   otherwise return GRUB_TERM_NO_KEY.  */
+static int
+grub_cros_keyboard_getkey (struct grub_term_input *term __attribute__ ((unused)))
+{
+  struct cros_ec_keyscan scan;
+  int i, j;
+  cros_ec_scan_keyboard(&scan);
+  for (i = 0; i < CROS_EC_KEYSCAN_COLS; i++)
+    if (scan.data[i] ^ old_scan.data[i])
+      for (j = 0; j < CROS_EC_KEYSCAN_ROWS; j++)
+       if ((scan.data[i] ^ old_scan.data[i]) & (1 << j))
+         {
+           grub_uint8_t code = map_code[i][j];
+           int ret;
+           if (!(scan.data[i] & (1 << j)))
+             code |= 0x80;
+           grub_dprintf ("cros_keyboard", "key <%d, %d> code %x\n", i, j, code);
+           if (code == 0)
+             ret = GRUB_TERM_NO_KEY;
+           else
+             ret = grub_ps2_process_incoming_byte (&ps2_state, code);
+           old_scan.data[i] ^= (1 << j);
+           if (ret != GRUB_TERM_NO_KEY)
+             return ret;
+         }
+  return GRUB_TERM_NO_KEY;
+}
+
+static struct grub_term_input grub_cros_keyboard_term =
+  {
+    .name = "cros_keyboard",
+    .getkey = grub_cros_keyboard_getkey
+  };
+
+static grub_err_t
+cros_attach(const struct grub_fdtbus_dev *dev __attribute__ ((unused)))
+{
+  grub_size_t keymap_size, i;
+  const grub_uint8_t *keymap = grub_fdtbus_get_prop (dev, "linux,keymap", &keymap_size);
+
+  if (keymap)
+    {
+      for (i = 0; i + 3 < keymap_size; i += 4)
+       if (keymap[i+1] < CROS_EC_KEYSCAN_COLS && keymap[i] < CROS_EC_KEYSCAN_ROWS && keymap[i+2] == 0 && keymap[i+3] < 0x80)
+         map_code[keymap[i+1]][keymap[i]] = keymap[i+3];
+    }
+
+  ps2_state.current_set = 1;
+  ps2_state.at_keyboard_status = 0;
+  cros_ec_init();
+  grub_term_register_input ("cros_keyboard", &grub_cros_keyboard_term);
+  return GRUB_ERR_NONE;
+}
+
+struct grub_fdtbus_driver cros =
+{
+  .compatible = "google,cros-ec-keyb",
+  .attach = cros_attach
+};
+
+void
+grub_cros_init (void)
+{
+  grub_fdtbus_register (&cros);
+}
index 95fb0b174c6a762fc649afd576052b8420beb577..09cd7fe328c7be9db4e13f725e8b88bbe06b4edf 100644 (file)
@@ -34,6 +34,8 @@ struct grub_fdt_board
 extern struct grub_fdt_board grub_fdt_boards[];
 void grub_machine_timer_init (void);
 void grub_pl050_init (void);
+void
+grub_cros_init (void);
 extern grub_addr_t EXPORT_VAR (start_of_ram);
 #endif /* ! ASM_FILE */