Closed niclashoyer closed 3 years ago
The scope of this crate is just to allow a single bus to be shared across multiple drivers, but we've seen desired use cases for the embedded-nal
as well, since we would like to share a network stack between multiple elements.
Underneath, the mutex implementation is identical, but the individual trait implementations are unique for each object. I'd have to think about this. In any case, it likely would be a new crate, as what you are discussing seems outside of the scope of what this crate is aimed at fixing.
Ok thanks, closing for now. I already got an implementation for "sync" pins here that I use solely for integration testing. I'll start from there.
If it would be possible to extract resource sharing into a generic crate, that would be great.
Hey @ryan-summers, I am facing the same problem as @niclashoyer here, since the ssd1306
display driver needs not only an SPI bus, but also a "command/data"-selection GPIO pin to be shared across displays.
Thinking about this, I came to an even more generic idea: Essentially, we want to share anything which implements a trait. After all, this whole crate is essentially a thread-safe RefCell
, but with extra steps:
Thing
Thing
(just passing through).Now my idea would be to do one of the following:
CommonBus
(which can be handled with a macro; that macro could either be a #[derive(...)]
on the trait (not gonna happen, since we don't control embedded-hal), or a declarative macro where you need to repeat the trait definition. (Example below).MyCommonBus
object which handles all the traits they need.For example, the second solution could look like this:
// Creates a mod my_common_bus with CommonBus, SharedBus, new!.
// Essentially generates the same code as the shared-bus-rtic crate
// contains, but with implementations for specifically the i2c::Write
// and the TraitWeLikeToImplement traits.
make_common_bus! (my_common_bus, {
// shamelessly pasted, with tiny addition, from https://docs.rs/embedded-hal/latest/embedded_hal/blocking/i2c/trait.Write.html
trait embedded_hal::i2c::Write<A: AddressMode = SevenBitAddress> {
type Error;
fn write(&mut self, address: A, bytes: &[u8]) -> Result<(), Self::Error>;
}
trait some_other::TraitWeLikeToImplement {
fn fnord(&mut self, ...) -> Blah;
}
})
my_common_bus::new!(...)
That's only a wild idea for now, but what do you think of this?
We could have a hybrid solution, where the user can use the macro to create their own, customized version of the CommonBus
type, and still offer them a "default" CommonBus
type which implements the common stuff like spi, i2c etc.
@niclashoyer I am going to hell for this example implementation of what i meant.
This allows you (or, if the macro is exported, the crate's users) to just copy-paste any trait definition and boom, you get a SharedBus
which also supports that trait).
(Doesn't fully work tho, because I tried to implement spi::Write<T>
for all T
, which you apparently didn't do for a good reason. Will address this next week)
What do you think?
Honestly, the embedded-hal 1.0 release should be deprecating this crate and I'd really like to sunset this as soon as it becomes possible. This crate as a workaround to the limitations of SPI + CS and I2C (at the time) when being used with RTIC. Now that e-h 1.0 is intending to fix these problems internally, I'm not that interested in making large-scale changes to this crate.
I see the value in something like this,, but honestly a shared display of SPI + CS + DC signal is a somewhat rare use-case where it may make more sense to just do the implementation internally in your end crate than it would be to make a generic solution.
Would it be possible to extend this to a (set of) digital input/output pins? I'm trying to switch different drivers at runtime and all use the same pins.
If this seams feasible, I could see what I can come up with.