Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mkrzero update #697

Merged
merged 6 commits into from
Oct 2, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions boards/arduino_mkrzero/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
# Unreleased

# v0.12.1

- update to `atsamd-hal-0.16`, along with redefining pins using the bsp_pins! macro
- split up library into pin definitions and peripheral & USB setup function definitions

# v0.12.0

- update to `atsamd-hal-0.14` and other latest dependencies (#564)
Expand Down
17 changes: 15 additions & 2 deletions boards/arduino_mkrzero/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "arduino_mkrzero"
version = "0.12.0"
version = "0.12.1"
authors = ["Wez Furlong <[email protected]>", "David McGillicuddy <[email protected]>"]
description = "Board Support crate for the Arduino MKRZERO"
keywords = ["no-std", "arm", "cortex-m", "embedded-hal", "arduino"]
Expand All @@ -15,18 +15,23 @@ version = "0.7"
optional = true

[dependencies.atsamd-hal]
version = "0.14"
version = "0.16"
default-features = false

[dependencies.usb-device]
version = "0.2"
optional = true

[dependencies.embedded-sdmmc]
version = "0.3"
optional = true

[dev-dependencies]
cortex-m = "0.7"
usbd-serial = "0.1"
panic-halt = "0.2"
panic-semihosting = "0.5"
cortex-m-rtic = "1.0"

[features]
# ask the HAL to enable atsamd21g support
Expand All @@ -35,14 +40,22 @@ rt = ["cortex-m-rt", "atsamd-hal/samd21g-rt"]
usb = ["atsamd-hal/usb", "usb-device"]
unproven = ["atsamd-hal/unproven"]
use_semihosting = []
rtic = ["atsamd-hal/rtic"]

# for cargo flash
[package.metadata]
chip = "ATSAMD21G18A"

[dependencies]
embedded-hal = "0.2.7"

[[example]]
name = "blinky_basic"

[[example]]
name = "blinky_rtic"
required-features = ["rtic", "unproven"]

[[example]]
name = "usb_logging"
required-features = ["usb"]
Expand Down
4 changes: 2 additions & 2 deletions boards/arduino_mkrzero/examples/blinky_basic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,8 @@ fn main() -> ! {
&mut peripherals.SYSCTRL,
&mut peripherals.NVMCTRL,
);
let mut pins = bsp::Pins::new(peripherals.PORT);
let mut led = pins.led_builtin.into_open_drain_output(&mut pins.port);
let pins = bsp::pins::Pins::new(peripherals.PORT);
let mut led = bsp::pin_alias!(pins.led).into_push_pull_output();
let mut delay = Delay::new(core.SYST, &mut clocks);

loop {
Expand Down
73 changes: 73 additions & 0 deletions boards/arduino_mkrzero/examples/blinky_rtic.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
//! Uses RTIC with the RTC as time source to blink an LED.
//!
//! The idle task is sleeping the CPU, so in practice this gives similar power
//! figure as the "sleeping_timer_rtc" example.
#![no_std]
#![no_main]

use arduino_mkrzero as bsp;

#[cfg(not(feature = "use_semihosting"))]
use panic_halt as _;
#[cfg(feature = "use_semihosting")]
use panic_semihosting as _;
use rtic::app;

#[app(device = bsp::pac, peripherals = true, dispatchers = [EVSYS])]
mod app {
use super::*;
use bsp::hal;
use hal::clock::{ClockGenId, ClockSource, GenericClockController};
use hal::pac::Peripherals;
use hal::prelude::*;
use hal::rtc::{Count32Mode, Duration, Rtc};

#[local]
struct Local {}

#[shared]
struct Shared {
// The LED could be a local resource, since it is only used in one task
// But we want to showcase shared resources and locking
led: bsp::pins::Led,
}

#[monotonic(binds = RTC, default = true)]
type RtcMonotonic = Rtc<Count32Mode>;

#[init]
fn init(cx: init::Context) -> (Shared, Local, init::Monotonics) {
let mut peripherals: Peripherals = cx.device;
let pins = bsp::pins::Pins::new(peripherals.PORT);
let mut core: rtic::export::Peripherals = cx.core;
let mut clocks = GenericClockController::with_external_32kosc(
peripherals.GCLK,
&mut peripherals.PM,
&mut peripherals.SYSCTRL,
&mut peripherals.NVMCTRL,
);
let _gclk = clocks.gclk0();
let rtc_clock_src = clocks
.configure_gclk_divider_and_source(ClockGenId::GCLK2, 1, ClockSource::XOSC32K, false)
.unwrap();
clocks.configure_standby(ClockGenId::GCLK2, true);
let rtc_clock = clocks.rtc(&rtc_clock_src).unwrap();
let rtc = Rtc::count32_mode(peripherals.RTC, rtc_clock.freq(), &mut peripherals.PM);
let led = bsp::pin_alias!(pins.led).into();

// We can use the RTC in standby for maximum power savings
core.SCB.set_sleepdeep();

// Start the blink task
blink::spawn().unwrap();

(Shared { led }, Local {}, init::Monotonics(rtc))
}

#[task(shared = [led])]
fn blink(mut cx: blink::Context) {
// If the LED were a local resource, the lock would not be necessary
let _ = cx.shared.led.lock(|led| led.toggle());
blink::spawn_after(Duration::secs(3)).ok();
}
}
7 changes: 4 additions & 3 deletions boards/arduino_mkrzero/examples/pwm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ use panic_semihosting as _;
use bsp::entry;
use hal::clock::{GenericClockController, Tcc0Tcc1Clock};
use hal::delay::Delay;
use hal::gpio::AlternateE;
use hal::pac::{CorePeripherals, Peripherals};
use hal::prelude::*;
use hal::pwm::{Channel, Pwm0};
Expand All @@ -27,18 +28,18 @@ fn main() -> ! {
&mut peripherals.NVMCTRL,
);
let mut delay = Delay::new(core.SYST, &mut clocks);
let mut pins = bsp::Pins::new(peripherals.PORT);
let pins = bsp::pins::Pins::new(peripherals.PORT);

// PWM0_CH1 is A4 on the board - pin 19 or PA05
// see: https://github.com/arduino/ArduinoCore-samd/blob/master/variants/mkrzero/variant.cpp
let _a4 = pins.a4.into_function_e(&mut pins.port);
let _a4 = pins.pa04.into_mode::<AlternateE>();
let gclk0 = clocks.gclk0();

let tcc0_tcc1_clock: &Tcc0Tcc1Clock = &clocks.tcc0_tcc1(&gclk0).unwrap();

let mut pwm0 = Pwm0::new(
&tcc0_tcc1_clock,
1.khz(),
1u32.kHz(),
peripherals.TCC0,
&mut peripherals.PM,
);
Expand Down
37 changes: 17 additions & 20 deletions boards/arduino_mkrzero/examples/usb_logging.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,6 @@

use arduino_mkrzero as bsp;
use bsp::hal;
use usb_device;
use usbd_serial;

#[cfg(not(feature = "use_semihosting"))]
use panic_halt as _;
Expand Down Expand Up @@ -38,25 +36,28 @@ fn main() -> ! {
&mut peripherals.SYSCTRL,
&mut peripherals.NVMCTRL,
);
let mut pins = bsp::Pins::new(peripherals.PORT);
let mut led = pins.led_builtin.into_open_drain_output(&mut pins.port);
let pins = bsp::pins::Pins::new(peripherals.PORT);
let mut led = bsp::pin_alias!(pins.led).into_push_pull_output();
let mut delay = Delay::new(core.SYST, &mut clocks);

let usb_n = bsp::pin_alias!(pins.usb_n);
let usb_p = bsp::pin_alias!(pins.usb_p);

let bus_allocator = unsafe {
USB_ALLOCATOR = Some(bsp::usb_allocator(
USB_ALLOCATOR = Some(bsp::usb::usb_allocator(
peripherals.USB,
&mut clocks,
&mut peripherals.PM,
pins.usb_n, // PA24, also usb_dm
pins.usb_p, // PA24 also usb_dp
usb_n.into(),
usb_p.into(),
));
USB_ALLOCATOR.as_ref().unwrap()
};

unsafe {
USB_SERIAL = Some(SerialPort::new(&bus_allocator));
USB_SERIAL = Some(SerialPort::new(bus_allocator));
USB_BUS = Some(
UsbDeviceBuilder::new(&bus_allocator, UsbVidPid(0x2222, 0x3333))
UsbDeviceBuilder::new(bus_allocator, UsbVidPid(0x2222, 0x3333))
.manufacturer("Fake company")
.product("Serial port")
.serial_number("TEST")
Expand All @@ -78,27 +79,23 @@ fn main() -> ! {

// Turn off interrupts so we don't fight with the interrupt
cortex_m::interrupt::free(|_| unsafe {
USB_BUS.as_mut().map(|_| {
USB_SERIAL.as_mut().map(|serial| {
// Skip errors so we can continue the program
let _ = serial.write("log line\r\n".as_bytes());
});
})
if let Some(serial) = USB_SERIAL.as_mut() {
let _ = serial.write("log line\r\n".as_bytes());
}
});
}
}

fn poll_usb() {
unsafe {
USB_BUS.as_mut().map(|usb_dev| {
USB_SERIAL.as_mut().map(|serial| {
if let Some(usb_dev) = USB_BUS.as_mut() {
if let Some(serial) = USB_SERIAL.as_mut() {
usb_dev.poll(&mut [serial]);

// Make the other side happy
let mut buf = [0u8; 16];
let _ = serial.read(&mut buf);
});
});
}
}
};
}

Expand Down
123 changes: 3 additions & 120 deletions boards/arduino_mkrzero/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,126 +7,9 @@ extern crate cortex_m_rt;
#[cfg(feature = "rt")]
pub use cortex_m_rt::entry;

#[cfg(feature = "usb")]
use gpio::v2::{AnyPin, PA24, PA25};
#[cfg(feature = "usb")]
use hal::clock::GenericClockController;
#[cfg(feature = "usb")]
use hal::usb::usb_device::bus::UsbBusAllocator;
#[cfg(feature = "usb")]
pub use hal::usb::UsbBus;

use hal::prelude::*;
use hal::*;

pub use hal::common::*;

pub use hal::pac;

use gpio::{Floating, Input, Port};

// The docs could be further improved with details of the specific channels etc
define_pins!(
/// Maps the pins to their arduino names and the numbers printed on the board.
/// Information from: <https://github.com/arduino/ArduinoCore-samd/blob/master/variants/mkrzero/variant.cpp>
struct Pins,
pac: pac,

/// Digital 0: PWM, TC
pin d0 = a22,

/// Digital 1: PWM, TC
pin d1 = a23,

/// Digital 2: PWM, TCC, ADC
pin d2 = a10,

/// Digital 3: PWM, TCC, ADC
pin d3 = a11,

/// Digital 4: PWM, TC
pin d4 = b10,

/// Digital 5: PWM, TC
pin d5 = b11,

/// Digital 6: PWM, TCC
pin d6 = a20,

/// Digital 7: PWM, TCC
pin d7 = a21,

/// SPI MOSI: PWM, TCC
pin mosi = a16,

/// SPI SCK
pin sck = a17,

/// SPI MISO: PWM, TC
pin miso = a19,

/// SDA
pin sda = a8,

/// SCL
pin scl = a9,

/// RX
pin rx = b23,

/// TX
pin tx = b22,

/// Analog 0: DAC
pin a0 = a2,

/// Analog 1
pin a1 = b2,

/// Analog 2
pin a2 = b3,

/// Analog 3: PWM, TCC
pin a3 = a4,

/// Analog 4: PWM, TCC
pin a4 = a5,

/// Analog 5
pin a5 = a6,

/// Analog 6
pin a6 = a7,

pin usb_n = a24,
pin usb_p = a25,
pin usb_id = a18,
pin aref = a3,
pin sd_sck = a12,
pin sd_mosi = a13,
pin sd_ss = a14,
pin sd_miso = a15,
pin sd_cd = a27,

/// LED built into the board
pin led_builtin = b8,

pin bottom_pad = a28,
pin adc_battery = b9,
pin xin32 = a0,
pin xout32 = a1,
);

pub mod pins;
pub mod sercom;
#[cfg(feature = "usb")]
pub fn usb_allocator(
usb: pac::USB,
clocks: &mut GenericClockController,
pm: &mut pac::PM,
dm: impl AnyPin<Id = PA24>,
dp: impl AnyPin<Id = PA25>,
) -> UsbBusAllocator<UsbBus> {
let gclk0 = clocks.gclk0();
let usb_clock = &clocks.usb(&gclk0).unwrap();

UsbBusAllocator::new(UsbBus::new(usb_clock, pm, dm, dp, usb))
}
pub mod usb;
Loading