{"id":18896539,"url":"https://github.com/manna-harbour/xmk","last_synced_at":"2025-04-15T01:51:40.484Z","repository":{"id":59734262,"uuid":"532458205","full_name":"manna-harbour/xmk","owner":"manna-harbour","description":"Use programmable keyboard firmware with any keyboard.","archived":false,"fork":false,"pushed_at":"2023-03-08T11:48:23.000Z","size":123,"stargazers_count":169,"open_issues_count":2,"forks_count":11,"subscribers_count":3,"default_branch":"main","last_synced_at":"2025-03-28T13:44:56.826Z","etag":null,"topics":["keyboard","keyboard-firmware","kmk","kmk-firmware","kmonad","qmk","zmk"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/manna-harbour.png","metadata":{"files":{"readme":"readme.org","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null},"funding":{"github":["manna-harbour"]}},"created_at":"2022-09-04T06:32:20.000Z","updated_at":"2025-03-02T23:57:40.000Z","dependencies_parsed_at":"2024-11-08T08:48:27.019Z","dependency_job_id":null,"html_url":"https://github.com/manna-harbour/xmk","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manna-harbour%2Fxmk","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manna-harbour%2Fxmk/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manna-harbour%2Fxmk/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manna-harbour%2Fxmk/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/manna-harbour","download_url":"https://codeload.github.com/manna-harbour/xmk/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248991538,"owners_count":21194894,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["keyboard","keyboard-firmware","kmk","kmk-firmware","kmonad","qmk","zmk"],"created_at":"2024-11-08T08:34:21.343Z","updated_at":"2025-04-15T01:51:40.460Z","avatar_url":"https://github.com/manna-harbour.png","language":"Python","funding_links":["https://github.com/sponsors/manna-harbour"],"categories":[],"sub_categories":[],"readme":"# Copyright 2023 Manna Harbour\n# https://github.com/manna-harbour/xmk\n\n# M-x org-make-toc to update TOC\n# https://github.com/alphapapa/org-make-toc\n\n# M-x org-babel-mark-block M-x mermaid-compile-region to preview diagram\n# https://github.com/abrochard/mermaid-mode\n\n* [[https://github.com/manna-harbour/xmk][𝑥MK]]\n:PROPERTIES:\n:TOC:      :include descendants :depth 1\n:END:\n\n[[docs/images/xmk-banner.jpg]]\n\n*Use programmable keyboard firmware with any keyboard.*\n\n:CONTENTS:\n- [[#introduction][Introduction]]\n- [[#operation][Operation]]\n- [[#xmk][xmk]]\n- [[#maps][Maps]]\n- [[#firmware][Firmware]]\n- [[#discussions-and-support][Discussions and Support]]\n:END:\n\n** Introduction\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#uses][Uses]]\n- [[#overview][Overview]]\n- [[#background][Background]]\n:END:\n*** Uses\n\n- Use QMK, ZMK, or KMK with any keyboard connected to a Linux host, including\n  - non-programmable keyboards,\n  - incompatible programmable keyboards,\n  - QMK, ZMK, or KMK keyboards (using a keymap or layer without dual function keys),\n  - BT or other wireless keyboards, and\n  - built-in laptop keyboards.\n- Record and play back timed keystrokes to\n  - test keymap changes,\n  - compare behaviour between QMK, ZMK, and KMK, or\n  - debug firmware timing issues.\n- For other uses see https://github.com/manna-harbour/xmk/discussions/2.\n\n*** Overview\n\n𝑥MK facilitates the use of programmable keyboard firmware with any keyboard.\n\nWith 𝑥MK, a keyboard, and an MCU board running programmable keyboard firmware, are connected to the host, and key events are diverted by ~xmk~ from the keyboard to the MCU board for processing by the firmware. 𝑥MK supports any keyboard, Linux hosts, and QMK, ZMK, or KMK keymaps, and requires an MCU board and the ~xmk~ application.\n\n#+begin_src mermaid :file xmk-overview.svg\ngraph LR\n    kbd([keyboard])--\u003exmk\n    subgraph host\n        xmk\n        apps([applications])\n    end\n    xmk--\u003emcu\n    mcu[MCU board]--\u003eapps\n#+end_src\n\nWith 𝑥MK Native, the firmware instead runs as a process on the host. 𝑥MK Native supports any keyboard, Linux hosts, and ZMK keymaps, and requires the ~xmk~ and ~usbip~ applications and no additional hardware.\n\n#+begin_src mermaid :file xmk-native-overview.svg\ngraph LR\n    kbd([keyboard])--\u003exmk\n    subgraph host\n        xmk--\u003efirmware--\u003eusbip--\u003eapps([applications])\n    end\n#+end_src\n\n*** Background\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#non-programmable-keyboards][Non-Programmable Keyboards]]\n- [[#programmable-keyboards][Programmable Keyboards]]\n- [[#𝑥mk-and-related-projects][𝑥MK and Related Projects]]\n:END:\n\n**** Non-Programmable Keyboards\n\nWith non-programmable keyboards, keyswitches are scanned for state changes by an integrated controller, and keycode events are generated with a fixed relationship between key and keycode. Keycode events are transmitted from the controller to the host and are made available to applications on the host.\n\n#+begin_src mermaid :file non-programmable-keyboard.svg\ngraph LR\n    subgraph non-programmable keyboard\n        ks([keyswitches])--\u003e|state \u003cbr\u003e changes|c[controller]\n    end\n    subgraph host\n        apps([applications])\n    end\n    c--\u003e|keycode \u003cbr\u003e events|apps\n#+end_src\n\n**** Programmable Keyboards\n\n[[https://qmk.fm/][QMK]], [[https://zmk.dev/][ZMK]], and [[https://github.com/KMKfw/kmk_firmware][KMK]] are firmware for compatible programmable keyboards, and support customisation functions such as remapping, layers, and dual functions keys. Typical programmable keyboards use an MCU board to run the firmware. The firmware scans the keyswitches for state changes in the same way as with a non-programmable keyboard. Keycode events are generated via a customisable keymap. Keycode events are transmitted from the keymap to the host and are made available to applications on the host.\n\n#+begin_src mermaid :file programmable-keyboard.svg\ngraph LR\n    subgraph programmable keyboard\n        ks([keyswitches])\n        subgraph MCU board\n            km[keymap]\n        end\n        ks--\u003e|state \u003cbr\u003e changes|km\n    end\n    km--\u003e|keycode \u003cbr\u003e events|apps\n    subgraph host\n        apps([applications])\n    end\n#+end_src\n\n**** 𝑥MK and Related Projects\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\n𝑥MK and related projects facilitate the use of customisable keymaps with non-programmable keyboards.\n\n:CONTENTS:\n- [[#kmonad][KMonad]]\n- [[#converter][Converter]]\n- [[#modification][Modification]]\n- [[#comparison-summary][Comparison Summary]]\n- [[#miryoku][Miryoku]]\n:END:\n\n***** KMonad\n\nWith [[https://github.com/kmonad/kmonad][KMonad]], key events are diverted from the keyboard to the ~kmonad~ application on the host for processing by the KMonad keymap. KMonad supports any keyboard, multiple platforms, and KMonad keymaps, and requires the ~kmonad~ application and no additional hardware.\n\n#+begin_src mermaid :file xmonad.svg\ngraph LR\n    kbd([keyboard])--\u003ekmonad\n    subgraph host\n        kmonad--\u003eapps([applications])\n    end\n#+end_src\n\n***** Converter\n\nWith a [[https://github.com/qmk/qmk_firmware/tree/master/keyboards/converter/usb_usb][QMK USB to USB keyboard protocol converter]], the converter is connected between keyboard and host, and key events are processed by the keymap. The converter supports USB keyboards, any host, and QMK keymaps, and requires the converter hardware and no additional software.\n\n#+begin_src mermaid :file xmonad.svg\ngraph LR\n    kbd([keyboard])--\u003ekm\n    subgraph converter\n        km[keymap]\n    end\n    subgraph host\n        km--\u003eapps([applications])\n    end\n#+end_src\n\n***** Modification\n\nWith hardware modification, the non-programmable controller can be replaced with an MCU board running programmable firmware, converting the [[#non-programmable-keyboards][non-programmable keyboard]] into a [[#programmable-keyboards][programmable keyboard]]. Hardware modification supports modifiable keyboards, any host, and QMK, ZMK, or KMK keymaps, and requires the MCU board and no additional software.\n\n***** Comparison Summary\n\n|            | 𝑥MK           | 𝑥MK Native     | KMonad   | Converter | Modification  |\n|------------+---------------+----------------+----------+-----------+---------------|\n| *Keyboard* | any           | any            | any      | USB       | modifiable    |\n| *OS*       | Linux         | Linux          | multiple | any       | any           |\n| *Hardware* | MCU board     | none           | none     | converter | MCU board     |\n| *Software* | ~xmk~         | ~xmk~, ~usbip~ | ~kmonad~ | none      | none          |\n| *Keymap*   | QMK, ZMK, KMK | ZMK            | KMonad   | QMK       | QMK, ZMK, KMK |\n\n***** Miryoku\n\n𝑥MK can be used with any keymap. [[https://github.com/manna-harbour/miryoku_qmk/tree/miryoku/users/manna-harbour_miryoku#𝑥mk][Miryoku QMK]], [[https://github.com/manna-harbour/miryoku_zmk#𝑥mk][Miryoku ZMK]], and [[https://github.com/manna-harbour/miryoku_kmk#𝑥mk][Miryoku KMK]] include support for 𝑥MK. [[https://github.com/manna-harbour/miryoku_kmonad][Miryoku KMonad]] can be used as an alternative to Miryoku QMK, Miryoku ZMK, and Miryoku KMK with 𝑥MK.\n\n** Operation\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#𝑥mk-operation][𝑥MK Operation]]\n- [[#𝑥mk-native-operation][𝑥MK Native Operation]]\n- [[#record-and-playback-operation][Record and Playback Operation]]\n:END:\n\n*** 𝑥MK Operation\n\nThe required hardware components are any keyboard, an MCU board running QMK / ZMK / KMK firmware built with the [[#qmk][QMK converter / xmk keyboard]] / [[#xmk-shield][ZMK xmk shield]] / [[#kmk][KMK xmk keyboard]] and desired keymap, and a Linux host. The required software components are the [[#xmk][xmk]] python application, and a [[#maps][map]] of keyboard keycode to keymap key positions.\n\nThe keyboard is connected to the host via USB, BT, PS/2, etc. Keycode events from the keyboard are made available on the host as a keyboard evdev device.\n\n~xmk~ reads the map, grabs the keyboard evdev device, reads the keyboard keycode events, converts keycodes to keymap key positions according to the map, and outputs key position event shell commands via stdout.\n\nThe MCU board is connected to the host via USB. The firmware includes a serial shell supporting keymap key position event shell commands. The shell is made available on the host as a tty device over USB CDC ACM (serial over USB).\n\nOutput from ~xmk~ is redirected to the tty device. The firmware shell interprets the shell commands and triggers the corresponding events in the keymap.\n\nKeycode events from the keymap are sent to the host via USB HID, and are made available to the host as an MCU board firmware evdev device.\n\n#+begin_src mermaid :file xmk.svg\ngraph TB\n    kbd([keyboard])--\u003e|keycode events via \u003cbr\u003e USB, BT, PS/2, etc.|kd\n    subgraph Linux host\n        kd[keyboard \u003cbr\u003e evdev device]--\u003e|keycode events \u003cbr\u003e via evdev|xmk\n        mapfile[(map)]--\u003e|keycode to keymap \u003cbr\u003e position mapping \u003cbr\u003e from file|xmk\n        xmk--\u003e|key position event shell commands \u003cbr\u003e via stdout|tty[MCU board firmware tty device]\n        md[MCU board firmware evdev device]--\u003e|keycode events via evdev|a([applications])\n    end\n    tty--\u003e|key position event shell commands \u003cbr\u003e via USB CDC ACM|sh\n    subgraph MCU board firmware\n        sh[shell]--\u003e|key position events|km[keymap]\n    end\n    km--\u003e|keycode events via USB HID|md\n#+end_src\n\n*** 𝑥MK Native Operation\n\nThe required hardware components are any keyboard, and a Linux host. The required software components are the [[#xmk][xmk]] python application, a [[#maps][map]] of keyboard keycode to keymap key positions, ZMK firmware built with the [[#native_posix_64-board][𝑥MK native_posix_64 board]] and desired keymap, and a USB/IP client.\n\nThe keyboard is connected to the host via USB, BT, PS/2, etc. Keycode events from the keyboard are made available on the host as a keyboard evdev device.\n\n~xmk~ reads the map, grabs the keyboard evdev device, reads the keyboard keycode events, converts keycodes to keymap key positions according to the map, and outputs key position event shell commands via stdout.\n\nThe firmware runs as a native process on the host. The firmware includes a serial shell supporting keymap key position event shell commands. The shell is made available on the host as a pty device.\n\nOutput from ~xmk~ is redirected to the pty device. The firmware shell interprets the shell commands and triggers the corresponding events in the keymap.\n\nThe firmware process includes a USB/IP server. Keycode events from the keymap are made available via the USB/IP server.\n\nThe USB/IP client connects to the USB/IP server, and receives keycode events via USB/IP. Keycode events are made available on the host as a USB/IP evdev device.\n\n#+begin_src mermaid :file xmk-native.svg\ngraph TB\n    kbd([keyboard])--\u003e|keycode events via \u003cbr\u003e USB, BT, PS/2, etc.|kd\n    subgraph Linux host\n        kd[keyboard \u003cbr\u003e evdev device]--\u003e|keycode events \u003cbr\u003e via evdev|xmk\n        mapfile[(map)]--\u003e|keycode to keymap \u003cbr\u003e position mapping \u003cbr\u003e from file|xmk\n        xmk--\u003e|key position event shell commands \u003cbr\u003e via stdout|pty[firmware process pty device]\n        subgraph firmware process\n            sh[shell]--\u003e|key position events|km[keymap]--\u003e|keycode events|us[USB/IP server]\n        end\n        pty--\u003e|key position event shell commands \u003cbr\u003e via pty|sh\n        us--\u003e|keycode events via USB/IP|uc[USB/IP client]--\u003e|keycode events|ud[USB/IP client evdev device]\n        ud--\u003e|keycode events via evdev|a([applications])\n    end\n#+end_src\n\n*** Record and Playback Operation\n\nWhen recording, in addition to the normal [[#𝑥mk-operation][𝑥MK operation]] and [[#𝑥mk-native-operation][𝑥MK Native operation]], ~xmk~ saves key position events with timing to a file.\n\n#+begin_src mermaid :file xmk-record.svg\ngraph TB\n    kd[[keyboard evdev device]]--\u003e|keycode events \u003cbr\u003e via evdev|xmk\n    mapfile[(map)]--\u003e|keycode to keymap \u003cbr\u003e position mapping \u003cbr\u003e from file|xmk\n    xmk--\u003e|key position event shell commands \u003cbr\u003e via stdout|tty[[firmware tty / pty device]]\n    xmk--\u003e|key position events \u003cbr\u003e with timing \u003cbr\u003e to file|rec[(recording)]\n#+end_src\n\n#+RESULTS:\n[[file:xmk-record.svg]]\n\nWhen playing back, the normal [[#𝑥mk-operation][𝑥MK operation]] and [[#𝑥mk-native-operation][𝑥MK Native operation]] is modified in that instead of reading the map and the keyboard evdev device, ~xmk~ reads key position events with timing from a file, and outputs key position event shell commands via stdout according to the timing.\n\n#+begin_src mermaid :file xmk-playback.svg\ngraph TB\n    rec[(recording)]--\u003e|key position events with timing \u003cbr\u003e from file|xmk\n    xmk--\u003e|key position event shell commands \u003cbr\u003e via stdout|tty[[firmware tty / pty device]]\n#+end_src\n\n** xmk\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\n~xmk~ is located at [[./src/xmk]].\n\n:CONTENTS:\n- [[#xmk-prerequisites][xmk Prerequisites]]\n- [[#xmk-setup][xmk Setup]]\n- [[#xmk-usage][xmk Usage]]\n:END:\n\n*** xmk Prerequisites\n\n- https://github.com/gvalkov/python-evdev\n\n*** xmk Setup\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#add-account-to-input-group][Add Account to input Group]]\n- [[#find-the-keyboard-device][Find the Keyboard Device]]\n- [[#select-the-keyboard][Select the Keyboard]]\n- [[#create-a-map][Create a Map]]\n- [[#select-the-map][Select the Map]]\n:END:\n\n**** Add Account to input Group\n\nAdd your account to the ~input~ group.\n\n#+BEGIN_SRC sh\nsudo usermod -aG input `whoami`\n#+END_SRC\n\nLogin again.\n\n**** Find the Keyboard Device\n\nFind the device for your keyboard under ~/dev/input~.\n\nFirst look under ~/dev/input/by-id/~. It will usually end in ~event-kbd~.\n\n#+BEGIN_SRC sh\nls /dev/input/by-id/*\n#+END_SRC\n\nNote the keyboard device in the output.\n\n#+BEGIN_EXAMPLE\n/dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd\n#+END_EXAMPLE\n\nIf not listed, find the device with ~evtest~.\n\n#+BEGIN_SRC sh\nevtest\n#+END_SRC\n\nNote the keyboard device in the output.\n\n#+BEGIN_EXAMPLE\n/dev/input/event21:\tSIGMACHIP USB Keyboard\n#+END_EXAMPLE\n\n**** Select the Keyboard\n\nThe ~-k~ option is used to select the keyboard. Give the path to the keyboard device from [[#find-the-keyboard-device][Find the Keyboard Device]].\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM0\n#+END_SRC\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/event21 -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM0\n#+END_SRC\n\n**** Create a Map\n\nThe ~-c~ option is used to create a map. Give the path to the map file to be created. Also [[#select-the-keyboard][select the keyboard]].\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -c ./src/maps/minidox/60_ansi\n#+END_SRC\n\nPress each key to be used in the keymap in order of keymap key position. Press a key a second time to insert a line break. Press a third time to exit. Optionally edit the file to reformat whitespace or add comments with ~#~.\n\n**** Select the Map\n\nThe ~-m~ option is used to select a map. Give the path to the map file. Use one of the included [[#maps][maps]], or first [[#create-a-map][create a map]].\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/tap -s \u003e /dev/ttyACM0\n#+END_SRC\n\n*** xmk Usage\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\n:CONTENTS:\n- [[#typing][Typing]]\n- [[#record][Record]]\n- [[#playback][Playback]]\n:END:\n\n**** Typing\n\nThe ~-s~ option is used to output firmware shell commands.\nRedirect output to the tty or pty device from [[#converterxmk-setup][converter/xmk Setup]], [[#xmk-shield-setup][xmk Shield Setup]],  [[#native_posix_64-board-setup][native_posix_64 Board Setup]], or [[#kmk-xmk-setup][KMK xmk Setup]] as appropriate.\nAlso [[#select-the-keyboard][select the keyboard]] and [[#select-the-map][select the map]].\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM0\n#+END_SRC\n\n**** Record\n\nThe ~-r~ option is used to record keystrokes with timing. Give the path to the recording file to be created. Optionally redirect output as when [[#typing][typing]]. Also [[#select-the-keyboard][select the keyboard]] and [[#select-the-map][select the map]].\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -r ./src/recordings/hello_world \u003e /dev/ttyACM0\n#+END_SRC\n\n**** Playback\n\nThe ~-p~ option is used to read recorded keystrokes with timing and output firmware shell commands. Give the path to the recording file. Redirect output as when [[#typing][typing]].\n\n#+BEGIN_SRC sh\n./src/xmk -p ./src/recordings/hello_world \u003e /dev/ttyACM0\n#+END_SRC\n\n** Maps\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nMap of keyboard keys to keymap key positions.\n\nSample maps are included under [[./src/maps]] by keymap layout.\n\n:CONTENTS:\n- [[#minidox][minidox]]\n:END:\n\n*** minidox\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#60_ansi][60_ansi]]\n- [[#60_ansi-noreverseangle][60_ansi-noreverseangle]]\n- [[#kinesis_advantage][kinesis_advantage]]\n- [[#tap][tap]]\n:END:\n\n**** 60_ansi\n\n[[https://raw.githubusercontent.com/manna-harbour/miryoku/master/data/mapping/miryoku-kle-mapping-60_ansi.png]]\n\n**** 60_ansi-noreverseangle\n\n[[https://raw.githubusercontent.com/manna-harbour/miryoku/master/data/mapping/miryoku-kle-mapping-60_ansi-noreverseangle.png]]\n\n**** kinesis_advantage\n\n[[https://raw.githubusercontent.com/manna-harbour/miryoku/master/data/mapping/miryoku-kle-mapping-kinesis_advantage.png]]\n\n**** tap\n\nCorresponds to the default [[https://github.com/manna-harbour/miryoku/tree/master/docs/reference#additional-features][Miryoku Tap layer]].\n\n** Firmware\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n:CONTENTS:\n- [[#qmk][QMK]]\n- [[#zmk][ZMK]]\n- [[#kmk][KMK]]\n:END:\n\n*** QMK\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nA bare QMK-compatible MCU board connected to the host over USB, running QMK built with the ~converter/xmk~ keyboard definition. USB HID is over USB. Communication from ~xmk~ to QMK is over USB CDC ACM UART.\n\n:CONTENTS:\n- [[#converterxmk-prerequisites][converter/xmk Prerequisites]]\n- [[#converterxmk-setup][converter/xmk Setup]]\n:END:\n\n**** converter/xmk Prerequisites\n\n- A [[https://github.com/qmk/qmk_firmware/blob/master/docs/compatible_microcontrollers.md][QMK-compatible]] MCU board.\n\n**** converter/xmk Setup\n\nThe ~converter/xmk~ keyboard definition is a available at [[https://github.com/qmk/qmk_firmware/tree/master/keyboards/converter/xmk]].\n\nAdd your keymap. If it is not using one of the supported layouts, also edit ~info.json~ to add a new entry under ~layouts~, ensuring the ~matrix~ entries are in order and without gaps. If adding support for a community layout, also append to ~community_layouts~.\n\nFor local builds, build with keyboard ~converter/xmk~.\n\nFor workflow builds, fork this repo. Edit [[./.github/workflows/build-converter-xmk.yml]] to modify the values for ~repository~ and ~ref~ in the ~qmk~ step for the QMK fork containing your keymap. Run the ~Build converter/xmk~ workflow.\n\nConnect the MCU board to USB, enter the bootloader (e.g. for [[https://learn.sparkfun.com/tutorials/pro-micro--fio-v3-hookup-guide/troubleshooting-and-faq#ts-reset][Pro-Micro]]), and flash the firmware.\n\nReconnect the MCU board and find the tty device.\n\n#+BEGIN_SRC sh\nsudo dmesg | grep tty\n#+END_SRC\n\nNote the tty device in the output.\n#+BEGIN_EXAMPLE\ncdc_acm 1-3.4.4:1.0: ttyACM0: USB ACM device\n#+END_EXAMPLE\n\nWhen using ~xmk~ for [[#typing][typing]], redirect output to the tty device from the previous step.\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM0\n#+END_SRC\n\nTo enter the bootloader after flashing the firmware, ~xmk~ can be used to trigger a ~QK_BOOT~ keycode if present in the keymap, or enter the ~boot~ command in the ~converter/xmk~ shell e.g. ~echo \"boot\" \u003e /dev/ttyACM0~.\n\n*** ZMK\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nTwo different methods of operation are supported.\n\n:CONTENTS:\n- [[#xmk-shield][xmk Shield]]\n- [[#native_posix_64-board][native_posix_64 Board]]\n:END:\n\n**** xmk Shield\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nA bare ZMK-compatible MCU board connected to the host over USB, running ZMK built with the ~xmk~ shield definition.  USB HID is over USB. Communication from ~xmk~ to ZMK is over USB CDC ACM UART.\n\n:CONTENTS:\n- [[#xmk-shield-prerequisites][xmk Shield Prerequisites]]\n- [[#xmk-shield-setup][xmk Shield Setup]]\n:END:\n\n***** xmk Shield Prerequisites\n\n- A [[https://zmk.dev/docs/hardware][ZMK-compatible]] MCU board.\n\n***** xmk Shield Setup\n\nEdit [[./zmk-config/xmk.keymap]] to add your keymap. No transform is required.\n\nFor local builds, merge https://github.com/zmkfirmware/zmk/pull/1318, ~west update~, and build with shield ~xmk~ and the appropriate board for your MCU board, using the path to [[./zmk-config]] for [[https://zmk.dev/docs/development/build-flash#building-from-zmk-config-folder][ZMK_CONFIG]].\n\nFor workflow builds, fork this repo. Edit [[./zmk-config/xmk.yml]] to adjust the value for ~board~ for your MCU board. Run the ~Build xmk shield~ workflow.\n\nConnect the MCU board to USB, enter the bootloader (e.g. for [[https://nicekeyboards.com/docs/nice-nano/getting-started#flashing-firmware-and-bootloaders][nice!nano]] or [[https://wiki.seeedstudio.com/Seeeduino-XIAO/#enter-bootloader-mode][Seeeduino XIAO]]), and flash the firmware.\n\nReconnect the MCU board and find the tty device.\n\n#+BEGIN_SRC sh\nsudo dmesg | grep tty\n#+END_SRC\n\nNote the tty device in the output.\n#+BEGIN_EXAMPLE\ncdc_acm 1-3.4.4:1.0: ttyACM0: USB ACM device\n#+END_EXAMPLE\n\nWhen using ~xmk~ for [[#typing][typing]], redirect output to the tty device from the previous step.\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM0\n#+END_SRC\n\nTo enter the bootloader after flashing the firmware, ~xmk~ can be used to trigger a ~\u0026bootloader~ binding if present in the keymap.\n\n**** native_posix_64 Board\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nNote: https://github.com/zmkfirmware/zmk/issues/1444.\n\nA Zephyr native posix application running on the host. USB HID is over USB/IP. Communication from ~xmk~ to ZMK is through a pty.\n\n:CONTENTS:\n- [[#native_posix_64-board-prerequisites][native_posix_64 Board Prerequisites]]\n- [[#native_posix_64-board-setup][native_posix_64 Board Setup]]\n:END:\n\n***** native_posix_64 Board Prerequisites\n\n- usbip\n\n***** native_posix_64 Board Setup\n\nEdit [[./zmk-config/native_posix_64.keymap]] to add your keymap. No transform is required.\n\nFor local builds, merge https://github.com/zmkfirmware/zmk/pull/1318, ~west update~, and build with board ~native_posix_64~, using the path to [[./zmk-config]] for [[https://zmk.dev/docs/development/build-flash#building-from-zmk-config-folder][ZMK_CONFIG]].\n\nFor workflow builds, fork this repo and run the ~Build native_posix_64 board~ workflow.\n\nLoad the usbip modules if necessary.\n\n#+BEGIN_SRC sh\nsudo modprobe vhci-hcd\n#+END_SRC\n\nExecute ~zmk.elf~.\n\n#+BEGIN_SRC sh\nzmk.elf\n#+END_SRC\n\nNote the pty device in the output.\n\n#+BEGIN_EXAMPLE\nUART_0 connected to pseudotty: /dev/pts/18\n#+END_EXAMPLE\n\nFind the busid of the usbip server.\n\n#+BEGIN_SRC sh\nusbip list -r localhost\n#+END_SRC\n\nNote the busid in the output.\n#+BEGIN_EXAMPLE\nExportable USB devices\n======================\n - localhost\n        1-1: OpenMoko, Inc. : unknown product (1d50:615e)\n           : /sys/devices/pci0000:00/0000:00:01.2/usb1/1-1\n           : (Defined at Interface level) (00/00/00)\n           :  0 - Human Interface Device / No Subclass / None (03/00/00)\n#+END_EXAMPLE\n\nAttach the usbip client using the busid from the previous step.\n\n#+BEGIN_SRC sh\nsudo usbip attach -r localhost -b 1-1\n#+END_SRC\n\nWhen using ~xmk~ for [[#typing][typing]], redirect output to the pty device from the earlier step.\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/pts/18\n#+END_SRC\n\n*** KMK\n:PROPERTIES:\n:TOC:      :include descendants :depth 1 :local depth\n:END:\n\nA bare KMK-compatible MCU board connected to the host over USB, running KMK with the KMK ~xmk~ keyboard definition.\nUSB HID is over USB.\nCommunication from ~xmk~ to KMK is over USB CDC ACM UART.\n\n:CONTENTS:\n- [[#kmk-xmk-prerequisites][KMK xmk Prerequisites]]\n- [[#kmk-xmk-setup][KMK xmk Setup]]\n:END:\n\n**** KMK xmk Prerequisites\n\n- A KMK-compatible MCU board.\n\n**** KMK xmk Setup\n\nMerge https://github.com/manna-harbour/kmk_firmware/tree/xmk with KMK master.\n\nInstall KMK from the merged branch according to the KMK documentation.\n\nAdd your keymap to ~boards/xmk/main.py~.\n\nCopy the contents of ~boards/xmk/~ to the root of the USB drive for your MCU board.\n\nReset or reconnect the MCU board and find the tty device.\n\n#+BEGIN_SRC sh\nsudo dmesg | grep tty\n#+END_SRC\n\nNote the second tty device in the output.\n#+BEGIN_EXAMPLE\ncdc_acm 1-1:1.0: ttyACM0: USB ACM device\ncdc_acm 1-1:1.2: ttyACM1: USB ACM device\n#+END_EXAMPLE\n\nWhen using ~xmk~ for [[#typing][typing]], redirect output to the tty device from the previous step.\n\n#+BEGIN_SRC sh\n./src/xmk -k /dev/input/by-id/usb-SIGMACHIP_USB_Keyboard-event-kbd -m ./src/maps/minidox/60_ansi -s \u003e /dev/ttyACM1\n#+END_SRC\n\n** Discussions and Support\n\n- [[https://github.com/manna-harbour/xmk/discussions/1][𝑥MK Discussions and Support]]\n\n* \n[[https://github.com/manna-harbour][https://raw.githubusercontent.com/manna-harbour/miryoku/master/data/logos/manna-harbour-boa-32.png]]\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmanna-harbour%2Fxmk","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmanna-harbour%2Fxmk","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmanna-harbour%2Fxmk/lists"}