<i509vcb[m]>
<thejpster[m]> "Oh cool, Associate Membership is..." <- > Enter your company’s information
<i509vcb[m]>
That is a bit of a problem unless you have a company
<i509vcb[m]>
Although out of pure curiosity, I wonder what the absolute minimum requirement is to be clasified as a company according to Bluetooth SIG
<i509vcb[m]>
I know that in the Linux userspace world, the Software Freedom Conservancy handles being the point of contact for compliance for Vulkan, OpenGL and OpenCL
<i509vcb[m]>
* and OpenCL implementations in Mesa that aren't maintained by the hardware vendor
takkaryx[m] has quit [Quit: Idle timeout reached: 172800s]
jakzale has quit [Remote host closed the connection]
jakzale has joined #rust-embedded
cr1901_ has joined #rust-embedded
cr1901 has quit [Ping timeout: 276 seconds]
reinchek has joined #rust-embedded
ckrenslehner[m] has joined #rust-embedded
<ckrenslehner[m]>
Hi! What is your general approach to debug logging? I get the chance to develop a proof of concept using rust (embassy-rs) for our ST-based product. In our now existing C-based firmware we use classical UART logging for... (full message at
<danielb[m]>
> storing a defmt log to a file is not supported by cargo-embed at the moment
<danielb[m]>
Are you sure about that?
<danielb[m]>
anyway if you don't want defmt, you can use rtt-target and push human-readable data through RTT
<danielb[m]>
RTT buffers data on your device, so depending on that buffer you may catch logs that come before you attach to the device
<danielb[m]>
* anyway if you don't want defmt, you can use rtt-target and push human-readable data through RTT - but this is usually less space efficient than defmt
M9names[m] has quit [Quit: Idle timeout reached: 172800s]
<MrPashaPG[m]>
<thejpster[m]> "Are you looking to implement..." <- im doing this for fun but what kind of license requirement dos it have?
<MrPashaPG[m]>
<JamesSizeland[m]> "I might be wrong, but my..." <- I don't understand what you mean. I'm just getting acquainted with these Bluetooth implementation concepts and I don't understand the requirements and permissions required. Are these types of requirements and permissions involved in the development process or are they only needed to register a commercial product?
<JamesSizeland[m]>
MrPashaPG[m]: Just commercial, experiment freely!
<MrPashaPG[m]>
<JamesSizeland[m]> "Just commercial, experiment..." <- Thank you for the explanation and your time.
<JamesMunns[m]>
<diondokter[m]> "Hey, could use an opinion here:..." <- bbqueue? (or bbq2?)
lulf[m] has joined #rust-embedded
<lulf[m]>
diondokter: Some kind of alloc() would be my recommendation (in trouble it's using one that's a bit tailored to the BLE use case).
<JamesMunns[m]>
<diondokter[m]> "Hey, could use an opinion here:..." <- (if you can rely on strictly FIFO semantics, otherwise, yeah, some kind of alloc)
dirbaio[m] has joined #rust-embedded
<dirbaio[m]>
if it's for talking to the hardware, you could make the api like the smoltcp/embassy-net driver trait, it delegates memory management to the impl so it can choose to be more efficient than "4kb per slot"
<diondokter[m]>
No, no hardware involved. The higher-level layer (the users of this crate) talks to the MAC using messages. It's those messages the MAC then needs to process and respond to that have this problem
<diondokter[m]>
lulf[m]: Do you mean a custom alloc thing? And not the rust alloc crate?
<lulf[m]>
Yeah. Well, the rust alloc might be better now, but I wanted to provide some quality of service policy for multiple connections/channels, like 'this client is guaranteed to have at least N packages available'
<diondokter[m]>
JamesMunns[m]: That would fall under the 'let the user pass some buffer for the library to allocate in' I guess
<diondokter[m]>
The annoying thing is that these big messages aren't used a lot either. Only incidental and short-lived
<JamesMunns[m]>
imo the most important deciders are:
<JamesMunns[m]>
* the variance between largest and typical messages
<JamesMunns[m]>
* whether you need to handle messages out of order (priority based, some requests take longer to serve and you want to continue to server other requests while working on that)
<diondokter[m]>
Hmmmm, maybe what I can do is put the really big message behind a feature flag so people who don't need that won't need to have an allocator for that. The other 1kb message is a response and if I can reuse a (stack or heap) allocation from the user from the request, then that'd be a solution for that message
<JamesMunns[m]>
you could do what lwip does, and have multiple "pools" of various sizes
<JamesMunns[m]>
so you could have 16x 256B buffers, 2x 1KiB buffers, and 1x 4KiB buffers or something (or some numbers chosen by the user)
<diondokter[m]>
Yeah that's possible too...
<diondokter[m]>
Lots to think about haha
<JamesMunns[m]>
(this is getting towards "build a specialized allocator" territory tho, for better or worse)
<JamesMunns[m]>
would be a fun yak to shave tho :)
<diondokter[m]>
That's definitely true haha
<diondokter[m]>
The stupid thing is that in C you'd just yolo take a pointer and be done with it :P
<dirbaio[m]>
and then get memory corruption :D
<JamesMunns[m]>
dirbaio[m]: free bonus data!
<diondokter[m]>
Well, the spec writers also yolo it
<JamesMunns[m]>
I'll just go down to the list store and pick up a bunch
<JamesMunns[m]>
(tbh every C-based netstack I've seen EITHER used malloc directly or had their own thing like lwip's pbuf pools)
<diondokter[m]>
This is an area where I think Rust can have influence on protocols. There are so many where they just expect people to use C and do all sorts of weird things. This one is pretty benign though.
<diondokter[m]>
But the PTP spec has all sorts of weird sharing of data
<thejpster[m]>
<JamesMunns[m]> "(tbh every C-based netstack I've..." <- Yes, this. Rust is missing a standardised pools allocator.
ivmarkov[m] has joined #rust-embedded
<ivmarkov[m]>
All, in your opinion: would a disable-all-interrupts+spinlock critical section (obviously on a multi-core CPU like rp2040 and the xtensa Espressif variants qualify as "lockful" or lock-free", as per wikipedia? Context is [this question and the follow-up answers](https://github.com/rust-lang/rust/issues/117305#issuecomment-2322870701)?
<ivmarkov[m]>
* Espressif variants) qualify
<ivmarkov[m]>
Basically, we have a bit of a situation where Upstream Rust refuses to accept a disable-all-interrupts+spinlock atomics' implementation as a "lock-free" implementation, but I'm wondering if their arguments are justified. As in - really - can a "NMI storm" or anything else happen while core0 is holding the lock - thus blocking it for indenfinite time, so that core1 is also not making progress for indefinite time? As in - concretely
<ivmarkov[m]>
for - say - rp2040?
<ivmarkov[m]>
* Espressif variants) qualify, * "lockful" or "lock-free", as
<JamesMunns[m]>
Dunno if these are useful points, but:
<JamesMunns[m]>
* The kernel of an OS could interrupt you much the same as interrupts do, technically in an unbounded fashion as well
<JamesMunns[m]>
* As a fun fact, armv5te is a platform also without hardware CAS atomics, and uses a "polyfill" on linux that asks the OS to perform the action in a critical section
Koen[m] has joined #rust-embedded
<Koen[m]>
:q
<JamesMunns[m]>
offering 64-bit atomics on a 32-bit target using a polyfill tho does read as weird to me.
<ivmarkov[m]>
I would really want to place this question in the topic of "baremetal", no-linux-underneath, all-code-in-a-single-space context, as it is easier to reason then.
<ivmarkov[m]>
As in your typical Embassy baremetal
berkus[m] has joined #rust-embedded
<berkus[m]>
@ivmarkov unless you check and give up the lock in case of contention, it's lockful
<ivmarkov[m]>
JamesMunns[m]: Forget about atomic64. We have long made this sacrifice. The real issue at hand is having `core::sync::atomic` in the presence of PSRAM, because of... reasons. But it really bolies down to what I asked - are disable-all-interrupts+spinlock lock-free or not (on baremetal, no kernel in sight etc., etc.)
<ivmarkov[m]>
s/bolies/boils/
<ivmarkov[m]>
* Forget about atomic64. We have long made this sacrifice. The real issue at hand is having core::sync::atomic in the presence of PSRAM, because of... reasons. But it really boils down to what I asked - are disable-all-interrupts+spinlock crit sections lock-free or not (on baremetal, no kernel in sight etc., etc.)
<ivmarkov[m]>
berkus[m]: How can I even have contention when the core that has the lock is in a disable-all-interrupts critical section?
<JamesMunns[m]>
also as Fun Facts, the RP2350 also supports PSRAM, and I believe that CAS atomics also don't work in that mapped memory space (though maybe it does with the weird config bit we have to set to avoid MPU usage? this is untested afaik)
<ivmarkov[m]>
JamesMunns[m]: Yea, 100% the problem on Espressif xtensa :( You now have my context!
Kaspar[m] has joined #rust-embedded
<Kaspar[m]>
ivmarkov[m]: If NMI is a valid argument, we'd have to mark everything using critical sections `unsafe` with `# Safety: only sound when not using NMI`.
<JamesMunns[m]>
fwiw, cortex-m also has NMIs, and cortex-m-rt does require their impl to be unsafe
<JamesMunns[m]>
because you absolutely can break other guarantees with them.
<ivmarkov[m]>
Kaspar[m]: No, bjorn3's argument about NMI is not that they can interrupt your code and break the "atomic" invariant, but that they can interrupt your code forever, all the time, and thus your core will stay "in the lock" forever, thus starving the other core also forever (as it will spinlock forever).
<JamesMunns[m]>
so could a poorly implemented OS, is the point I'm getting at
<JamesMunns[m]>
in the case of "bare metal", you ARE the OS, fulfilling the same platform guarantees, just in the guarantees of whatever RT you setup
<JamesMunns[m]>
so, a misbehaving NMI, is the same as a misbehaving OS.
<JamesMunns[m]>
both can break guarantees that are otherwise typically made of the environment.
<ivmarkov[m]>
It is also not just NMIs though, but more like - "am I missing something else unanticipated" that can block the first core "in the disable-all-interrupts lock" thus blocking the other core too on the spinlock?
<JamesMunns[m]>
I don't really know! I can't think of anything, but I guess the stated docs:
<JamesMunns[m]>
> All atomic types in this module are guaranteed to be lock-free if they’re available. This means they don’t internally acquire a global mutex.
<JamesMunns[m]>
Is ALREADY untrue in the presence of armv5te.
<berkus[m]>
<ivmarkov[m]> "How can I even have contention..." <- umm.. any other core?
<ivmarkov[m]>
berkus[m]: But... content for _what_? The point is, inside that critical section you are only modifying a `u32` so to say. As in (1) lock (2) *my_u32 = 1 (3) unlock.
<berkus[m]>
ivmarkov[m]: wait. "lock" is a interrupt_disable only?
<ivmarkov[m]>
berkus[m]: Thats the whole point.
<berkus[m]>
that's not a lock then
<berkus[m]>
it's a critical section
<ivmarkov[m]>
But interrupt disable only on one of the cores in a multi-core setup
<berkus[m]>
then you need a proper lock, no?
<ivmarkov[m]>
The other core spinlocks. Not sure if that qualifies as a "proper lock".
<berkus[m]>
spinlock is not lock free if that's what you're asking
<berkus[m]>
to need a lock you need to have a possibility of contention - i.e. several cores accessing the same variable
<berkus[m]>
if you have a possibility of contention and a lock, then it makes sense to talk about lock-free and lockful - i.e. when, in presence of contention, you carry on or retry repeatedly (allowing other cores to make progress), or you lock the resource - thus preventing other cores from making progress
<ivmarkov[m]>
berkus[m]: But the point is, the lock is very short lived, and since it disables all interrupts on the core that managed to get the lock, you have a _guarantee_ that the lock will not last forever.
<JamesMunns[m]>
@ivmarkov fwiw, my opinion is that bjorn is wrong, in that the presence of an NMI doesn't invalidate the lock-freedom of the system.
<JamesMunns[m]>
Yes, a misbehaving system may cause the system to deadlock, but that's beyond what the LANGUAGE guarantees, and more to what the SYSTEM guarantees, and that is up to the OS/RT implementor, and their requirements.
<JamesMunns[m]>
Even with hardware atomics, like aarch64, CAS ops are only guaranteed to make forward progress in certain cases, like if they are not pathologically interrupted (which can trigger a failed CAS), and if the distance between read exclusive and write exclusive is short enough.
<berkus[m]>
But the point is it is still technically NOT lock-free
<berkus[m]>
If the core dies while holding the lock nobody else will make any progress ever
<ivmarkov[m]>
berkus[m]: Agreed. But how can a core even die? A hardware error? But then your firmware is basically dead as well, and with hardware errors anything could happen, so isn't it a bit too much leaned towards theory rather than actual situation?
<JamesMunns[m]>
berkus[m]: I think this is a criteria the RT implementor MUST guarantee to uphold, for example if you kill a core, you have to unlock the spinlock if it is holding it.
<berkus[m]>
ivmarkov[m]: 1. take a lock
<berkus[m]>
2. power off
<JamesMunns[m]>
(it could go into deep sleep, wfi, etc.)
<berkus[m]>
JamesMunns[m]: yes, and that's why you might want to have a lock-free-with-a-timeout approach instead - where nobody ever holds any locks, only atomic swaps
<ivmarkov[m]>
berkus[m]: If you mean power off the first core which took the lock from the second core - yes - I see where you are going...
<berkus[m]>
ivmarkov[m]: yup, can be killed by anything, like a battery controller
<ivmarkov[m]>
But then again, as per James earlier comment: is this the SYSTEM fault, or the LANGUAGE fault?
<berkus[m]>
It's a DESIGN CHOICE fault?
<JamesMunns[m]>
I think it is a SYSTEM fault, but if you can't guarantee it won't happen, then you can't meet the LANGUAGEs requirements for offering the interface.
<ivmarkov[m]>
So... no lockless atomics on rp2350 with PSRAM...
<JamesMunns[m]>
maybe, that's what I've been advising people
<JamesMunns[m]>
(still needs to be tested though, like I mentioned that config bit in the auxillary control register might include the externally mapped memory space in the global monitor? it's unclear to me at least)
<ivmarkov[m]>
On Xtensa Espressif I have it a bit confirmed that the only approach is essentially disable-all-interrupts+spinlocks (hw atomics do not work), so yeah, don't put your core::sync::atomic stuff in PSRAM...
<berkus[m]>
i don't know anything about PSRAM shenanigans - can you elaborate what's going wrong there?
<JamesMunns[m]>
you can't state "these types only go in these linker sections"
<JamesMunns[m]>
so if you put an Atomic on the heap, and the heap is backed by external PSRAM, where CAS doesn't work, then what?
<ivmarkov[m]>
berkus[m]: Maybe James (or mabez for xtensa)... my knowledge of xtensa falls short here. But Espressif - in their C SDK implemented spinlock-based atomics when PSRAM is enabled precisely because native ones do not work... and we can't upstream these spinlock-based ones in Rust STD...
<JamesMunns[m]>
however my $0.02 is that if you can *practically* guarantee something, and document the shortcomings like "don't do silly things like wfi in an cas loop", and it makes things better for all users, you should push back on that.
<berkus[m]>
> we can't upstream these spinlock-based ones in Rust STD
<berkus[m]>
why not, espressif is an official toolchain now?
<ivmarkov[m]>
JamesMunns[m]: I'm super-careful at the moment, that's what I do. Basically PSRAM is only used for `[u8; N]` buffers, and manually-reviewed structures that are data carriers only... :(
<ivmarkov[m]>
But you can imagine the pain...
<JamesMunns[m]>
berkus[m]: espidf is an official rust target, yes
<ivmarkov[m]>
(ESP-IDF has caps-based heap, where you can configure it in such a way that it only allocates from PSRAM if yhou ask it to, else it allocs from DRAM)
<berkus[m]>
it needs to have regular testing to get to higher tiers
<berkus[m]>
be part of CI
<berkus[m]>
might be tricky )
<ivmarkov[m]>
berkus[m]: (Yes, I know, or at least it should build under CI - but I have no time for that)
<ivmarkov[m]>
* for that; not yet)
<ivmarkov[m]>
s/yhou/you/
<JamesMunns[m]>
berkus[m]: fwiw cortex-m is tier2 iirc and they're fine with limited CI testing.
<ivmarkov[m]>
Yes, but tier2/tier3 is not the point. Even with tier3 we don't have major problems (occasional breakages once per 3 months, nothing major). Yet, this atomic thing is really a bummer
<ivmarkov[m]>
To conclude the topic: even on baremetal the PSRAM thing is an issue, because portable-atomic currently will NOT switch to critical-section-based emulated atomics if it figures out your CPU supports native atomics. It will only emulate with critical-section the non-native atomics. So even that we need to fix, but at least taiki-e expressed support to fix that, with a cfg flag...
<JamesMunns[m]>
IMO it's worth pushing for the requirement to change, something like "is guaranteed, unless otherwise stated in some platform deviation list" or something :D
<ivmarkov[m]>
<JamesMunns[m]> "however my $0.02 is that if..." <- Hm, I'll ask shamelessly then: would you support us in that? You know, I'm nobody in embedded... :D
<JamesMunns[m]>
psh, I got no rank to pull, but I think there's merit to documented deviance in the service of pragmatism.
<ivmarkov[m]>
* To conclude the topic: even on baremetal the PSRAM thing is an issue, because `portable-atomic` currently will NOT switch to `critical-section`-based emulated atomics if it figures out your CPU supports native atomics. It will only emulate with `critical-section` the non-native atomics (>= `u64`). So even that we need to fix, but at least taiki-e expressed support to fix that, with a cfg flag...
<JamesMunns[m]>
If you restart the discussion somewhere, feel free to tag me in. I'd just be wearing my "just some embedded guy" hat, but happy to repeat what I said here and help to try and make a case.
<JamesMunns[m]>
(and might be worth getting consensus/discussion the wg in general, since it does apply to other embedded targets as well, before re-raising with project teams)
<ivmarkov[m]>
The thing is, this problem is a bit unique to ESP-IDF (and STD), as no other embedded MCU target has STD support (and thus needs core::sync::atomic). all others live happily with portable-atomic and there as I mentioned we won't have an issue soon.
<ivmarkov[m]>
* The thing is, this problem is a bit unique to ESP-IDF (and STD), as no other embedded MCU target has STD support (and thus needs core::sync::atomic). All others live happily with portable-atomic and there as I mentioned we won't have an issue soon.
<ivmarkov[m]>
So in a way the problem might be too small for the wg to chime in
<JamesMunns[m]>
I think its still an issue for rp23, if the exclusive monitor doesn't cover mapped psram
<JamesMunns[m]>
and would still apply to core::sync::atomic if it also requires some platform specific fill for it.
<JamesMunns[m]>
(gotta run)
<ivmarkov[m]>
JamesMunns[m]: I don't understand this if you could clarify: All Rust targets for rp23 are baremetal `core`-only no_std, right? Without support in `core::sync::atomic` for those? So who cares, as long as `portable-atomic` (will) work on those, with crit-section emulation of atomics enabled?
<JamesMunns[m]>
JamesMunns[m]: rp23 is thumbv8, and has hardware atomics. Just only on internal sram
<JamesMunns[m]>
JamesMunns[m]: so it has core::sync::atomic + CAS
<JamesMunns[m]>
JamesMunns[m]: rp2040 only has portable-atomic CAS
<ivmarkov[m]>
JamesMunns[m]: Ah clear now! So 100% same story as ESP-IDF
<JamesMunns[m]>
* rp2040 is thumbv6 only has
<thejpster[m]>
JamesMunns[m]: Correct. The MPU fix was to fix CAS atomics in internal SRAM (oops, my bad). It cannot fix CAS in XIP memory (hardware doesn’t support it).
<JamesMunns[m]>
thejpster[m]: I dunno, the auxctl docs made me wonder, they say something like "all memory sections will be treated as part of the global monitor". Worth testing imo.
<JamesMunns[m]>
thejpster[m]: Wouldn't be surprised either way tho
<ivmarkov[m]>
<berkus[m]> "> we can't upstream these..." <- Because `core::sync::atomic` must be lockless or lese they won't upstream.
<ivmarkov[m]>
* Because core::sync::atomic must be lockless or else they won't let you upstream.
<ivmarkov[m]>
Ah, it is documented black on white there. That's how they "retired" out AtomicU64 - because it was not lockless.
<ivmarkov[m]>
But now it is about PSRAM, so the stakes are much higher
mabez[m] has joined #rust-embedded
<mabez[m]>
<ivmarkov[m]> "Maybe James (or mabez for xtensa..." <- I can comment a bit on the Xtensa side, or at least Espressif's implementation of PSRAM for Xtensa. It's basically implemented like flash is for performance reasons, but because it'... (full message at
<ivmarkov[m]>
mabez[m]: Once the baremetal xtensa targets get upstream, would they be having a `core::sync::atomic` impl? Because if you don't provide one, then for baremetal you'll have it solved anyway - by just using the only other option which would be `portable-atomic`?
<ivmarkov[m]>
Actually they are upstreamed already, so perhaps the question is, are they having c-s-atomic as in right now?
<ivmarkov[m]>
s/`?/` (which would support c-s-emulated atomics anyway)?/
<mabez[m]>
ivmarkov[m]: yeah they have cas atomics in their target description currently
<ivmarkov[m]>
Ah, so not nice... in a way! :D
<ivmarkov[m]>
<mabez[m]> "yeah they have cas atomics in..." <- In the worst-worst case where our case to Upstream fails, perhaps we can use our own Json targets downstream that _must_ be used by the user if PSRAM is enabled and mapped in the ESP-IDF `malloc` allocator. For baremetal... perhaps same...
<ivmarkov[m]>
But it is gross.
<mabez[m]>
yeah it's really not pleasant, but is solvable at least
<ivmarkov[m]>
* `malloc` allocator (as we can force the json targets to emit libcalls for atomics). For
cr1901_ is now known as cr1901
jistr has quit [Quit: quit]
jistr has joined #rust-embedded
almindor[m] has joined #rust-embedded
<almindor[m]>
how does one get a `embedded-hal-async::digital::Wait` implementing gpio pin with esp-hal?
<almindor[m]>
oh nvm, I misunderstood what Wait is fr
<almindor[m]>
s/fr/for/
jistr has quit [Remote host closed the connection]
jistr has joined #rust-embedded
esden[cis] has quit [Quit: Idle timeout reached: 172800s]
Noah[m] has quit [Quit: Idle timeout reached: 172800s]
jistr has quit [Remote host closed the connection]
<JamesSizeland[m]>
I had a question about ferrocene targets for bare metal safety critical use, is there a list of qualified MCU targets?
<diondokter[m]>
I see cortex-m is out of the experimental section now. Good to see :)
<JamesSizeland[m]>
Yeah I found this, I guess I'm asking what boards are armV8-A 😅 I don't think I've come across any yet.
<diondokter[m]>
That's the Cortex-A chips (aka, what's in your phone or you macbook)
<diondokter[m]>
A raspberry pi 5 would is that too AFAIK
<diondokter[m]>
s/would//
<JamesSizeland[m]>
Aha of course, got it. Looks like some cortex-M(4F) are qualified and others can be.
<diondokter[m]>
JamesSizeland[m]: It says they're 'quality managed', not qualified
<JamesSizeland[m]>
diondokter[m]: Sorry yes, thanks for the correction
<JamesSizeland[m]>
Is anyone using Rust for embedded medical then? I guess it's still early days there.
<diondokter[m]>
Before I joined Tweede golf we've done one. But it had pretty relaxed certification requirements because of the type of device it was
<diondokter[m]>
* Before I joined Tweede golf it has done one. But it had pretty relaxed certification requirements because of the type of device it was
<JamesSizeland[m]>
But for example class C is currently not an option?
<thejpster[m]>
<diondokter[m]> "It says they're 'quality managed..." <- That’s what the docs say today, yes. If you have a need then call us and we’re can tell you what the docs will say tomorrow.
<thejpster[m]>
Also QM means “passes the full test suite”. The only difference between that and Qualified is paperwork.
<JamesSizeland[m]>
Ok, so that sounds like possible with some effort, nice.
<thejpster[m]>
s/’re//
<JamesSizeland[m]>
Thanks for the answers 🙏
<JamesSizeland[m]>
Who will be at RustNation this week btw?
jistr has joined #rust-embedded
<almindor[m]>
how would I construct a embassy_time::Delay out of a esp-hal::Delay?
<GrantM11235[m]>
You can create an embassy_time::Delay out of thin air
<almindor[m]>
that's some black magic over there...
<almindor[m]>
seriously tho how does this work? :D
<danielb[m]>
there's a time driver behind it that does the magic
<GrantM11235[m]>
It's a zero sized type. It doesn't have anything in it, it only exists to have have the delay trait impl'd for it
<danielb[m]>
embassy_time builds on embassy_time_driver, which is driven by esp_hal_embassy
<danielb[m]>
the bits are tied together with ~zipties and hotmelt~ extern "Rust" functions
<danielb[m]>
* the bits are tied together with zipties and hotmelt extern "Rust" functions
<almindor[m]>
rust abstractions get scary sometimes
<danielb[m]>
but but but... isn't this actually simple? 🥺
ShuntaroOhno[m] has joined #rust-embedded
<ShuntaroOhno[m]>
I want to develop a board called ‘Spresense‘ with Rust, but is there a channel where people can talk about individual boards?