1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
//! System configuration: the registers that wire peripherals to each other
//! rather than to the outside world.
//!
//! Only `EXTISS` is covered so far, through
//! [`ExtiLine::source`](crate::exti::ExtiLine::source).
use crate::pac;
use crate::rcu::Rcu;
/// Owns the SYSCFG registers.
pub struct Syscfg {
syscfg: pac::Syscfg,
}
impl Syscfg {
/// Points EXTI line `line` at the port encoded by `code`.
///
/// # Panics
///
/// If `line` is above 15 — the lines above that have no source to select.
pub(crate) fn set_extiss(&mut self, line: u8, code: u8) {
match line {
// SAFETY: `code` is an `ExtiPin::SS_CODE`, one of the port codes this
// field takes.
l @ 0..=3 => self.syscfg.extiss0().modify(|_, w| unsafe {
match l {
0 => w.exti0_ss().bits(code),
1 => w.exti1_ss().bits(code),
2 => w.exti2_ss().bits(code),
_ => w.exti3_ss().bits(code),
}
}),
// SAFETY: as above.
l @ 4..=7 => self.syscfg.extiss1().modify(|_, w| unsafe {
match l {
4 => w.exti4_ss().bits(code),
5 => w.exti5_ss().bits(code),
6 => w.exti6_ss().bits(code),
_ => w.exti7_ss().bits(code),
}
}),
// SAFETY: as above.
l @ 8..=11 => self.syscfg.extiss2().modify(|_, w| unsafe {
match l {
8 => w.exti8_ss().bits(code),
9 => w.exti9_ss().bits(code),
10 => w.exti10_ss().bits(code),
_ => w.exti11_ss().bits(code),
}
}),
// SAFETY: as above.
l @ 12..=15 => self.syscfg.extiss3().modify(|_, w| unsafe {
match l {
12 => w.exti12_ss().bits(code),
13 => w.exti13_ss().bits(code),
14 => w.exti14_ss().bits(code),
_ => w.exti15_ss().bits(code),
}
}),
_ => unreachable!(),
}
}
}
/// Takes the raw peripheral into [`Syscfg`].
pub trait SyscfgExt {
/// Switches the SYSCFG clock on and hands back the owning type.
///
/// The clock bit is shared with the comparator, so CMP is clocked too; see
/// [`Rcu::enable_cfgcmp`].
fn constrain(self, rcu: &mut Rcu) -> Syscfg;
}
impl SyscfgExt for pac::Syscfg {
fn constrain(self, rcu: &mut Rcu) -> Syscfg {
rcu.enable_cfgcmp();
Syscfg { syscfg: self }
}
}