Skip to content

Is it possible to use this library with RTIC? #4

@capnfabs

Description

@capnfabs

Hi there,

I'm a visitor from rust-embedded/embedded-hal#35 :) I'm currently trying to use shared-bus in an RTFM project and am trying to late-initialise peripherals. I can't quite get it to work when using shared-bus, however, because the initial BusManager either goes out of scope at the end of the init method, or gets moved into init::LateResources, and therefore I can't figure out how to annotate the lifetime of the BusProxy. Here's a small-ish example:

//! examples/init.rs

#![deny(unsafe_code)]
#![no_main]
#![no_std]

extern crate panic_semihosting;

use stm32f0::stm32f0x0::I2C1;

use stm32f0xx_hal::{
    i2c::I2c,
    prelude::*,
    gpio,
    gpio::{
        Alternate,
        gpiob,
    },
};

use rtfm::app;

use shared_bus::BusManager;
use ssd1306::Builder;
use ssd1306::prelude::*;
use embedded_graphics::prelude::*;

type I2C1Bus = I2c<I2C1, gpiob::PB8<Alternate<gpio::AF1>>, gpiob::PB9<Alternate<gpio::AF1>>>;

#[app(device = stm32f0::stm32f0x0)]
const APP: () = {
    static mut I2C_BUS: BusManager<
        cortex_m::interrupt::Mutex<core::cell::RefCell<I2C1Bus>>, I2C1Bus> = ();
    static mut DISPLAY: ssd1306::mode::graphics::GraphicsMode<
        ssd1306::interface::i2c::I2cInterface<
            shared_bus::proxy::BusProxy<
                '_,  // this lifetime parameter is the one I can't figure out.
                cortex_m::interrupt::Mutex<core::cell::RefCell<I2C1Bus>>,
                I2C1Bus>>> = ();

    #[init]
    fn init() -> init::LateResources {
        let dp = device;

        let mut flash = dp.FLASH;
        let mut rcc = dp.RCC.configure().freeze(&mut flash);
        let gpiob = dp.GPIOB.split(&mut rcc);

        // Configure i2C pins
        let (scl, sda) = cortex_m::interrupt::free(|token| {
            (
                gpiob.pb8.into_alternate_af1(token),
                gpiob.pb9.into_alternate_af1(token),
            )
        });
        let i2c = I2c::i2c1(dp.I2C1, (scl, sda), 400.khz(), &mut rcc);
        let bus = BusManager::<cortex_m::interrupt::Mutex<_>, _>::new(i2c);

        let mut disp: GraphicsMode<_> = Builder::new().connect_i2c(bus.acquire()).into();

        init::LateResources {
            I2C_BUS: bus,
            DISPLAY: disp,
        }
    }
};

My questions are:

  • is it possible to initialise i2c devices using SharedBus in the #[init] method of an RTFM application?
  • if not, is this something that you'd be open to design ideas / pull requests for?

Also, I can't figure out if this is more an issue on the RTFM side or on the shared-bus side - I suspect that it's a limitation intrinsic to the way resources are initialised with RTFM. I'm still new to rust; please let me know if this seems like something I should be raising over there instead.

Thanks in advance.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions