Hi all, I would like to summarize the background, technical motivation, and proposed evolution plan for PR #20686, which introduces a Zephyr-based Bluetooth host stack under net/bt.
https://github.com/apache/nuttx/pull/20686 First of all, I fully understand the concerns raised in the discussion. Adding a new Bluetooth stack is a significant architectural change, and it is reasonable for the community to ask whether we should instead continue improving the existing NuttX Bluetooth implementation. I would like to explain why we believe introducing the new stack incrementally is the more practical path, while still keeping the long-term NuttX architecture clean and maintainable. ------------------------------ 1. Why not only enhance the existing NuttX Bluetooth stack? The existing NuttX Bluetooth implementation is mainly focused on BLE functionality. However, modern Bluetooth support is no longer limited to basic BLE. A complete Bluetooth host stack now commonly includes: - BLE GAP/GATT/ATT/SMP - Classic Bluetooth profiles - A2DP - AVRCP - HFP/HSP - HID - LE Mesh - LE Audio - Additional profile-level interoperability logic The Zephyr Bluetooth stack already provides a broad and actively maintained implementation across many of these areas. Rebuilding equivalent functionality directly on top of the current NuttX Bluetooth stack would require a very large multi-year effort, including not only protocol implementation but also interoperability testing with real phones, headsets, speakers, cars, and other commercial devices. Therefore, our goal is not to discard NuttX's existing work lightly, but to provide a practical path to make NuttX capable of supporting a much wider Bluetooth feature set in a reasonable time frame. ------------------------------ 2. Why place the stack in nuttx instead of nuttx-apps? Another important discussion point is whether the new Bluetooth stack should live in nuttx-apps, similar to how NimBLE is currently integrated. Our concern is that a host stack is not just an application-level component. It interacts closely with: - HCI transport - L2CAP channels - Socket or device interfaces - Memory pools - Timers and work queues - Security and pairing state - Profile registration - Controller event dispatch - Future kernel/user boundary mechanisms Putting the core host stack in nuttx-apps would either require exposing many internal kernel interfaces or would force the application-side stack to depend on non-public NuttX internals. We already have a similar problem with the current NimBLE integration. The NimBLE port in nuttx-apps directly depends on many NuttX kernel/internal APIs. As a result, it is difficult to support protected/kernel builds cleanly, and it is also hard to keep the port synchronized with upstream NimBLE over time. For this reason, we believe the Bluetooth host core belongs in the NuttX tree. User-facing profiles, tools, shell commands, or demo applications can still live outside the core as appropriate, but the transport-facing host stack should have a well-defined place inside NuttX. There is also a performance consideration. In flat build mode, the Bluetooth host stack can run directly on the kernel side without additional syscall or user/kernel boundary overhead. This is especially important for IoT chips with relatively low CPU frequency, where Bluetooth data path and profile handling overhead can have a visible impact on throughput, latency, and power consumption. At the same time, this does not mean that the final architecture must remain flat-build-only. A compatible evolution path is to keep the performance-sensitive transport and host core on the kernel side, while gradually moving suitable Bluetooth profile implementations or profile-facing helper layers into libc-visible build paths. This allows protected and kernel builds to use proper public interfaces, while still preserving good performance for flat build and low-end IoT platforms. In other words, placing the stack in nuttx gives us a cleaner long-term architecture: - Flat build can get the best performance with minimum overhead. - Protected/kernel build can be supported later through proper public interfaces. - Profile code can be migrated into libc-compatible paths where appropriate. - Userspace does not need to directly depend on private kernel symbols. - The design avoids repeating the long-term maintainability issue seen in some existing userspace Bluetooth integrations. ------------------------------ 3. Coexistence with the existing NuttX Bluetooth stack We also understand the concern that net/bt and the existing Bluetooth implementation currently expose different APIs and are not mutually compatible. The current proposal is not to immediately remove the legacy stack. Instead, the new stack is introduced as an optional implementation guarded by Kconfig. This allows: - Existing users of the legacy stack to continue working. - New users to test the Zephyr-based stack. - The community to compare functionality and architecture. - Migration work to happen incrementally. In the long term, if the new stack becomes stable and covers more use cases, we can discuss how to reduce duplication, unify public APIs where possible, or eventually deprecate parts that are no longer maintained. But we do not propose an immediate disruptive replacement. ------------------------------ 4. Current limitation: flat build only The current implementation is intentionally limited to flat build. This is now reflected in Kconfig by making CONFIG_BT depend on BUILD_FLAT. The Kconfig help text also documents that protected and kernel builds are not supported yet. The reason is that the first phase focuses on getting the host stack working correctly inside NuttX with minimal syscall overhead and minimal boundary complexity. In flat build, the Bluetooth stack can run directly with the required kernel-side resources, which is suitable for validating the transport, host, and profile behavior first. This also provides better runtime performance for low-end IoT chips, where avoiding additional syscall and user/kernel boundary overhead is valuable for Bluetooth throughput, latency, and power efficiency. We do not want to hide this limitation. Protected/kernel build support is important, but it should be added with a proper architecture rather than by exposing many internal kernel APIs directly to userspace. ------------------------------ 5. Planned protected/kernel build support Our plan is to add protected/kernel build support in a later phase, currently targeted for 27Q2. The intended direction is: - Keep the transport-facing Bluetooth host logic on the kernel side. - Expose user-facing functionality through proper socket/VFS/device interfaces. - Move suitable profiles or profile helpers into libc-visible build paths where appropriate. - Allow profile implementations to be shared across flat, protected, and kernel builds where possible. - Avoid userspace directly depending on private kernel symbols. - Keep syscall boundaries explicit and maintainable. This is different from simply placing the whole host stack in nuttx-apps and allowing it to call internal kernel APIs. We want to avoid repeating the long-term maintainability problem that exists in some current userspace Bluetooth integrations. The goal is to support protected/kernel builds without sacrificing the performance advantage that flat build can provide on resource-constrained IoT platforms. ------------------------------ 6. Why incremental upstreaming is useful We understand the preference for a complete architecture before merging. However, the Bluetooth stack is large. Waiting until BLE, Classic Bluetooth, all profiles, socket integration, protected build support, and every cleanup item are complete before upstreaming would make the patch set very large and difficult to review. An incremental approach has several advantages: - The community can review the basic architecture earlier. - Simulator testing can be added and improved gradually. - BLE and Classic paths can be validated step by step. - Future profile work can build on a shared base. - Long-lived out-of-tree divergence can be avoided. - Copyright and style issues can be corrected early. - Architectural feedback can be incorporated before the stack grows further. This PR is intended as phase 1: establish the base host stack integration, Kconfig structure, compatibility layer, and simulator-testable functionality. It is not intended to claim that all final architecture work is complete. ------------------------------ 7. Testing status At this stage, the supported platform is the simulator configuration only. The simulator Bluetooth test framework covers both: - Classic Bluetooth related paths. - BLE related paths. This allows us to validate the core host stack behavior in CI-friendly environments first. Hardware-specific controller and transport support can then be added progressively after the base stack becomes stable. ------------------------------ 8. Copyright cleanup The copyright concern is valid. The imported code should preserve the original Zephyr copyright and license information where applicable, and new NuttX-specific adaptation code should follow the standard Apache NuttX copyright style. Any unrelated third-party company copyright notices introduced by the porting process should be removed unless they are legally required for genuinely original contributions from that entity. We are willing to clean this up as part of the PR. ------------------------------ 9. Summary To summarize our position: - Enhancing the existing BLE-focused NuttX stack into a full modern Bluetooth stack would be a very large effort. - The Zephyr Bluetooth stack already provides broad functionality across BLE, Classic Bluetooth, Mesh, LE Audio, and profiles. - The new stack currently supports flat build only, and this limitation is now explicitly documented in Kconfig. - Flat build provides better runtime performance by avoiding additional syscall and user/kernel boundary overhead, which is especially important for low-end IoT chips. - Protected/kernel build support is planned for 27Q2 using proper socket/VFS/libc-visible interfaces instead of exposing private kernel APIs directly. - Suitable Bluetooth profile implementations can later be migrated into libc-compatible build paths, allowing protected/kernel build compatibility while preserving good performance in flat build. - The new stack can coexist with the legacy Bluetooth implementation during the transition period. - Incremental upstreaming is preferable to maintaining a large out-of-tree port until every future phase is complete. - Simulator testing currently covers both Classic Bluetooth and BLE paths. We hope this clarifies the motivation and direction of the proposal. We are open to improving the structure, naming, Kconfig organization, copyright cleanup, and documentation based on community feedback. Our goal is to provide NuttX with a maintainable path toward a complete modern Bluetooth stack while respecting NuttX's architecture and long-term maintainability. Thanks, Archer
