summaryrefslogtreecommitdiff
path: root/app/src/usb.c
diff options
context:
space:
mode:
authorNick Winans <nick.win999@gmail.com>2020-10-23 00:55:50 -0500
committerGitHub <noreply@github.com>2020-10-23 00:55:50 -0500
commit70ffcca3b42f5dacf5be155a56b11387a7e68b63 (patch)
tree80954a5afb17978ad897e3dde0385cfee0a902c9 /app/src/usb.c
parent162c6b77db27c158b05ed65effa8d8ded68ba9b7 (diff)
parent04b7a759f4c676c96da261a724cef1517614dea1 (diff)
Merge branch 'main' into bluetooth/battery-reporting
Diffstat (limited to 'app/src/usb.c')
-rw-r--r--app/src/usb.c86
1 files changed, 86 insertions, 0 deletions
diff --git a/app/src/usb.c b/app/src/usb.c
new file mode 100644
index 0000000..434b3d4
--- /dev/null
+++ b/app/src/usb.c
@@ -0,0 +1,86 @@
+/*
+ * Copyright (c) 2020 The ZMK Contributors
+ *
+ * SPDX-License-Identifier: MIT
+ */
+
+#include <device.h>
+#include <init.h>
+
+#include <usb/usb_device.h>
+#include <usb/class/usb_hid.h>
+#include <dt-bindings/zmk/keys.h>
+
+#include <zmk/hid.h>
+#include <zmk/keymap.h>
+
+LOG_MODULE_DECLARE(zmk, CONFIG_ZMK_LOG_LEVEL);
+
+static enum usb_dc_status_code usb_status = USB_DC_UNKNOWN;
+
+#ifdef CONFIG_ZMK_USB
+
+static struct device *hid_dev;
+
+static K_SEM_DEFINE(hid_sem, 1, 1);
+
+static void in_ready_cb(void) { k_sem_give(&hid_sem); }
+
+static const struct hid_ops ops = {
+ .int_in_ready = in_ready_cb,
+};
+
+int zmk_usb_hid_send_report(const u8_t *report, size_t len) {
+ switch (usb_status) {
+ case USB_DC_SUSPEND:
+ return usb_wakeup_request();
+ case USB_DC_ERROR:
+ case USB_DC_RESET:
+ case USB_DC_DISCONNECTED:
+ case USB_DC_UNKNOWN:
+ return -ENODEV;
+ default:
+ k_sem_take(&hid_sem, K_MSEC(30));
+ int err = hid_int_ep_write(hid_dev, report, len, NULL);
+
+ if (err) {
+ k_sem_give(&hid_sem);
+ }
+
+ return err;
+ }
+}
+
+#endif /* CONFIG_ZMK_USB */
+
+enum usb_dc_status_code zmk_usb_get_status() { return usb_status; }
+
+void usb_status_cb(enum usb_dc_status_code status, const u8_t *params) { usb_status = status; };
+
+static int zmk_usb_init(struct device *_arg) {
+ int usb_enable_ret;
+
+#ifdef CONFIG_ZMK_USB
+ hid_dev = device_get_binding("HID_0");
+ if (hid_dev == NULL) {
+ LOG_ERR("Unable to locate HID device");
+ return -EINVAL;
+ }
+
+ usb_hid_register_device(hid_dev, zmk_hid_report_desc, sizeof(zmk_hid_report_desc), &ops);
+
+ usb_hid_init(hid_dev);
+
+#endif /* CONFIG_ZMK_USB */
+
+ usb_enable_ret = usb_enable(usb_status_cb);
+
+ if (usb_enable_ret != 0) {
+ LOG_ERR("Unable to enable USB");
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+SYS_INIT(zmk_usb_init, APPLICATION, CONFIG_ZMK_USB_INIT_PRIORITY);