Hi raiden00pl,

Regarding your point about the NimBLE port using the POSIX API — yes, it
uses POSIX, but there are real issues with the current implementation that
go beyond just kernel/protected mode support.
1. ble_npl_hw_enter_critical is not a real critical section

Look at the NuttX port's implementation:
https://github.com/apache/mynewt-nimble/blob/master/porting/npl/nuttx/src/os_atomic.c

static pthread_mutex_t s_mutex = PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP;

uint32_t ble_npl_hw_enter_critical(void)
{
    pthread_mutex_lock(&s_mutex);
    return 0;
}

This is a mutex, not a critical section. It does not disable interrupts or
preemption — an ISR can still fire and corrupt data that the "critical
section" was supposed to protect. On top of that, using a mutex opens the
door to ABBA deadlocks when combined with any other lock held inside the
critical region:

   - Thread A: enter_critical → lock(s_mutex) → try lock(mutex M) ← blocked
   by B
   - Thread B: lock(M) → enter_critical → lock(s_mutex) ← blocked by A

Compare this with the FreeRTOS port, which correctly uses
vPortEnterCritical() / vPortExitCritical() (i.e., actually disabling
scheduling/preemption). The current NuttX port simply does not meet the
semantic contract that the NimBLE stack expects from
ble_npl_hw_enter_critical.
2. Time subsystem uses clock_gettime instead of kernel tick APIs

https://github.com/apache/mynewt-nimble/blob/master/porting/npl/nuttx/src/os_time.c

ble_npl_time_get() is backed by clock_gettime(CLOCK_MONOTONIC, ...), which
involves a syscall and floating-point arithmetic on every call. In a BLE
stack where timestamps and timing are on the hot path, this adds measurable
overhead compared to accessing the kernel tick counter directly.
3. Others are already using the kernel approach — and for good reason

A concrete example: Xiaomi's Bluetooth stack (zblue) for openvela/NuttX
uses kernel APIs directly, bypassing POSIX for the performance-critical
paths:
https://github.com/sprhawk/zblue-port-openvela/tree/yaotepai/port/kernel

This isn't an academic exercise — it's a production choice. They recognized
that a BLE stack needs tight integration with the OS timer subsystem,
direct access to critical section primitives, and efficient event delivery,
none of which POSIX provides well in this context.
My question

If other organizations are already using a more performant, architecturally
correct kernel-level integration for their BLE stacks on NuttX, why should
we be told that we must use the slower, less correct POSIX path? NuttX's
POSIX compliance is valuable, but it shouldn't come at the cost of shipping
a BLE stack with a broken critical section primitive. There should be room
for both approaches, and the decision should be driven by technical merit,
not by treating POSIX as the only acceptable answer.

Best regards,

raiden00pl <[email protected]> 于2026年10月16日周五 14:06写道:

> > 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.
>
> Is this an AI analysis or something? Because it’s definitely not true:
> Nimble
> port uses the POSIX API. The only issue with kernel mode is that
> SIGEV_SIGNAL is not supported in kernel mode, but this is a nuttx
> limitation,
> not a port architecture issue.
> I agree that synchronizing with an external repository is a challenge.
> However,
> a plus side is that we aren't the ones maintaining the code that must
> comply
> with the BLE standard.
>
> I also consider placing the entire BLE stack within the kernel to be a bad
> idea.
> Even if performance isn't ideal, it’s the price one pays for a sound
> architecture.
> NuttX has always focused on addressing architectural challenges (POSIX
> compliance)
> rather than striving to be the best in terms of performance.
>
>
> pt., 16 paź 2026 o 06:52 chao an <[email protected]> napisał(a):
>
> > No, I do not agree that the current port is only a Zephyr API replacement
> > and
> > NuttX coding-style reformatting.
> >
> >
> >
> > This code base has already fixed part of the issues that still exist in
> the
> >
> > Zephyr community implementation. In addition, we still have pending
> > features and
> > fixes that have not been submitted yet. Since some of those changes were
> > made by
> > other developers, I cannot submit their work by myself without proper
> > permission
> > and attribution.
> >
> >
> > https://github.com/zephyrproject-rtos/zephyr/pull/122348
> >
> >
> > I have already stated in the email why I do not recommend putting the
> > initial
> > Bluetooth host stack into nuttx-apps. Architecturally, placing it in apps
> > would
> > cause significant performance degradation compared with the Zephyr
> design.
> > The
> > Bluetooth host stack is tightly coupled with kernel primitives, buffer
> >
> > management, work queues, timing, and HCI/driver paths. Moving it entirely
> > to
> > apps would change that integration model and make the architecture worse
> > from
> > the beginning.
> >
> >
> >
> > Therefore, please read my previous email more carefully. The concern here
> > is not
> > only the initial review size, but also the long-term architecture and
> > runtime
> > performance of the Bluetooth stack in NuttX.
> >
> > BRs,
> >
> > Xiang Xiao <[email protected]> 于2026年10月16日周五 12:44写道:
> >
> > > On Fri, Oct 16, 2026 at 11:25 AM chao an <[email protected]> wrote:
> > >
> > > > 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
> > > >
> > > >
> > > But most of these profiles should belong to the userspace, please split
> > the
> > > related code to nuttx-apps.git, instead nuttx/.
> > > especially, the code related shell spread in the whole code base:
> > >
> > >
> >
> https://github.com/anchao/nuttx/tree/6d6ddbb271cfdeb3e0993b5ebe992b4eab858c6c/net/bt/audio/shell
> > >
> > >
> >
> https://github.com/anchao/nuttx/tree/6d6ddbb271cfdeb3e0993b5ebe992b4eab858c6c/net/bt/host/classic/shell
> > >
> > >
> >
> https://github.com/anchao/nuttx/tree/6d6ddbb271cfdeb3e0993b5ebe992b4eab858c6c/net/bt/host/shell
> > >
> > >
> >
> https://github.com/anchao/nuttx/blob/6d6ddbb271cfdeb3e0993b5ebe992b4eab858c6c/net/bt/mesh/shell/
> > >
> > >
> >
> https://github.com/anchao/nuttx/blob/6d6ddbb271cfdeb3e0993b5ebe992b4eab858c6c/net/bt/services/ias/shell
> > > it's definitely wrong to put the shell code inside kernel space.
> > >
> > >
> > > > 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.
> > > >
> > > >
> > > These are kernel public API, the only problem is that they are called
> by
> > > userspace.
> > >
> > >
> > > > 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.
> > > >
> > > >
> > >
> > > But Zephyr bluetooth stack is implemented as a monolithic block like
> > > NimBLE.
> > > Your current porting just include:
> > >
> > >    1. Switch Zephyr API to NuttX kernel API
> > >    2. Format the code base to follow The NuttX coding style
> > >
> > > No any change related to the kernel/user space separation, so it's
> better
> > > to contain in nuttx-apps.git in the current stage.
> > > I would suggest you put the initial code inside nuttx-apps and move the
> > > part which belongs to the kernel step by step,
> > > so the community can review the change more carefully.
> > >
> >
>

Reply via email to