Skip to content

Commit a66ac47

Browse files
committed
Bring in cortex-m-rtic.
Currently crashes into DefaultHandler at end of main.
1 parent 6428256 commit a66ac47

4 files changed

Lines changed: 454 additions & 93 deletions

File tree

Cargo.toml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,10 @@ cortex-m = "0.7.1"
1212
cortex-m-rt = "0.6.13"
1313
defmt = "0.2.0"
1414
defmt-rtt = "0.2.0"
15+
cortex-m-rtic = "0.5"
1516
panic-probe = { version = "0.2.0", features = ["print-defmt"] }
16-
stm32f0xx-hal = { version = "0.17", features = ["stm32f030x6"] }
17+
stm32f0xx-hal = { version = "0.17", features = ["stm32f031"] }
18+
1719

1820
[features]
1921
# set logging levels here

src/lib.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@ use defmt_rtt as _; // global logger
66
use panic_probe as _;
77
use stm32f0xx_hal as _; // memory layout // panic handler
88

9+
pub mod monotonic;
10+
911
// same panicking *behavior* as `panic-probe` but doesn't print a panic message
1012
// this prevents the panic message being printed *twice* when `defmt::panic` is invoked
1113
#[defmt::panic_handler]

src/main.rs

Lines changed: 129 additions & 92 deletions
Original file line numberDiff line numberDiff line change
@@ -3,108 +3,145 @@
33

44
use neotron_bmc as _;
55

6-
use hal::{i2c, pac, prelude::*, serial, spi};
7-
use stm32f0xx_hal as hal;
6+
use neotron_bmc::monotonic::{Tim6Monotonic, U16Ext};
87

9-
static VERSION: &'static str = include_str!(concat!(env!("OUT_DIR"), "/version.txt"));
10-
11-
/// Holds all the I/O pins in our system
12-
#[allow(unused)]
13-
struct Pins {
14-
// spi_clk: hal::gpio::gpioa::PA5<hal::gpio::Alternate<hal::gpio::AF0>>,
15-
// spi_cipo: hal::gpio::gpioa::PA6<hal::gpio::Alternate<hal::gpio::AF0>>,
16-
// spi_copi: hal::gpio::gpioa::PA7<hal::gpio::Alternate<hal::gpio::AF0>>,
17-
// i2c_scl: hal::gpio::gpiob::PB6<hal::gpio::Alternate<hal::gpio::AF4>>,
18-
// i2c_sda: hal::gpio::gpiob::PB7<hal::gpio::Alternate<hal::gpio::AF4>>,
19-
uart_tx: hal::gpio::gpioa::PA9<hal::gpio::Alternate<hal::gpio::AF1>>,
20-
uart_rx: hal::gpio::gpioa::PA10<hal::gpio::Alternate<hal::gpio::AF1>>,
21-
uart_cts: hal::gpio::gpioa::PA11<hal::gpio::Alternate<hal::gpio::AF1>>,
22-
uart_rts: hal::gpio::gpioa::PA12<hal::gpio::Alternate<hal::gpio::AF1>>,
23-
led_power: hal::gpio::gpiob::PB0<hal::gpio::Output<hal::gpio::PushPull>>,
24-
led_status: hal::gpio::gpiob::PB1<hal::gpio::Output<hal::gpio::PushPull>>,
25-
}
26-
27-
#[cortex_m_rt::entry]
28-
fn main() -> ! {
29-
defmt::info!("Neotron BMC version {:?} booting", VERSION);
30-
31-
let p = pac::Peripherals::take().unwrap();
32-
33-
// Configure the clocks.
34-
// We have no external crystal, and instead run from the High Speed Internal Oscillator.
35-
let mut flash = p.FLASH;
36-
let mut rcc = p
37-
.RCC
38-
.configure()
39-
.hclk(48.mhz())
40-
.pclk(48.mhz())
41-
.sysclk(48.mhz())
42-
.freeze(&mut flash);
43-
44-
defmt::info!("Clocks are clocked");
45-
46-
let gpioa = p.GPIOA.split(&mut rcc);
47-
let gpiob = p.GPIOB.split(&mut rcc);
48-
49-
let mut pins: Pins = cortex_m::interrupt::free(move |cs| {
50-
Pins {
51-
// SPI pins
52-
// spi_clk: gpioa.pa5.into_alternate_af0(cs),
53-
// spi_cipo: gpioa.pa6.into_alternate_af0(cs),
54-
// spi_copi: gpioa.pa7.into_alternate_af0(cs),
55-
// I²C pins
56-
// i2c_scl: gpiob.pb6.into_alternate_af4(cs),
57-
// i2c_sda: gpiob.pb7.into_alternate_af4(cs),
58-
// USART pins
59-
uart_tx: gpioa.pa9.into_alternate_af1(cs),
60-
uart_rx: gpioa.pa10.into_alternate_af1(cs),
61-
uart_cts: gpioa.pa11.into_alternate_af1(cs),
62-
uart_rts: gpioa.pa12.into_alternate_af1(cs),
63-
// LED pins
64-
led_power: gpiob.pb0.into_push_pull_output(cs),
65-
led_status: gpiob.pb1.into_push_pull_output(cs),
66-
}
67-
});
68-
69-
// // Configure UART. Pick some default baud rate - we can change it later
70-
let mut serial = serial::Serial::usart1(
71-
p.USART1,
72-
(pins.uart_tx, pins.uart_rx),
73-
115_200.bps(),
74-
&mut rcc,
75-
);
76-
77-
use core::fmt::Write;
78-
79-
loop {
80-
serial.write_str("Hello, world!\r\n").unwrap();
81-
82-
defmt::info!("Off Off");
83-
84-
pins.led_power.set_low().unwrap();
85-
pins.led_status.set_low().unwrap();
8+
use cortex_m_rt::exception;
869

87-
cortex_m::asm::delay(6_000_000);
10+
use rtic::app;
8811

89-
defmt::info!("Off On");
12+
use stm32f0xx_hal::{
13+
gpio::gpioa::{PA10, PA11, PA12, PA9},
14+
gpio::gpiob::{PB0, PB1},
15+
gpio::{Alternate, Output, PushPull, AF1},
16+
pac,
17+
prelude::*,
18+
serial,
19+
};
9020

91-
pins.led_power.set_low().unwrap();
92-
pins.led_status.set_high().unwrap();
21+
use cortex_m::interrupt::free as disable_interrupts;
9322

94-
cortex_m::asm::delay(6_000_000);
23+
static VERSION: &'static str = include_str!(concat!(env!("OUT_DIR"), "/version.txt"));
9524

96-
defmt::info!("On Off");
25+
const PERIOD_MS: u16 = 1000;
9726

98-
pins.led_power.set_high().unwrap();
99-
pins.led_status.set_low().unwrap();
27+
#[app(device = crate::pac, peripherals = true, monotonic = crate::Tim6Monotonic)]
28+
const APP: () = {
29+
struct Resources {
30+
uart_cts: PA11<Alternate<AF1>>,
31+
uart_rts: PA12<Alternate<AF1>>,
32+
led_power: PB0<Output<PushPull>>,
33+
led_status: PB1<Output<PushPull>>,
34+
serial: serial::Serial<pac::USART1, PA9<Alternate<AF1>>, PA10<Alternate<AF1>>>,
35+
}
10036

101-
cortex_m::asm::delay(6_000_000);
37+
#[init(spawn = [blinker])]
38+
fn init(ctx: init::Context) -> init::LateResources {
39+
defmt::info!("Neotron BMC version {:?} booting", VERSION);
40+
41+
let dp: pac::Peripherals = ctx.device;
42+
43+
let mut flash = dp.FLASH;
44+
let mut rcc = dp
45+
.RCC
46+
.configure()
47+
.hclk(48.mhz())
48+
.pclk(48.mhz())
49+
.sysclk(48.mhz())
50+
.freeze(&mut flash);
51+
52+
defmt::info!("Configuring TIM6 at 7.8125 kHz...");
53+
crate::Tim6Monotonic::initialize(dp.TIM6);
54+
55+
defmt::info!("Creating pins...");
56+
let gpioa = dp.GPIOA.split(&mut rcc);
57+
let gpiob = dp.GPIOB.split(&mut rcc);
58+
let (uart_tx, uart_rx, uart_cts, uart_rts, mut led_power, led_status) =
59+
disable_interrupts(|cs| {
60+
(
61+
gpioa.pa9.into_alternate_af1(cs),
62+
gpioa.pa10.into_alternate_af1(cs),
63+
gpioa.pa11.into_alternate_af1(cs),
64+
gpioa.pa12.into_alternate_af1(cs),
65+
gpiob.pb0.into_push_pull_output(cs),
66+
gpiob.pb1.into_push_pull_output(cs),
67+
)
68+
});
69+
70+
defmt::info!("Creating UART...");
71+
72+
let serial = serial::Serial::usart1(dp.USART1, (uart_tx, uart_rx), 115_200.bps(), &mut rcc);
73+
74+
ctx.spawn.blinker().unwrap();
75+
76+
led_power.set_high().unwrap();
77+
78+
defmt::info!("Init complete!");
79+
80+
init::LateResources {
81+
serial,
82+
uart_cts,
83+
uart_rts,
84+
led_power,
85+
led_status,
86+
}
87+
}
10288

103-
defmt::info!("On On");
89+
#[idle(resources = [])]
90+
fn idle(_: idle::Context) -> ! {
91+
defmt::info!("Idle is running...");
92+
loop {
93+
cortex_m::asm::nop();
94+
// defmt::info!("Idle is asleep...");
95+
// cortex_m::asm::wfi();
96+
// defmt::info!("Idle is awake...");
97+
}
98+
}
10499

105-
pins.led_power.set_high().unwrap();
106-
pins.led_status.set_high().unwrap();
100+
// #[task(binds = USART1, resources=[serial])]
101+
// fn usart1_interrupt(ctx: usart1_interrupt::Context) {
102+
// defmt::info!("USART1 IRQ!");
103+
// // Reading the register clears the RX-Not-Empty-Interrupt flag.
104+
// match ctx.resources.serial.read()
105+
// {
106+
// Ok(b) => {
107+
// defmt::info!("Read byte {:x}", b);
108+
// }
109+
// Err(_) => {
110+
// defmt::warn!("No byte available?");
111+
// }
112+
// }
113+
// }
114+
115+
#[task(resources = [led_status], schedule = [blinker])]
116+
fn blinker(ctx: blinker::Context) {
117+
// Use the safe local `static mut` of RTIC
118+
static mut LED_STATE: bool = false;
119+
120+
if *LED_STATE {
121+
ctx.resources.led_status.set_low().unwrap();
122+
*LED_STATE = false;
123+
} else {
124+
ctx.resources.led_status.set_high().unwrap();
125+
*LED_STATE = true;
126+
}
127+
//ctx.schedule.blinker(ctx.scheduled + PERIOD_MS.millis()).unwrap();
128+
}
107129

108-
cortex_m::asm::delay(6_000_000);
130+
// Let it use the USB interrupt as a generic software interrupt.
131+
extern "C" {
132+
fn USB();
109133
}
134+
};
135+
136+
#[exception]
137+
unsafe fn DefaultHandler(value: i16) {
138+
defmt::panic!("DefaultHandler({})", value);
110139
}
140+
141+
// SPI pins
142+
// spi_clk: gpioa.pa5.into_alternate_af0(cs),
143+
// spi_cipo: gpioa.pa6.into_alternate_af0(cs),
144+
// spi_copi: gpioa.pa7.into_alternate_af0(cs),
145+
// I²C pins
146+
// i2c_scl: gpiob.pb6.into_alternate_af4(cs),
147+
// i2c_sda: gpiob.pb7.into_alternate_af4(cs),

0 commit comments

Comments
 (0)