--- /dev/null
+/*
+ * GRUB -- GRand Unified Bootloader
+ * Copyright (C) 2007,2009 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/dl.h>
+#include <grub/dma.h>
+#include <grub/mm.h>
+#include <grub/misc.h>
+#include <grub/mm_private.h>
+#include <grub/cache.h>
+
+struct grub_pci_dma_chunk *
+grub_memalign_dma32 (grub_size_t align, grub_size_t size)
+{
+ void *ret;
+ if (align < 64)
+ align = 64;
+ size = ALIGN_UP (size, align);
+ ret = grub_memalign (align, size);
+ if (!ret)
+ return 0;
+ grub_arch_sync_dma_caches (ret, size);
+ return ret;
+}
+
+void
+grub_dma_free (struct grub_pci_dma_chunk *ch)
+{
+ grub_size_t size = (((struct grub_mm_header *) ch) - 1)->size * GRUB_MM_ALIGN;
+ grub_arch_sync_dma_caches (ch, size);
+ grub_free (ch);
+}
+
+volatile void *
+grub_dma_get_virt (struct grub_pci_dma_chunk *ch)
+{
+ return (void *) ch;
+}
+
+grub_uint32_t
+grub_dma_get_phys (struct grub_pci_dma_chunk *ch)
+{
+ return (grub_uint32_t) (grub_addr_t) ch;
+}
+
static grub_uint8_t map_code[CROS_EC_KEYSCAN_COLS][CROS_EC_KEYSCAN_ROWS];
+static grub_uint8_t e0_translate[16] =
+ {
+ 0x1c, 0x1d, 0x35, 0x00,
+ 0x38, 0x00, 0x47, 0x48,
+ 0x49, 0x4b, 0x4d, 0x4f,
+ 0x50, 0x51, 0x52, 0x53,
+ };
+
/* If there is a character pending, return it;
otherwise return GRUB_TERM_NO_KEY. */
static int
{
grub_uint8_t code = map_code[i][j];
int ret;
+ grub_uint8_t brk = 0;
if (!(scan.data[i] & (1 << j)))
- code |= 0x80;
+ brk = 0x80;
grub_dprintf ("cros_keyboard", "key <%d, %d> code %x\n", i, j, code);
- if (code == 0)
- ret = GRUB_TERM_NO_KEY;
+ if (code < 0x60)
+ ret = grub_ps2_process_incoming_byte (&ps2_state, code | brk);
+ else if (code >= 0x60 && code < 0x70 && e0_translate[code - 0x60])
+ {
+ grub_ps2_process_incoming_byte (&ps2_state, 0xe0);
+ ret = grub_ps2_process_incoming_byte (&ps2_state, e0_translate[code - 0x60] | brk);
+ }
else
- ret = grub_ps2_process_incoming_byte (&ps2_state, code);
+ ret = GRUB_TERM_NO_KEY;
old_scan.data[i] ^= (1 << j);
if (ret != GRUB_TERM_NO_KEY)
return ret;
--- /dev/null
+#include <grub/types.h>
+/*
+ * Hard-code the number of columns we happen to know we have right now. It
+ * would be more correct to call cros_ec_mkbp_info() at startup and determine
+ * the actual number of keyboard cols from there.
+ */
+#define CROS_EC_KEYSCAN_COLS 13
+#define CROS_EC_KEYSCAN_ROWS 8
+
+/* Information returned by a key scan */
+struct cros_ec_keyscan {
+ grub_uint8_t data[CROS_EC_KEYSCAN_COLS];
+};
+
+typedef struct CrosEcBusOps
+{
+ int (*init)(struct CrosEcBusOps *me);
+
+ /**
+ * Send a command to a ChromeOS EC device and return the reply.
+ *
+ * The device's internal input/output buffers are used.
+ *
+ * @param bus ChromeOS EC bus ops
+ * @param cmd Command to send (EC_CMD_...)
+ * @param cmd_version Version of command to send (EC_VER_...)
+ * @param dout Output data (may be NULL If dout_len=0)
+ * @param dout_len Size of output data in bytes
+ * @param dinp Returns pointer to response data
+ * @param din_len Maximum size of response in bytes
+ * @return number of bytes in response, or -1 on error
+ */
+ int (*send_command)(struct CrosEcBusOps *me, grub_uint8_t cmd,
+ int cmd_version,
+ const void *dout, grub_uint32_t dout_len,
+ void *din, grub_uint32_t din_len);
+
+ int (*send_packet)(struct CrosEcBusOps *me,
+ const void *dout, grub_uint32_t dout_len,
+ void *din, grub_uint32_t din_len);
+
+ /**
+ * Byte I/O functions.
+ *
+ * Read or write a sequence a bytes over the desired protocol.
+ * Used to support protocol variants - currently only implemented
+ * for LPC.
+ *
+ * @param data Read / write data buffer
+ * @param port I/O port
+ * @size Number of bytes to read / write
+ */
+ void (*read)(grub_uint8_t *data, grub_uint16_t port, int size);
+ void (*write)(const grub_uint8_t *data, grub_uint16_t port, int size);
+} CrosEcBusOps;
+
+int cros_ec_set_bus(CrosEcBusOps *bus);
+int cros_ec_scan_keyboard(struct cros_ec_keyscan *scan);
+int cros_ec_init(void);