Skip to content

Commit f7b1c18

Browse files
committed
Use bitflags for triggering flag on GPIOHS
1 parent ce08802 commit f7b1c18

File tree

2 files changed

+169
-80
lines changed

2 files changed

+169
-80
lines changed

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,3 +13,4 @@ edition = "2018"
1313
embedded-hal = { version = "0.2.3", features = ["unproven"] }
1414
nb = "0.1.1"
1515
k210-pac = "0.2.0"
16+
bitflags = "1.2.1"

src/gpiohs.rs

Lines changed: 168 additions & 80 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,123 @@ use core::marker::PhantomData;
55
use crate::bit_utils::{u32_set_bit, u32_toggle_bit, u32_bit_is_set, u32_bit_is_clear};
66
use embedded_hal::digital::v2::{InputPin, OutputPin};
77

8+
// todo: verify
9+
10+
/// Floating mode (type state)
11+
pub struct Floating;
12+
13+
/// PullUp mode (type state)
14+
pub struct PullUp;
15+
16+
/// Input mode (type state)
17+
pub struct Input<MODE>(MODE);
18+
19+
/// Output mode (type state)
20+
pub struct Output<MODE>(MODE);
21+
22+
pub trait GpiohsExt {
23+
fn split(self) -> Parts;
24+
}
25+
26+
impl GpiohsExt for pac::GPIOHS {
27+
fn split(self) -> Parts {
28+
Parts {
29+
gpiohs0: Gpiohs0 { _mode: PhantomData },
30+
}
31+
}
32+
}
33+
34+
pub struct Parts {
35+
pub gpiohs0: Gpiohs0<Input<Floating>>,
36+
}
37+
38+
pub struct Gpiohs0<MODE> {
39+
_mode: PhantomData<MODE>,
40+
}
41+
42+
impl<MODE> Gpiohs0<MODE> {
43+
pub fn into_pull_up_input(self) -> Gpiohs0<Input<PullUp>> {
44+
pac::GPIOHS::set_output_en(0, false);
45+
pac::GPIOHS::set_input_en(0, true);
46+
pac::GPIOHS::set_pullup_en(0, true);
47+
Gpiohs0 { _mode: PhantomData }
48+
}
49+
50+
// todo: all modes
51+
}
52+
53+
bitflags::bitflags! {
54+
pub struct Edge: u8 {
55+
const RISING = 0b00000001;
56+
const FALLING = 0b00000010;
57+
const HIGH = 0b00000100;
58+
const LOW = 0b00001000;
59+
}
60+
}
61+
62+
impl<MODE> Gpiohs0<MODE> {
63+
pub fn trigger_on_edge(&self, edge: Edge) {
64+
pac::GPIOHS::set_rise_ie(0, false);
65+
pac::GPIOHS::set_rise_ip(0, true);
66+
pac::GPIOHS::set_fall_ie(0, false);
67+
pac::GPIOHS::set_fall_ip(0, true);
68+
pac::GPIOHS::set_high_ie(0, false);
69+
pac::GPIOHS::set_high_ip(0, true);
70+
pac::GPIOHS::set_low_ie(0, false);
71+
pac::GPIOHS::set_low_ip(0, true);
72+
if edge.contains(Edge::RISING) {
73+
pac::GPIOHS::set_rise_ie(0, true);
74+
}
75+
if edge.contains(Edge::FALLING) {
76+
pac::GPIOHS::set_fall_ie(0, true);
77+
}
78+
if edge.contains(Edge::HIGH) {
79+
pac::GPIOHS::set_high_ie(0, true);
80+
}
81+
if edge.contains(Edge::LOW) {
82+
pac::GPIOHS::set_low_ie(0, true);
83+
}
84+
}
85+
}
86+
87+
impl<MODE> InputPin for Gpiohs0<Input<MODE>> {
88+
type Error = core::convert::Infallible;
89+
90+
fn is_high(&self) -> Result<bool, Self::Error> {
91+
Ok(unsafe {
92+
let p = &(*pac::GPIOHS::ptr()).input_val as *const _ as *const _;
93+
u32_bit_is_set(p, 0)
94+
})
95+
}
96+
97+
fn is_low(&self) -> Result<bool, Self::Error> {
98+
Ok(unsafe {
99+
let p = &(*pac::GPIOHS::ptr()).input_val as *const _ as *const _;
100+
u32_bit_is_clear(p, 0)
101+
})
102+
}
103+
}
104+
105+
impl<MODE> OutputPin for Gpiohs0<Output<MODE>> {
106+
type Error = core::convert::Infallible;
107+
108+
fn set_high(&mut self) -> Result<(), Self::Error> {
109+
unsafe {
110+
let p = &(*pac::GPIOHS::ptr()).output_val as *const _ as *mut _;
111+
u32_set_bit(p, true, 0);
112+
}
113+
Ok(())
114+
}
115+
116+
fn set_low(&mut self) -> Result<(), Self::Error> {
117+
unsafe {
118+
let p = &(*pac::GPIOHS::ptr()).output_val as *const _ as *mut _;
119+
u32_set_bit(p, false, 0);
120+
}
121+
Ok(())
122+
}
123+
}
124+
8125
trait GpiohsAccess {
9126
fn peripheral() -> &'static mut pac::gpiohs::RegisterBlock;
10127

@@ -78,94 +195,65 @@ trait GpiohsAccess {
78195
}
79196
}
80197

81-
// todo: {high, low, fall, rise}_{ie, ip}
82-
}
83-
84-
impl GpiohsAccess for pac::GPIOHS {
85-
fn peripheral() -> &'static mut pac::gpiohs::RegisterBlock {
86-
unsafe { &mut *(pac::GPIOHS::ptr() as *mut _) }
198+
fn set_rise_ie(index: usize, bit: bool) {
199+
unsafe {
200+
let p = &mut Self::peripheral().rise_ie as *mut _ as *mut _;
201+
u32_set_bit(p, bit, index);
202+
}
87203
}
88-
}
89-
90-
// todo: verify
91-
92-
/// Floating mode (type state)
93-
pub struct Floating;
94-
95-
/// PullUp mode (type state)
96-
pub struct PullUp;
97-
98-
/// Input mode (type state)
99-
pub struct Input<MODE>(MODE);
100-
101-
/// Output mode (type state)
102-
pub struct Output<MODE>(MODE);
103-
104-
pub trait GpiohsExt {
105-
fn split(self) -> Parts;
106-
}
107-
108-
impl GpiohsExt for pac::GPIOHS {
109-
fn split(self) -> Parts {
110-
Parts {
111-
gpiohs0: Gpiohs0 { _mode: PhantomData },
204+
205+
fn set_rise_ip(index: usize, bit: bool) {
206+
unsafe {
207+
let p = &mut Self::peripheral().rise_ip as *mut _ as *mut _;
208+
u32_set_bit(p, bit, index);
112209
}
113210
}
114-
}
115-
116-
pub struct Parts {
117-
pub gpiohs0: Gpiohs0<Input<Floating>>,
118-
}
119-
120-
pub struct Gpiohs0<MODE> {
121-
_mode: PhantomData<MODE>,
122-
}
123-
124-
impl<MODE> Gpiohs0<MODE> {
125-
pub fn into_pull_up_input(self) -> Gpiohs0<Input<PullUp>> {
126-
pac::GPIOHS::set_output_en(0, false);
127-
pac::GPIOHS::set_input_en(0, true);
128-
pac::GPIOHS::set_pullup_en(0, true);
129-
Gpiohs0 { _mode: PhantomData }
211+
212+
fn set_fall_ie(index: usize, bit: bool) {
213+
unsafe {
214+
let p = &mut Self::peripheral().fall_ie as *mut _ as *mut _;
215+
u32_set_bit(p, bit, index);
216+
}
130217
}
131-
132-
// todo: all modes
133-
}
134-
135-
impl<MODE> InputPin for Gpiohs0<Input<MODE>> {
136-
type Error = core::convert::Infallible;
137-
138-
fn is_high(&self) -> Result<bool, Self::Error> {
139-
Ok(unsafe {
140-
let p = &(*pac::GPIOHS::ptr()).input_val as *const _ as *const _;
141-
u32_bit_is_set(p, 0)
142-
})
218+
219+
fn set_fall_ip(index: usize, bit: bool) {
220+
unsafe {
221+
let p = &mut Self::peripheral().fall_ip as *mut _ as *mut _;
222+
u32_set_bit(p, bit, index);
223+
}
143224
}
144-
145-
fn is_low(&self) -> Result<bool, Self::Error> {
146-
Ok(unsafe {
147-
let p = &(*pac::GPIOHS::ptr()).input_val as *const _ as *const _;
148-
u32_bit_is_clear(p, 0)
149-
})
225+
226+
fn set_high_ie(index: usize, bit: bool) {
227+
unsafe {
228+
let p = &mut Self::peripheral().high_ie as *mut _ as *mut _;
229+
u32_set_bit(p, bit, index);
230+
}
150231
}
151-
}
152-
153-
impl<MODE> OutputPin for Gpiohs0<Output<MODE>> {
154-
type Error = core::convert::Infallible;
155-
156-
fn set_high(&mut self) -> Result<(), Self::Error> {
157-
unsafe {
158-
let p = &(*pac::GPIOHS::ptr()).output_val as *const _ as *mut _;
159-
u32_set_bit(p, true, 0);
232+
233+
fn set_high_ip(index: usize, bit: bool) {
234+
unsafe {
235+
let p = &mut Self::peripheral().high_ip as *mut _ as *mut _;
236+
u32_set_bit(p, bit, index);
160237
}
161-
Ok(())
162238
}
163-
164-
fn set_low(&mut self) -> Result<(), Self::Error> {
165-
unsafe {
166-
let p = &(*pac::GPIOHS::ptr()).output_val as *const _ as *mut _;
167-
u32_set_bit(p, false, 0);
239+
240+
fn set_low_ie(index: usize, bit: bool) {
241+
unsafe {
242+
let p = &mut Self::peripheral().low_ie as *mut _ as *mut _;
243+
u32_set_bit(p, bit, index);
168244
}
169-
Ok(())
245+
}
246+
247+
fn set_low_ip(index: usize, bit: bool) {
248+
unsafe {
249+
let p = &mut Self::peripheral().low_ip as *mut _ as *mut _;
250+
u32_set_bit(p, bit, index);
251+
}
252+
}
253+
}
254+
255+
impl GpiohsAccess for pac::GPIOHS {
256+
fn peripheral() -> &'static mut pac::gpiohs::RegisterBlock {
257+
unsafe { &mut *(pac::GPIOHS::ptr() as *mut _) }
170258
}
171259
}

0 commit comments

Comments
 (0)