784692e64a
19086: Remodel the USB in Kconfig r=aabadie a=MrKevinWeiss ### Contribution description #### The issues with current architecture Generally there has been some confusion on how to manage KConfig with respect to the board selection of default STDIO backends, specifically for boards that require a USB based backend as there are possible stacks to use. The `<BOARD>.config` way of selecting cannot handle conditional selects. The issues is more with boards such as `esp32s2-wemos-mini`, currently some USB stack will be selected regardless of overridding the preferred STDIO. Selecting a USB stack directly with `STDIO_USB*` creates some circular dependency issues with kconfig and is hard to manage. We also have a mutually exclusive USB stacks, TINYUSB or USBUS which should probably be a choice. #### Desired behaviour 1. Ideally we want a board to default to the most obvious STDIO implementation, for example, if I have nucleo, it uses a UART, for some ESPs, USB is the default way to communicate. 2. These backends could always be overridden though, for example, I may just connect directly to a UART and want my STDIO there, or maybe use a ble based STDIO. 3. The next condition would be specifically for boards with a USB based STDIO. Since we have a TINYUSB stack and a USBUS stack we would want to use the associated STDIO depending on the stack the application selects. 4. However, if nothing is selected by the application, than bring in a USB stack (board based preference) unless there is a specific non-USB based STDIO is selected. For these boards that have this requirement, we DO NOT want to bring in the USB stack if the STDIO is specifically overridden (important for kconfig). #### Update kconfiglib package to RIOT-OS org managed one There is a problem with the upstreamed Kconfiglib implementation and the maintainer is not responsive to the fix. The issue is to do with `menuconfig`s in choices and has been fixed with the RIOT-OS based fork. This PR requires this fix. #### Changes to the USB stack A new entry point is introduced `USB_DEVICE` which indicates wanting a USB device but not caring which stack is used. This allows making a `choice` between the `TINYUSB` and `USBUS` stack allowing mutual exclusivity. Making the USB stack a `choice` means that a specific stack cannot be selected from non-board/non-cpu/non-application based symbols. Thus the `REQUIRES_` design pattern is used for a module to indicate a specific stack should be selected. This is needed for the `MODULE_TINYUSB_NETDEV` in this case. #### Changes to USB STDIO implementations The `MODULE_STDIO_CDC_ACM` and `MODULE_STDIO_TINYUSB_CDC_ACM` are both depends on now, using a `REQUIRES_USB_STDIO` to select the dependencies. This means we do not have to use `select PACKAGE_TINYUSB if TEST_KCONFIG && !MODULE_USBUS` in the board select. ##### Why not just select the USB from STDIO_USB Issue with using select for STDIO choices is that we cannot check which stack we are using to default the STDIO to that, breaking desired behaviour 3. #### The `FORCE_USB_STDIO` Desired behaviour 4 means that we do not want to bring in the USB stack if we override, say, to the UART STDIO backend. Due to the limitations of Kconfig, this is my solution to prevent the USB from being brought in if there is an STDIO that doesn't need it. It is only for the `esp32s2-wemos-mini` board and would not be used in other places and would only need to be explicitly disabled for applications requiring different STDIO backend and no USB. It is not perfect but I think the best solution and fairly understandable... <details><summary><h4>Issues with Kconfig</h4></summary> When using a `choice` and having conditional defaults, for example: ```kconfig choice IMPL default FOO if CHOOSE_FOO default BAR ``` there is a limitation of the level of the level of knowledge that can be expected from Kconfig, a limitation on circular dependencies, and a limitation that the dependencies only get resolved once. For example, if ` BAR` selects something that would eventually select `CHOOSE_FOO`, then the default should be `FOO` and which would no longer select `BAR` preventing the select `CHOOSE_FOO`... Messy stuff and we would want an error saying no no no. What Kconfig cannot handle is something like: ```kconfig choice IMPL bool "Implementation" default FOO if CHOOSE_FOO default BAR config FOO bool "Foo" config BAR bool "Bar" endchoice config CHOOSE_FOO bool config SYMBOL bool select CHOOSE_FOO if !BAR ``` `SYMBOL` causes a circular dependency in Kconfig even though the only possible outcome for the `choice` selection would be static. If we select `BAR` then `CHOOSE_FOO` would not be selected and we stay with `BAR`. If we select `FOO` than `CHOOSE_FOO` will be selected which stays with `FOO`. Everything should be fine, but isn't because Kconfig does not resolve to that degree, it simply sees that there is a dependency of the `IMPL` choice outcome (ie. `if !BAR`) that is a condition for a dependency of the `IMPL` choice selection (ie. ` if CHOOSE_FOO`). This is a limitation of the Kconfig what what makes this problem so challenging, with Make we say "select some sort of USB backend if no other stdio is specifically requested" and it will. </details> An attempt at remodelling the dependencies of the USB stack in Kconfig. Currently there are some issues, especially with the integration of TinyUSB package as a backend. This will require a kconfiglib package fix though... ### Testing procedure `TEST_KCONFIG=1 BOARD=reel make menuconfig -C examples/hello-world` ### Issues/PRs references Requires https://github.com/ulfalizer/Kconfiglib/pull/123 to be merged upstream or fork for RIOT Relates maybe to #18998 and #19038 19672: pkg/micropython: model in Kconfig r=aabadie a=aabadie Co-authored-by: MrKevinWeiss <weiss.kevin604@gmail.com> Co-authored-by: Alexandre Abadie <alexandre.abadie@inria.fr> |
||
---|---|---|
.cargo | ||
.github | ||
.vscode | ||
boards | ||
bootloaders | ||
core | ||
cpu | ||
dist | ||
doc | ||
drivers | ||
examples | ||
fuzzing | ||
kconfigs | ||
makefiles | ||
pkg | ||
sys | ||
tests | ||
.bandit | ||
.gitattributes | ||
.gitignore | ||
.mailmap | ||
.murdock | ||
.murdock.yml | ||
bors.toml | ||
CITATION.cff | ||
CODE_OF_CONDUCT.md | ||
CODEOWNERS | ||
CODING_CONVENTIONS_C++.md | ||
CODING_CONVENTIONS.md | ||
CONTRIBUTING.md | ||
doc.txt | ||
Kconfig | ||
LICENSE | ||
LOSTANDFOUND.md | ||
MAINTAINING.md | ||
Makefile | ||
Makefile.base | ||
Makefile.dep | ||
Makefile.features | ||
Makefile.include | ||
README.md | ||
release-notes.txt | ||
SECURITY.md | ||
SUBSYSTEMS.md | ||
uncrustify-riot.cfg | ||
Vagrantfile |
The friendly Operating System for IoT!
RIOT is a real-time multi-threading operating system that supports a range of devices that are typically found in the Internet of Things (IoT): 8-bit, 16-bit and 32-bit microcontrollers.
RIOT is based on the following design principles: energy-efficiency, real-time capabilities, small memory footprint, modularity, and uniform API access, independent of the underlying hardware (this API offers partial POSIX compliance).
RIOT is developed by an international open source community which is independent of specific vendors (e.g. similarly to the Linux community). RIOT is licensed with LGPLv2.1, a copyleft license which fosters indirect business models around the free open-source software platform provided by RIOT, e.g. it is possible to link closed-source code with the LGPL code.
FEATURES
RIOT provides features including, but not limited to:
- a preemptive, tickless scheduler with priorities
- flexible memory management
- high resolution, long-term timers
- MTD abstraction layer
- File System integration
- support 200+ boards based on AVR, MSP430, ESP8266, ESP32, RISC-V, ARM7 and ARM Cortex-M
- the native port allows to run RIOT as-is on Linux and BSD. Multiple instances of RIOT running on a single machine can also be interconnected via a simple virtual Ethernet bridge or via a simulated IEEE 802.15.4 network (ZEP)
- IPv6
- 6LoWPAN (RFC4944, RFC6282, and RFC6775)
- UDP
- RPL (storing mode, P2P mode)
- CoAP
- OTA updates via SUIT
- MQTT
- USB (device mode)
- Display / Touchscreen support
- CCN-Lite
- LoRaWAN
- UWB
- Bluetooth (BLE) via NimBLE
GETTING RIOT
The most convenient way to get RIOT is to clone it via Git
$ git clone https://github.com/RIOT-OS/RIOT
this will ensure that you get all the newest features and bug fixes with the caveat of an ever changing work environment.
If you prefer things more stable, you can download the source code of one of our quarter annual releases via Github as ZIP file or tarball. You can also checkout a release in a cloned Git repository using
$ git pull --tags
$ git checkout <YYYY.MM>
For more details on our release cycle, check our documentation.
GETTING STARTED
- You want to start the RIOT? Just follow our quickstart guide or try this tutorial. For specific toolchain installation, follow instructions in the getting started page.
- The RIOT API itself can be built from the code using doxygen. The latest version of the documentation is uploaded daily to doc.riot-os.org.
FORUM
Do you have a question, want to discuss a new feature, or just want to present your latest project using RIOT? Come over to our forum and post to your hearts content.
CONTRIBUTE
To contribute something to RIOT, please refer to our contributing document.
MAILING LISTS
- RIOT commits: commits@riot-os.org
- Github notifications: notifications@riot-os.org
LICENSE
- Most of the code developed by the RIOT community is licensed under the GNU Lesser General Public License (LGPL) version 2.1 as published by the Free Software Foundation.
- Some external sources, especially files developed by SICS are published under a separate license.
All code files contain licensing information.
For more information, see the RIOT website: