Skip to content

Commit

Permalink
#9: Added example for thumbv6 target RP2040
Browse files Browse the repository at this point in the history
  • Loading branch information
marius-meissner committed May 17, 2024
1 parent 0ed8cfa commit 260d9ee
Show file tree
Hide file tree
Showing 6 changed files with 197 additions and 0 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
.idea/*
target/*
example/target/*
Cargo.lock
23 changes: 23 additions & 0 deletions example/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
[package]
name = "rt-mcp2517-example-rp-pico"
description = "Example/Test crate for testing thumbv6"
authors = ["AtlasAero GmbH <info@atlasaero.eu>", "Neomium GmbH <info@neomium.eu>"]
version = "0.1.0"
edition = "2021"

[dependencies]
mcp2517 = { path = "..", version = "*" }

# Embedded crates
embedded-hal = "1.0.0"
embedded-time = "0.12.1"
embedded-alloc = "0.5.1"
critical-section = "1.1.2"
panic-halt= "0.2.0"

# Hardware support crates
rp2040-hal = "0.10.1"
cortex-m = "0.7.7"
cortex-m-rt = "0.7.4"
rp-pico = "0.9.0"
rp2040-boot2 = "0.3.0"
50 changes: 50 additions & 0 deletions example/src/clock.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
use crate::mutex::Mutex;
use embedded_time::clock::Error;
use embedded_time::duration::{Duration, Fraction};
use embedded_time::fixed_point::FixedPoint;
use embedded_time::timer::param::{Armed, OneShot};
use embedded_time::{Clock, Instant, Timer};
use rp2040_hal::Timer as PicoTimer;

pub struct SystemClock {
inner: Mutex<Option<PicoTimer>>,
}

impl SystemClock {
pub const fn default() -> Self {
Self {
inner: Mutex::new(None),
}
}

pub fn initialize(&self, timer: PicoTimer) {
self.inner.replace(Some(timer))
}

/// Returns the current ticks in us since startup
pub fn get_ticks(&self) -> u64 {
let mut ticks = 0;

self.inner.access(|timer| {
ticks = timer.as_ref().unwrap().get_counter().ticks();
});

ticks
}
}

impl Clock for SystemClock {
type T = u64;
const SCALING_FACTOR: Fraction = Fraction::new(1, 1_000_000);

fn try_now(&self) -> Result<Instant<Self>, Error> {
Ok(Instant::new(self.get_ticks()))
}

fn new_timer<Dur: Duration>(&self, duration: Dur) -> Timer<OneShot, Armed, Self, Dur>
where
Dur: FixedPoint,
{
Timer::new(self, duration)
}
}
17 changes: 17 additions & 0 deletions example/src/heap.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
use embedded_alloc::Heap as EmbeddedAllocHeap;

#[global_allocator]
static HEAP: EmbeddedAllocHeap = EmbeddedAllocHeap::empty();

const HEAP_SIZE: usize = 65_536;

pub struct Heap {}

impl Heap {
pub fn init() {
use core::mem::MaybeUninit;

static mut HEAP_MEM: [MaybeUninit<u8>; HEAP_SIZE] = [MaybeUninit::uninit(); HEAP_SIZE];
unsafe { HEAP.init(HEAP_MEM.as_ptr() as usize, HEAP_SIZE) }
}
}
65 changes: 65 additions & 0 deletions example/src/main.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
#![no_std]
#![no_main]

pub mod clock;
pub mod heap;
pub mod mutex;

use crate::clock::SystemClock;
use crate::heap::Heap;
use hal::clocks::Clock;
use hal::fugit::RateExtU32;
use hal::pac;
use mcp2517::can::Controller;
use panic_halt as _;
use rp2040_hal as hal;

#[link_section = ".boot2"]
#[used]
pub static BOOT2: [u8; 256] = rp2040_boot2::BOOT_LOADER_GENERIC_03H;

const XTAL_FREQ_HZ: u32 = 12_000_000u32;

#[rp2040_hal::entry]
fn main() -> ! {
Heap::init();

let mut pac = pac::Peripherals::take().unwrap();
let mut watchdog = hal::Watchdog::new(pac.WATCHDOG);

// Configure the clocks
let clocks = hal::clocks::init_clocks_and_plls(
XTAL_FREQ_HZ,
pac.XOSC,
pac.CLOCKS,
pac.PLL_SYS,
pac.PLL_USB,
&mut pac.RESETS,
&mut watchdog,
)
.unwrap();

let sio = hal::Sio::new(pac.SIO);

let pins = hal::gpio::Pins::new(pac.IO_BANK0, pac.PADS_BANK0, sio.gpio_bank0, &mut pac.RESETS);

let spi_mosi = pins.gpio7.into_function::<hal::gpio::FunctionSpi>();
let spi_miso = pins.gpio4.into_function::<hal::gpio::FunctionSpi>();
let spi_sclk = pins.gpio6.into_function::<hal::gpio::FunctionSpi>();
let spi = hal::spi::Spi::<_, _, _, 8>::new(pac.SPI0, (spi_mosi, spi_miso, spi_sclk));

// Exchange the uninitialised SPI driver for an initialised one
let spi = spi.init(
&mut pac.RESETS,
clocks.peripheral_clock.freq(),
16.MHz(),
embedded_hal::spi::MODE_0,
);

// Configure GPIO5 as an CS pin
let pin_cs = pins.gpio5.into_push_pull_output();

let _controller: Controller<_, _, SystemClock> = Controller::new(spi, pin_cs);

loop {}
}
41 changes: 41 additions & 0 deletions example/src/mutex.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
use core::cell::RefCell;
use core::ops::DerefMut;
use critical_section::with;

pub struct Mutex<T> {
inner: RefCell<T>,
}

impl<T> Mutex<T> {
pub const fn new(inner: T) -> Self {
Self {
inner: RefCell::new(inner),
}
}

/// Exclusive mutable access to inner value
pub fn access<F>(&self, f: F)
where
F: FnOnce(&mut T),
{
with(|_cs| {
f(self.inner.borrow_mut().deref_mut());
})
}

/// Replaces the inner value
pub fn replace(&self, value: T) {
with(|_cs| {
self.inner.replace(value);
});
}
}

impl<T: Clone> Mutex<T> {
/// Returns a copy of the inner value
pub fn clone_inner(&self) -> T {
with(|_cs| self.inner.borrow().clone())
}
}

unsafe impl<T> Sync for Mutex<T> {}

0 comments on commit 260d9ee

Please sign in to comment.