summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVadim Bendebury <vbendeb@chromium.org>2015-11-12 16:44:46 -0800
committerchrome-bot <chrome-bot@chromium.org>2015-11-17 14:40:26 -0800
commita8f2e3625e34b51da381236a14a7d28adc37df4a (patch)
tree6965c1b45350c11d61bbf560fa0a01162b2de119
parent2d57e6f6d98a06abd55e193b6f5d193280f01988 (diff)
downloadchrome-ec-a8f2e3625e34b51da381236a14a7d28adc37df4a.tar.gz
add the 'extension' command framework
This patch introduces a facility which would allow to compile in callbacks for arbitrary commands passed over various communication protocols. Typically this will be used for testing, when various test commands are multiplexed over an existing protocol. The callbacks are associated with 16 bit command codes. On input the callback receives a buffer, containing the command's argument, the size of the command argument and the maximum size of the buffer. On output the callback stores processing result in the same buffer and updates the size to the actual amount of returned data. Callback descriptors are stored in a dedicated read only section which is scanned by extension_route_command() to find a callback associated with a certain command code. A console channel is also being introduced to allow controlling console output generated by extension commands handlers. BRANCH=none BUG=chrome-os-partner:47524 TEST=none yet Change-Id: I8ae16a78ca7d72176a5e7f74dd7a232078e7c06c Signed-off-by: Vadim Bendebury <vbendeb@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/312586 Reviewed-by: Randall Spangler <rspangler@chromium.org>
-rw-r--r--common/console_output.c3
-rw-r--r--common/extension.c36
-rw-r--r--core/cortex-m/ec.lds.S5
-rw-r--r--core/cortex-m0/ec.lds.S5
-rw-r--r--include/config.h2
-rw-r--r--include/console.h3
-rw-r--r--include/extension.h56
-rw-r--r--include/link_defs.h4
8 files changed, 114 insertions, 0 deletions
diff --git a/common/console_output.c b/common/console_output.c
index d15971ebea..28d661561c 100644
--- a/common/console_output.c
+++ b/common/console_output.c
@@ -39,6 +39,9 @@ static const char * const channel_names[] = {
"clock",
"dma",
"events",
+#ifdef CONFIG_EXTENSION_COMMAND
+ "extension",
+#endif
"gesture",
"gpio",
"hostcmd",
diff --git a/common/extension.c b/common/extension.c
new file mode 100644
index 0000000000..a588ce892e
--- /dev/null
+++ b/common/extension.c
@@ -0,0 +1,36 @@
+/* Copyright 2015 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#include "byteorder.h"
+#include "console.h"
+#include "extension.h"
+#include "link_defs.h"
+
+#define CPRINTF(format, args...) cprintf(CC_EXTENSION, format, ## args)
+
+void extension_route_command(uint16_t command_code,
+ void *buffer,
+ size_t in_size,
+ size_t *out_size)
+{
+ struct extension_command *cmd_p;
+ struct extension_command *end_p;
+
+ cmd_p = (struct extension_command *)&__extension_cmds;
+ end_p = (struct extension_command *)&__extension_cmds_end;
+
+ while (cmd_p != end_p) {
+ if (cmd_p->command_code == command_code) {
+ cmd_p->handler(buffer, in_size, out_size);
+ return;
+ }
+ cmd_p++;
+ }
+
+ CPRINTF("%s: handler %d not found\n", __func__, command_code);
+
+ /* This covers the case of the handler not found. */
+ *out_size = 0;
+}
diff --git a/core/cortex-m/ec.lds.S b/core/cortex-m/ec.lds.S
index 38a235d53f..d32145d243 100644
--- a/core/cortex-m/ec.lds.S
+++ b/core/cortex-m/ec.lds.S
@@ -107,6 +107,11 @@ SECTIONS
__cmds_end = .;
. = ALIGN(4);
+ __extension_cmds = .;
+ KEEP(*(.rodata.extensioncmds))
+ __extension_cmds_end = .;
+
+ . = ALIGN(4);
__hcmds = .;
KEEP(*(.rodata.hcmds))
__hcmds_end = .;
diff --git a/core/cortex-m0/ec.lds.S b/core/cortex-m0/ec.lds.S
index 10f31953d8..dc36b49f72 100644
--- a/core/cortex-m0/ec.lds.S
+++ b/core/cortex-m0/ec.lds.S
@@ -65,6 +65,11 @@ SECTIONS
__cmds_end = .;
. = ALIGN(4);
+ __extension_cmds = .;
+ KEEP(*(.rodata.extensioncmds))
+ __extension_cmds_end = .;
+
+ . = ALIGN(4);
__hcmds = .;
KEEP(*(.rodata.hcmds))
__hcmds_end = .;
diff --git a/include/config.h b/include/config.h
index f0effc425b..fa522c3b41 100644
--- a/include/config.h
+++ b/include/config.h
@@ -116,6 +116,8 @@
/* Support AP Warm reset Interrupt. */
#undef CONFIG_AP_WARM_RESET_INTERRUPT
+/* Allow proprietary communication protocols' extensions. */
+#undef CONFIG_EXTENSION_COMMAND
/*
* Support controlling the display backlight based on the state of the lid
* switch. The EC will disable the backlight when the lid is closed.
diff --git a/include/console.h b/include/console.h
index 81e5a8c3c2..01cf13d6ea 100644
--- a/include/console.h
+++ b/include/console.h
@@ -29,6 +29,9 @@ enum console_channel {
CC_COMMAND = 0, /* Console command (interactive I/O). Use this only
* inside a console command routine. */
CC_ACCEL,
+#ifdef CONFIG_EXTENSION_COMMAND
+ CC_EXTENSION,
+#endif
CC_CHARGER,
CC_CHIPSET,
CC_CLOCK,
diff --git a/include/extension.h b/include/extension.h
new file mode 100644
index 0000000000..45637d9518
--- /dev/null
+++ b/include/extension.h
@@ -0,0 +1,56 @@
+/* Copyright 2015 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#ifndef __EC_INCLUDE_EXTENSION_H
+#define __EC_INCLUDE_EXTENSION_H
+
+#include <stddef.h>
+#include <stdint.h>
+
+#include "common.h"
+
+/*
+ * Type of function handling extension commands.
+ *
+ * @param buffer As input points to the input data to be processed, as
+ * output stores data, processing result.
+ * @param command_size Number of bytes of input data
+ * @param response_size On input - max size of the buffer, on output - actual
+ * number of data returned by the handler.
+ */
+typedef void (*extension_handler)(void *buffer,
+ size_t command_size,
+ size_t *response_size);
+/*
+ * Find handler for an extension command.
+ *
+ * @param command_code Code associated with a extension command handler.
+ * @param buffer Data to be processd by the handler, the same space
+ * is used for data returned by the handler.
+ * @command_size Size of the input data.
+ * @param size On input - max size of the buffer, on output - actual
+ * number of data returned by the handler.
+ */
+void extension_route_command(uint16_t command_code,
+ void *buffer,
+ size_t command_size,
+ size_t *size);
+
+struct extension_command {
+ uint16_t command_code;
+ extension_handler handler;
+} __packed;
+
+/* Values for different extension commands. */
+enum {
+ EXTENSION_AES = 0,
+};
+
+#define DECLARE_EXTENSION_COMMAND(code, handler) \
+ const struct extension_command __keep __extension_cmd_##code \
+ __attribute__((section(".rodata.extensioncmds"))) \
+ = {code, handler}
+
+#endif /* __EC_INCLUDE_EXTENSION_H */
diff --git a/include/link_defs.h b/include/link_defs.h
index df0cbb6811..ff443557b2 100644
--- a/include/link_defs.h
+++ b/include/link_defs.h
@@ -19,6 +19,10 @@
extern const struct console_command __cmds[];
extern const struct console_command __cmds_end[];
+/* Extension commands. */
+extern const void *__extension_cmds;
+extern const void *__extension_cmds_end;
+
/* Hooks */
extern const struct hook_data __hooks_init[];
extern const struct hook_data __hooks_init_end[];