Skip to content

Commit c54d5fa

Browse files
committed
WIP - 32bit mode
1 parent d219616 commit c54d5fa

File tree

4 files changed

+72
-54
lines changed

4 files changed

+72
-54
lines changed

src/bus.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ use crate::registers::UsbRegisters;
1212
use crate::UsbPeripheral;
1313

1414
/// USB peripheral driver for STM32 microcontrollers.
15-
pub struct UsbBus<USB> {
15+
pub struct UsbBus<USB: UsbPeripheral> {
1616
peripheral: USB,
1717
regs: Mutex<UsbRegisters<USB>>,
1818
endpoints: [Endpoint<USB>; NUM_ENDPOINTS],

src/endpoint.rs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ pub const NUM_ENDPOINTS: usize = 8;
1616

1717
/// Arbitrates access to the endpoint-specific registers and packet buffer memory.
1818
#[derive(Default)]
19-
pub struct Endpoint<USB> {
19+
pub struct Endpoint<USB: UsbPeripheral> {
2020
out_buf: Option<Mutex<EndpointBuffer<USB>>>,
2121
in_buf: Option<Mutex<EndpointBuffer<USB>>>,
2222
ep_type: Option<EndpointType>,
@@ -72,8 +72,8 @@ impl<USB: UsbPeripheral> Endpoint<USB> {
7272
self.out_buf = Some(Mutex::new(buffer));
7373

7474
let descr = self.descr();
75-
descr.addr_rx().set(offset);
76-
descr.count_rx().set(size_bits);
75+
descr.addr_rx().set(offset.into());
76+
descr.count_rx().set(size_bits.into());
7777
}
7878

7979
pub fn is_in_buf_set(&self) -> bool {
@@ -85,8 +85,8 @@ impl<USB: UsbPeripheral> Endpoint<USB> {
8585
self.in_buf = Some(Mutex::new(buffer));
8686

8787
let descr = self.descr();
88-
descr.addr_tx().set(offset);
89-
descr.count_tx().set(0);
88+
descr.addr_tx().set(offset.into());
89+
descr.count_tx().set(0.into());
9090
}
9191

9292
fn descr(&self) -> BufferDescriptor<USB> {
@@ -151,7 +151,7 @@ impl<USB: UsbPeripheral> Endpoint<USB> {
151151
};
152152

153153
in_buf.write(buf);
154-
self.descr().count_tx().set(buf.len() as u16);
154+
self.descr().count_tx().set((buf.len() as u16).into());
155155

156156
self.set_stat_tx(cs, EndpointStatus::Valid);
157157

@@ -173,7 +173,7 @@ impl<USB: UsbPeripheral> Endpoint<USB> {
173173

174174
self.clear_ctr_rx(cs);
175175

176-
let count = (self.descr().count_rx().get() & 0x3ff) as usize;
176+
let count = (self.descr().count_rx().get().into() & 0x3ff) as usize;
177177
if count > buf.len() {
178178
return Err(UsbError::BufferOverflow);
179179
}

src/endpoint_memory.rs

Lines changed: 24 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,18 @@
11
use crate::endpoint::NUM_ENDPOINTS;
2-
use crate::UsbPeripheral;
2+
use crate::{UsbPeripheral, Word};
33
use core::marker::PhantomData;
44
use core::slice;
55
use usb_device::{Result, UsbError};
66
use vcell::VolatileCell;
77

8-
pub struct EndpointBuffer<USB> {
9-
mem: &'static mut [VolatileCell<u16>],
8+
pub struct EndpointBuffer<USB: UsbPeripheral> {
9+
mem: &'static mut [VolatileCell<USB::Word>],
1010
marker: PhantomData<USB>,
1111
}
1212

1313
impl<USB: UsbPeripheral> EndpointBuffer<USB> {
1414
pub fn new(offset_bytes: usize, size_bytes: usize) -> Self {
15-
let ep_mem_ptr = USB::EP_MEMORY as *mut VolatileCell<u16>;
15+
let ep_mem_ptr = USB::EP_MEMORY as *mut VolatileCell<_>;
1616

1717
let offset_words = offset_bytes >> 1;
1818
let count_words = size_bytes >> 1;
@@ -36,7 +36,7 @@ impl<USB: UsbPeripheral> EndpointBuffer<USB> {
3636
}
3737

3838
#[inline(always)]
39-
fn read_word(&self, index: usize) -> u16 {
39+
fn read_word(&self, index: usize) -> USB::Word {
4040
if USB::EP_MEMORY_ACCESS_2X16 {
4141
self.mem[index].get()
4242
} else {
@@ -45,46 +45,32 @@ impl<USB: UsbPeripheral> EndpointBuffer<USB> {
4545
}
4646

4747
#[inline(always)]
48-
fn write_word(&self, index: usize, value: u16) {
48+
fn write_word(&self, index: usize, value: USB::Word) {
4949
if USB::EP_MEMORY_ACCESS_2X16 {
5050
self.mem[index].set(value);
5151
} else {
5252
self.mem[index * 2].set(value);
5353
}
5454
}
5555

56-
pub fn read(&self, mut buf: &mut [u8]) {
56+
pub fn read(&self, buf: &mut [u8]) {
5757
let mut index = 0;
58+
let mut writer = buf.into_iter().peekable();
5859

59-
while buf.len() >= 2 {
60-
let word = self.read_word(index);
61-
62-
buf[0] = (word & 0xff) as u8;
63-
buf[1] = (word >> 8) as u8;
64-
60+
while writer.peek().is_some() {
61+
self.read_word(index).write_to_iter_le(&mut writer);
6562
index += 1;
66-
67-
buf = &mut buf[2..];
68-
}
69-
70-
if buf.len() > 0 {
71-
buf[0] = (self.read_word(index) & 0xff) as u8;
7263
}
7364
}
7465

75-
pub fn write(&self, mut buf: &[u8]) {
66+
pub fn write(&self, buf: &[u8]) {
7667
let mut index = 0;
68+
let mut reader = buf.into_iter().peekable();
7769

78-
while buf.len() >= 2 {
79-
let value: u16 = buf[0] as u16 | ((buf[1] as u16) << 8);
70+
while reader.peek().is_some() {
71+
let value = Word::from_iter_le(&mut reader);
8072
self.write_word(index, value);
8173
index += 1;
82-
83-
buf = &buf[2..];
84-
}
85-
86-
if buf.len() > 0 {
87-
self.write_word(index, buf[0] as u16);
8874
}
8975
}
9076

@@ -106,36 +92,28 @@ impl<USB: UsbPeripheral> EndpointBuffer<USB> {
10692
}
10793

10894
#[repr(C)]
109-
pub struct BufferDescriptor<USB> {
110-
ptr: *const VolatileCell<u16>,
95+
pub struct BufferDescriptor<USB: UsbPeripheral> {
96+
ptr: *const VolatileCell<USB::Word>,
11197
marker: PhantomData<USB>,
11298
}
11399

114100
impl<USB: UsbPeripheral> BufferDescriptor<USB> {
115101
#[inline(always)]
116-
fn field(&self, index: usize) -> &'static VolatileCell<u16> {
102+
fn field(&self, index: usize) -> &'static VolatileCell<USB::Word> {
117103
let mul = if USB::EP_MEMORY_ACCESS_2X16 { 1 } else { 2 };
118104
unsafe { &*(self.ptr.add(index * mul)) }
119105
}
120106

121107
#[inline(always)]
122-
pub fn addr_tx(&self) -> &'static VolatileCell<u16> {
123-
self.field(0)
124-
}
125-
126-
#[inline(always)]
127-
pub fn count_tx(&self) -> &'static VolatileCell<u16> {
128-
self.field(1)
129-
}
130-
131-
#[inline(always)]
132-
pub fn addr_rx(&self) -> &'static VolatileCell<u16> {
133-
self.field(2)
108+
pub fn set_tx(&self, address: u16, count: u16) {
109+
self.field(0) // addr
110+
self.field(1) // count (msb in 32bit)
134111
}
135112

136113
#[inline(always)]
137-
pub fn count_rx(&self) -> &'static VolatileCell<u16> {
138-
self.field(3)
114+
pub fn get_rx(&self) -> (u16, u16) {
115+
self.field(2) // addr
116+
self.field(3) // count(msb in 32bit)
139117
}
140118
}
141119

@@ -170,7 +148,7 @@ impl<USB: UsbPeripheral> EndpointMemoryAllocator<USB> {
170148
let mul = if USB::EP_MEMORY_ACCESS_2X16 { 1 } else { 2 };
171149

172150
unsafe {
173-
let ptr = (USB::EP_MEMORY as *const VolatileCell<u16>).add((index as usize) * 4 * mul);
151+
let ptr = (USB::EP_MEMORY as *const VolatileCell<USB::Word>).add((index as usize) * 4 * mul);
174152
BufferDescriptor {
175153
ptr,
176154
marker: Default::default(),

src/lib.rs

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,8 @@ pub unsafe trait UsbPeripheral: Send + Sync {
3535
/// Set to `true` if "2x16 bits/word" access scheme is used, otherwise set to `false`.
3636
const EP_MEMORY_ACCESS_2X16: bool;
3737

38+
type Word: Word;
39+
3840
/// Enables USB device on its peripheral bus
3941
fn enable();
4042

@@ -44,3 +46,41 @@ pub unsafe trait UsbPeripheral: Send + Sync {
4446
/// peripheral initialization.
4547
fn startup_delay();
4648
}
49+
50+
pub trait Word: From<u16> + Into<u32> + Copy + Send + 'static
51+
{
52+
fn from_iter_le<'a>(it: &mut impl Iterator<Item = &'a u8>) -> Self;
53+
fn write_to_iter_le<'a>(self, it: &mut impl Iterator<Item = &'a mut u8>);
54+
}
55+
56+
impl Word for u16 {
57+
fn from_iter_le<'a>(it: &mut impl Iterator<Item = &'a u8>) -> Self {
58+
Self::from_le_bytes([
59+
*it.next().unwrap_or(&0),
60+
*it.next().unwrap_or(&0),
61+
])
62+
}
63+
64+
fn write_to_iter_le<'a>(self, it: &mut impl Iterator<Item = &'a mut u8>) {
65+
for (w, r) in it.zip(self.to_le_bytes()) {
66+
*w = r;
67+
}
68+
}
69+
}
70+
71+
impl Word for u32 {
72+
fn from_iter_le<'a>(it: &mut impl Iterator<Item = &'a u8>) -> Self {
73+
Self::from_le_bytes([
74+
*it.next().unwrap_or(&0),
75+
*it.next().unwrap_or(&0),
76+
*it.next().unwrap_or(&0),
77+
*it.next().unwrap_or(&0),
78+
])
79+
}
80+
81+
fn write_to_iter_le<'a>(self, it: &mut impl Iterator<Item = &'a mut u8>) {
82+
for (w, r) in it.zip(self.to_le_bytes()) {
83+
*w = r;
84+
}
85+
}
86+
}

0 commit comments

Comments
 (0)