stuffs
This commit is contained in:
@@ -2,10 +2,12 @@ use crate::gpio::ports::{setup_gpio_port, Port, PortOptions, UsablePort};
|
|||||||
|
|
||||||
pub struct UsableBoard;
|
pub struct UsableBoard;
|
||||||
impl UsableBoard {
|
impl UsableBoard {
|
||||||
pub fn setup_gpio_port(&self, port: Port, options: PortOptions) -> UsablePort {
|
pub fn setup_gpio_port(&mut self, port: Port, options: PortOptions) -> UsablePort {
|
||||||
setup_gpio_port(port, options)
|
setup_gpio_port(port, options)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: have a no_op function here if so desired
|
||||||
|
|
||||||
// TODO: check page 704 for timers
|
// TODO: check page 704 for timers
|
||||||
// TODO: impl Drop trait so that tasks all run before the main function ends?
|
// TODO: impl Drop trait so that tasks all run before the main function ends?
|
||||||
// TODO: examine page 670 for when (if) I do interrupts
|
// TODO: examine page 670 for when (if) I do interrupts
|
||||||
|
@@ -1,7 +1,17 @@
|
|||||||
use crate::{memory, L};
|
use crate::{memory, H, L};
|
||||||
|
|
||||||
use super::ports::Port;
|
use super::ports::Port;
|
||||||
|
|
||||||
|
fn reverse_array<const N: usize, T: Default + Copy>(array: [T; N]) -> [T; N] {
|
||||||
|
let mut result: [T; N] = [<T>::default(); N];
|
||||||
|
|
||||||
|
for (out_index, in_index) in (0..N).rev().enumerate() {
|
||||||
|
result[out_index] = array[in_index];
|
||||||
|
}
|
||||||
|
|
||||||
|
result
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Clone, Copy)]
|
#[derive(Clone, Copy)]
|
||||||
pub enum Pin {
|
pub enum Pin {
|
||||||
Zero = 0,
|
Zero = 0,
|
||||||
@@ -14,6 +24,10 @@ pub enum Pin {
|
|||||||
Seven = 7,
|
Seven = 7,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn pins_to_bits<const N: usize>(pins: &[Pin; N]) -> [u32; N] {
|
||||||
|
pins.map(|pin| pin as u32)
|
||||||
|
}
|
||||||
|
|
||||||
pub enum Function {
|
pub enum Function {
|
||||||
Analog,
|
Analog,
|
||||||
Digital,
|
Digital,
|
||||||
@@ -23,10 +37,16 @@ pub enum Function {
|
|||||||
UART,
|
UART,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub enum Pull {
|
||||||
|
Down,
|
||||||
|
Up,
|
||||||
|
Neither,
|
||||||
|
}
|
||||||
|
|
||||||
/// Page 1351 of data sheet
|
/// Page 1351 of data sheet
|
||||||
pub struct ReadablePinOptions {
|
pub struct ReadablePinOptions {
|
||||||
pub function: Function,
|
pub function: Function,
|
||||||
pub pull_up: Option<bool>,
|
pub pull: Pull,
|
||||||
}
|
}
|
||||||
pub struct ReadablePins<const N: usize> {
|
pub struct ReadablePins<const N: usize> {
|
||||||
data_address: *mut u32,
|
data_address: *mut u32,
|
||||||
@@ -128,121 +148,49 @@ impl WritablePin {
|
|||||||
/// Page 684 of the data sheet for how the lock mechanism works
|
/// Page 684 of the data sheet for how the lock mechanism works
|
||||||
const UNLOCK: u32 = 0x4C4F434B;
|
const UNLOCK: u32 = 0x4C4F434B;
|
||||||
|
|
||||||
fn setup_pins() {
|
fn setup_pins<const N: usize>(
|
||||||
todo!();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn setup_readable_pins<const N: usize>(
|
|
||||||
port: Port,
|
port: Port,
|
||||||
pins: [Pin; N],
|
pins: [Pin; N],
|
||||||
options: ReadablePinOptions,
|
writable: bool,
|
||||||
) -> ReadablePins<N> {
|
function: Function,
|
||||||
|
pull: Pull,
|
||||||
|
) {
|
||||||
// Unlock the pins
|
// Unlock the pins
|
||||||
unsafe {
|
unsafe {
|
||||||
memory::write(port.lock(), UNLOCK);
|
memory::write(port.lock(), UNLOCK);
|
||||||
|
|
||||||
memory::set_bits(port.commit(), &pins.map(|bit| bit as u32));
|
memory::set_bits(port.commit(), &pins_to_bits(&pins));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Disable analog when it's not selected (and enable analog if it is)
|
// Disable analog when it's not selected (and enable analog if it is)
|
||||||
match options.function {
|
match function {
|
||||||
Function::Analog => unsafe {
|
Function::Analog => unsafe {
|
||||||
memory::set_bits(port.analog_mode_select(), &pins.map(|bit| bit as u32));
|
memory::set_bits(port.analog_mode_select(), &pins_to_bits(&pins));
|
||||||
},
|
},
|
||||||
_ => unsafe {
|
_ => unsafe {
|
||||||
memory::clear_bits(port.analog_mode_select(), &pins.map(|bit| bit as u32));
|
memory::clear_bits(port.analog_mode_select(), &pins_to_bits(&pins));
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
unsafe {
|
// Set to output pins if output (otherwise set to input)
|
||||||
memory::clear_bits(port.direction(), &pins.map(|bit| bit as u32));
|
if writable {
|
||||||
}
|
|
||||||
|
|
||||||
for pin in pins {
|
|
||||||
let mut memory_bits = [0; 4];
|
|
||||||
|
|
||||||
let min = (pin as u32) * 4;
|
|
||||||
let max = min + 4;
|
|
||||||
let range = min..max;
|
|
||||||
|
|
||||||
for (i, memory_bit) in range.enumerate() {
|
|
||||||
memory_bits[i] = memory_bit;
|
|
||||||
}
|
|
||||||
|
|
||||||
let values = match options.function {
|
|
||||||
Function::Analog => todo!(),
|
|
||||||
Function::Digital => [L, L, L, L],
|
|
||||||
Function::CAN => todo!(),
|
|
||||||
Function::I2C => todo!(),
|
|
||||||
Function::PWM => todo!(),
|
|
||||||
Function::UART => todo!(),
|
|
||||||
};
|
|
||||||
unsafe {
|
unsafe {
|
||||||
memory::write_bits(port.port_control(), &memory_bits, values);
|
memory::set_bits(port.direction(), &pins_to_bits(&pins));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
unsafe {
|
||||||
|
memory::clear_bits(port.direction(), &pins_to_bits(&pins));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Configure pull-up and pull-down resistors
|
let function_values = reverse_array(match function {
|
||||||
match options.pull_up {
|
Function::Analog => todo!(),
|
||||||
Some(true) => unsafe {
|
Function::Digital => [L, L, L, L],
|
||||||
memory::set_bits(port.pull_up_select(), &pins.map(|bit| bit as u32));
|
Function::CAN => [H, L, L, L],
|
||||||
},
|
Function::I2C => [L, L, H, H],
|
||||||
Some(false) => unsafe {
|
Function::PWM => [L, H, L, H],
|
||||||
memory::set_bits(port.pull_down_select(), &pins.map(|bit| bit as u32));
|
Function::UART => [L, L, L, H],
|
||||||
},
|
});
|
||||||
None => {
|
|
||||||
unsafe {
|
|
||||||
memory::clear_bits(port.pull_up_select(), &pins.map(|bit| bit as u32));
|
|
||||||
}
|
|
||||||
unsafe {
|
|
||||||
memory::clear_bits(port.pull_down_select(), &pins.map(|bit| bit as u32));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
match options.function {
|
|
||||||
Function::Digital => unsafe {
|
|
||||||
memory::set_bits(port.digital_enable(), &pins.map(|bit| bit as u32));
|
|
||||||
},
|
|
||||||
Function::Analog => unsafe {
|
|
||||||
memory::clear_bits(port.digital_enable(), &pins.map(|bit| bit as u32));
|
|
||||||
},
|
|
||||||
_ => todo!(),
|
|
||||||
}
|
|
||||||
|
|
||||||
let data_address = port.data(&pins);
|
|
||||||
|
|
||||||
let pins: [ReadablePin; N] = pins.map(|bit| ReadablePin { data_address, bit });
|
|
||||||
|
|
||||||
ReadablePins { data_address, pins }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn setup_writable_pins<const N: usize>(
|
|
||||||
port: Port,
|
|
||||||
pins: [Pin; N],
|
|
||||||
options: WritablePinOptions,
|
|
||||||
) -> WritablePins<N> {
|
|
||||||
// Unlock the pins
|
|
||||||
unsafe {
|
|
||||||
memory::write(port.lock(), UNLOCK);
|
|
||||||
|
|
||||||
memory::set_bits(port.commit(), &pins.map(|bit| bit as u32));
|
|
||||||
}
|
|
||||||
|
|
||||||
// Disable analog when it's not selected (and enable analog if it is)
|
|
||||||
match options.function {
|
|
||||||
Function::Analog => unsafe {
|
|
||||||
memory::set_bits(port.analog_mode_select(), &pins.map(|bit| bit as u32));
|
|
||||||
},
|
|
||||||
_ => unsafe {
|
|
||||||
memory::clear_bits(port.analog_mode_select(), &pins.map(|bit| bit as u32));
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
unsafe {
|
|
||||||
memory::set_bits(port.direction(), &pins.map(|bit| bit as u32));
|
|
||||||
}
|
|
||||||
|
|
||||||
for pin in pins {
|
for pin in pins {
|
||||||
let mut memory_bits = [0; 4];
|
let mut memory_bits = [0; 4];
|
||||||
|
|
||||||
@@ -254,54 +202,76 @@ pub fn setup_writable_pins<const N: usize>(
|
|||||||
memory_bits[i] = memory_bit;
|
memory_bits[i] = memory_bit;
|
||||||
}
|
}
|
||||||
|
|
||||||
let values = match options.function {
|
|
||||||
Function::Analog => todo!(),
|
|
||||||
Function::Digital => [L, L, L, L],
|
|
||||||
Function::CAN => todo!(),
|
|
||||||
Function::I2C => todo!(),
|
|
||||||
Function::PWM => todo!(),
|
|
||||||
Function::UART => todo!(),
|
|
||||||
};
|
|
||||||
unsafe {
|
unsafe {
|
||||||
memory::write_bits(port.port_control(), &memory_bits, values);
|
memory::write_bits(port.port_control(), &memory_bits, function_values);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Configure pull-up and pull-down resistors
|
||||||
|
match pull {
|
||||||
|
Pull::Down => unsafe {
|
||||||
|
memory::set_bits(port.pull_down_select(), &pins_to_bits(&pins));
|
||||||
|
},
|
||||||
|
Pull::Up => unsafe {
|
||||||
|
memory::set_bits(port.pull_up_select(), &pins_to_bits(&pins));
|
||||||
|
},
|
||||||
|
Pull::Neither => {
|
||||||
|
unsafe {
|
||||||
|
memory::clear_bits(port.pull_up_select(), &pins_to_bits(&pins));
|
||||||
|
}
|
||||||
|
unsafe {
|
||||||
|
memory::clear_bits(port.pull_down_select(), &pins_to_bits(&pins));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: check page 671 or 682 (+ more prob) for a table showing initial pin states
|
// TODO: check page 671 or 682 (+ more prob) for a table showing initial pin states
|
||||||
|
|
||||||
// TODO: finish
|
// Disable alternate function when it's not used (and enable it when it is)
|
||||||
|
match function {
|
||||||
match options.function {
|
|
||||||
Function::Analog | Function::Digital => unsafe {
|
Function::Analog | Function::Digital => unsafe {
|
||||||
memory::clear_bits(
|
memory::clear_bits(port.alternate_function_select(), &pins_to_bits(&pins));
|
||||||
port.alternate_function_select(),
|
|
||||||
&pins.map(|bit| bit as u32),
|
|
||||||
);
|
|
||||||
},
|
},
|
||||||
_ => unsafe {
|
_ => unsafe {
|
||||||
memory::set_bits(
|
memory::set_bits(port.alternate_function_select(), &pins_to_bits(&pins));
|
||||||
port.alternate_function_select(),
|
|
||||||
&pins.map(|bit| bit as u32),
|
|
||||||
);
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
match options.function {
|
// Enable digital function when it's needed (and disable it when it's not)
|
||||||
Function::Digital => unsafe {
|
match function {
|
||||||
memory::set_bits(port.digital_enable(), &pins.map(|bit| bit as u32));
|
Function::Digital | Function::UART => unsafe {
|
||||||
|
memory::set_bits(port.digital_enable(), &pins_to_bits(&pins));
|
||||||
},
|
},
|
||||||
Function::Analog => unsafe {
|
Function::Analog => unsafe {
|
||||||
memory::clear_bits(port.digital_enable(), &pins.map(|bit| bit as u32));
|
memory::clear_bits(port.digital_enable(), &pins_to_bits(&pins));
|
||||||
},
|
},
|
||||||
_ => todo!(),
|
_ => todo!(),
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setup_readable_pins<const N: usize>(
|
||||||
|
port: Port,
|
||||||
|
pins: [Pin; N],
|
||||||
|
options: ReadablePinOptions,
|
||||||
|
) -> ReadablePins<N> {
|
||||||
|
setup_pins(port, pins, false, options.function, options.pull);
|
||||||
|
|
||||||
let data_address = port.data(&pins);
|
let data_address = port.data(&pins);
|
||||||
|
let pins: [ReadablePin; N] = pins.map(|bit| ReadablePin { data_address, bit });
|
||||||
|
ReadablePins { data_address, pins }
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn setup_writable_pins<const N: usize>(
|
||||||
|
port: Port,
|
||||||
|
pins: [Pin; N],
|
||||||
|
options: WritablePinOptions,
|
||||||
|
) -> WritablePins<N> {
|
||||||
|
setup_pins(port, pins, true, options.function, Pull::Neither);
|
||||||
|
|
||||||
|
let data_address = port.data(&pins);
|
||||||
let pins: [WritablePin; N] = pins.map(|pin| WritablePin {
|
let pins: [WritablePin; N] = pins.map(|pin| WritablePin {
|
||||||
data_address,
|
data_address,
|
||||||
bit: pin,
|
bit: pin,
|
||||||
});
|
});
|
||||||
|
|
||||||
WritablePins { data_address, pins }
|
WritablePins { data_address, pins }
|
||||||
}
|
}
|
||||||
|
@@ -144,7 +144,7 @@ pub struct UsablePort {
|
|||||||
|
|
||||||
impl UsablePort {
|
impl UsablePort {
|
||||||
pub fn setup_readable_pins<const N: usize>(
|
pub fn setup_readable_pins<const N: usize>(
|
||||||
&self,
|
&mut self,
|
||||||
pins: [Pin; N],
|
pins: [Pin; N],
|
||||||
options: ReadablePinOptions,
|
options: ReadablePinOptions,
|
||||||
) -> ReadablePins<N> {
|
) -> ReadablePins<N> {
|
||||||
@@ -152,7 +152,7 @@ impl UsablePort {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn setup_writable_pins<const N: usize>(
|
pub fn setup_writable_pins<const N: usize>(
|
||||||
&self,
|
&mut self,
|
||||||
pins: [Pin; N],
|
pins: [Pin; N],
|
||||||
options: WritablePinOptions,
|
options: WritablePinOptions,
|
||||||
) -> WritablePins<N> {
|
) -> WritablePins<N> {
|
||||||
|
154
src/main.rs
154
src/main.rs
@@ -1,14 +1,71 @@
|
|||||||
#![no_std]
|
#![no_std]
|
||||||
#![no_main]
|
#![no_main]
|
||||||
|
#![feature(default_alloc_error_handler)]
|
||||||
|
|
||||||
use core::{arch::asm, ptr};
|
use core::{
|
||||||
|
alloc::{GlobalAlloc, Layout},
|
||||||
|
arch::asm,
|
||||||
|
cell::UnsafeCell,
|
||||||
|
ptr,
|
||||||
|
};
|
||||||
|
|
||||||
|
// Bump pointer allocator for *single* core systems
|
||||||
|
struct BumpPointerAlloc {
|
||||||
|
head: UnsafeCell<usize>,
|
||||||
|
end: usize,
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for BumpPointerAlloc {}
|
||||||
|
|
||||||
|
unsafe impl GlobalAlloc for BumpPointerAlloc {
|
||||||
|
unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
|
||||||
|
// `interrupt::free` is a critical section that makes our allocator safe
|
||||||
|
// to use from within interrupts
|
||||||
|
interrupt::free(|_| {
|
||||||
|
let head = self.head.get();
|
||||||
|
let size = layout.size();
|
||||||
|
let align = layout.align();
|
||||||
|
let align_mask = !(align - 1);
|
||||||
|
|
||||||
|
// move start up to the next alignment boundary
|
||||||
|
let start = (*head + align - 1) & align_mask;
|
||||||
|
|
||||||
|
if start + size > self.end {
|
||||||
|
// a null pointer signal an Out Of Memory condition
|
||||||
|
ptr::null_mut()
|
||||||
|
} else {
|
||||||
|
*head = start + size;
|
||||||
|
start as *mut u8
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe fn dealloc(&self, _: *mut u8, _: Layout) {
|
||||||
|
// this allocator never deallocates memory
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Declaration of the global memory allocator
|
||||||
|
// NOTE the user must ensure that the memory region `[0x2000_0100, 0x2000_0200]`
|
||||||
|
// is not used by other parts of the program
|
||||||
|
#[global_allocator]
|
||||||
|
static HEAP: BumpPointerAlloc = BumpPointerAlloc {
|
||||||
|
head: UnsafeCell::new(0x2000_0100),
|
||||||
|
end: 0x2000_0200,
|
||||||
|
};
|
||||||
|
|
||||||
|
#[macro_use]
|
||||||
|
extern crate alloc;
|
||||||
|
use alloc::string::String;
|
||||||
|
use alloc::{format, vec};
|
||||||
|
|
||||||
|
use cortex_m::interrupt;
|
||||||
use panic_halt as _; // you can put a breakpoint on `rust_begin_unwind` to catch panics
|
use panic_halt as _; // you can put a breakpoint on `rust_begin_unwind` to catch panics
|
||||||
|
|
||||||
use cortex_m_rt::entry;
|
use cortex_m_rt::entry;
|
||||||
use driver_and_task_library::{
|
use driver_and_task_library::{
|
||||||
setup_board, Function, Pin, Port, PortOptions, ReadablePinOptions, UsableBoard,
|
setup_board, Function, Pin, Port, PortOptions, ReadablePinOptions, UsableBoard,
|
||||||
WritablePinOptions, H, L,
|
WritablePinOptions, H, L, Pull,
|
||||||
};
|
};
|
||||||
|
|
||||||
const SYSCTL_RCGC1_R: *mut u32 = 0x400FE104 as *mut u32;
|
const SYSCTL_RCGC1_R: *mut u32 = 0x400FE104 as *mut u32;
|
||||||
@@ -24,6 +81,18 @@ const UART0_CTL_R: *mut u32 = 0x4000C030 as *mut u32;
|
|||||||
const GPIO_PORTA_AFSEL_R: *mut u32 = 0x40004420 as *mut u32;
|
const GPIO_PORTA_AFSEL_R: *mut u32 = 0x40004420 as *mut u32;
|
||||||
const GPIO_PORTA_DEN_R: *mut u32 = 0x4000451C as *mut u32;
|
const GPIO_PORTA_DEN_R: *mut u32 = 0x4000451C as *mut u32;
|
||||||
|
|
||||||
|
// page 219
|
||||||
|
/// 16 MHz
|
||||||
|
const SYSTEM_OSC_CLOCK_SPEED: u32 = 16_000_000;
|
||||||
|
// the MOSC is variable frequeny (5 MHz to 25 MHz)
|
||||||
|
|
||||||
|
// the XOSC can act as a real time clock as well!
|
||||||
|
|
||||||
|
// The internal system clock (SysClk), is derived from any of the above sources plus two others: the
|
||||||
|
// output of the main internal PLL and the precision internal oscillator divided by four (4 MHz ± 1%).
|
||||||
|
// The frequency of the PLL clock reference must be in the range of 5 MHz to 25 MHz (inclusive).
|
||||||
|
// Table 5-3 on page 220 shows how the various clock sources can be used in a system
|
||||||
|
|
||||||
/// UART0 Clock Gating Control
|
/// UART0 Clock Gating Control
|
||||||
const SYSCTL_RCGC1_UART0: u32 = 0x00000001;
|
const SYSCTL_RCGC1_UART0: u32 = 0x00000001;
|
||||||
/// port A Clock Gating Control
|
/// port A Clock Gating Control
|
||||||
@@ -41,13 +110,14 @@ const UART_FR_RXFE: u32 = 0x00000010;
|
|||||||
/// Pins 0 and 1
|
/// Pins 0 and 1
|
||||||
const PINS_0_AND_1: u32 = 0b0000_0011;
|
const PINS_0_AND_1: u32 = 0b0000_0011;
|
||||||
|
|
||||||
fn uart0_init(board: UsableBoard) {
|
fn uart0_init(board: &mut UsableBoard) {
|
||||||
unsafe {
|
unsafe {
|
||||||
// activate UART0
|
// activate UART0
|
||||||
ptr::write_volatile(
|
ptr::write_volatile(
|
||||||
SYSCTL_RCGC1_R,
|
SYSCTL_RCGC1_R,
|
||||||
ptr::read_volatile(SYSCTL_RCGC1_R) | SYSCTL_RCGC1_UART0,
|
ptr::read_volatile(SYSCTL_RCGC1_R) | SYSCTL_RCGC1_UART0,
|
||||||
);
|
);
|
||||||
|
|
||||||
// activate port A
|
// activate port A
|
||||||
// ptr::write_volatile(SYSCTL_RCGC2_R, ptr::read_volatile(SYSCTL_RCGC2_R) | SYSCTL_RCGC2_GPIOA);
|
// ptr::write_volatile(SYSCTL_RCGC2_R, ptr::read_volatile(SYSCTL_RCGC2_R) | SYSCTL_RCGC2_GPIOA);
|
||||||
// ^ commented in favor of v
|
// ^ commented in favor of v
|
||||||
@@ -113,16 +183,38 @@ fn uart0_out_string(s: &str) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const RED: [bool; 3] = [H, L, L];
|
||||||
|
const YELLOW: [bool; 3] = [H, H, L];
|
||||||
|
const GREEN: [bool; 3] = [L, H, L];
|
||||||
|
|
||||||
#[entry]
|
#[entry]
|
||||||
fn main() -> ! {
|
fn main() -> ! {
|
||||||
let board = setup_board();
|
let mut board = setup_board();
|
||||||
let port_f = board.setup_gpio_port(Port::F, PortOptions);
|
let mut port_a = board.setup_gpio_port(Port::A, PortOptions);
|
||||||
|
let mut port_f = board.setup_gpio_port(Port::F, PortOptions);
|
||||||
|
|
||||||
|
uart0_init(&mut board);
|
||||||
|
|
||||||
|
// WIP: page 682
|
||||||
|
port_a.setup_writable_pins(
|
||||||
|
[Pin::One],
|
||||||
|
WritablePinOptions {
|
||||||
|
function: Function::UART,
|
||||||
|
},
|
||||||
|
);
|
||||||
|
|
||||||
|
uart0_out_string("Hi, this is after uart setup_writable_pins\r\n\r\n");
|
||||||
|
// TODO: finish this
|
||||||
|
// port_a.setup_readable_pins([Pin::Zero], WritablePinOptions {
|
||||||
|
// function: Function::UART,
|
||||||
|
// });
|
||||||
|
// uart0_out_string("Hi, this is after uart setup_readable_pins\r\n\r\n");
|
||||||
|
|
||||||
let switches = port_f.setup_readable_pins(
|
let switches = port_f.setup_readable_pins(
|
||||||
[Pin::Zero, Pin::Four],
|
[Pin::Zero, Pin::Four],
|
||||||
ReadablePinOptions {
|
ReadablePinOptions {
|
||||||
function: Function::Digital,
|
function: Function::Digital,
|
||||||
pull_up: Some(true),
|
pull: Pull::Up,
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
let [_sw1, _sw2] = switches.pins();
|
let [_sw1, _sw2] = switches.pins();
|
||||||
@@ -134,45 +226,33 @@ fn main() -> ! {
|
|||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
let white = [H, H, H];
|
let WHITE = [H, H, H];
|
||||||
let _black = [L, L, L];
|
let BLACK = [L, L, L];
|
||||||
|
|
||||||
let red = [H, L, L];
|
let CYAN = [L, H, H];
|
||||||
let yellow = [H, H, L];
|
let BLUE = [L, L, H];
|
||||||
let green = [L, H, L];
|
let MAGENTA = [H, L, H];
|
||||||
let cyan = [L, H, H];
|
|
||||||
let blue = [L, L, H];
|
|
||||||
let magenta = [H, L, H];
|
|
||||||
|
|
||||||
let rainbow = [red, yellow, green, cyan, blue, magenta];
|
let rainbow = [RED, YELLOW, GREEN, CYAN, BLUE, MAGENTA];
|
||||||
|
|
||||||
rgb_led.write_all(cyan);
|
// TODO: WIP: debugging
|
||||||
|
// let s = format!("Rainbow: {:?}\r\n", rainbow);
|
||||||
uart0_init(board);
|
let s = String::from("\r\ntesting a static string!!!\r\n\r\n\r\n");
|
||||||
|
// let s = format!("Format");
|
||||||
rgb_led.write_all(white);
|
// let s: String = rainbow.into();
|
||||||
|
uart0_out_string(&s);
|
||||||
for _ in 0..2 {
|
|
||||||
for c in [
|
|
||||||
'H', 'a', 'y', '!', '\r', '\n', 'H', 'e', 'y', '!', '\r', '\n', 'H', 'e', 'y', '!',
|
|
||||||
'\r', '\n', 'H', 'e', 'y', '!', '\r', '\n',
|
|
||||||
] {
|
|
||||||
uart0_out_char(c as u8);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
uart0_out_string("Those example string!\r\n");
|
|
||||||
|
|
||||||
loop {
|
loop {
|
||||||
|
uart0_out_string("Hi the program is still running down here!\r\n");
|
||||||
match switches.read_all() {
|
match switches.read_all() {
|
||||||
[L, L] => {
|
[L, L] => rgb_led.write_all(WHITE),
|
||||||
rgb_led.write_all(white);
|
[L, H] => rgb_led.write_all(BLUE),
|
||||||
uart0_out_string("Hey! You're pressing the button down!\r\n");
|
[H, L] => rgb_led.write_all(RED),
|
||||||
}
|
[H, H] => rgb_led.write_all(BLACK),
|
||||||
[L, H] => rgb_led.write_all(blue),
|
|
||||||
[H, L] => rgb_led.write_all(red),
|
|
||||||
[H, H] => rgb_led.write_all(green),
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// uart0_out_string(&format!("The switches read {:?}", switches.read_all()));
|
||||||
|
|
||||||
for _ in 0..1000000 {
|
for _ in 0..1000000 {
|
||||||
unsafe {
|
unsafe {
|
||||||
asm!("nop");
|
asm!("nop");
|
||||||
|
Reference in New Issue
Block a user