added TL Mailbox initialization for STM32WB

This commit is contained in:
goueslati 2023-05-02 12:16:48 +01:00
parent 6096f0cf4b
commit bab30a7e87
11 changed files with 2063 additions and 1334 deletions

File diff suppressed because it is too large Load diff

View file

@ -57,6 +57,8 @@ pub mod rtc;
pub mod sdmmc;
#[cfg(spi)]
pub mod spi;
#[cfg(stm32wb)]
pub mod tl_mbox;
#[cfg(usart)]
pub mod usart;
#[cfg(all(usb, feature = "time"))]

View file

@ -0,0 +1,26 @@
use core::mem::MaybeUninit;
use super::unsafe_linked_list::LST_init_head;
use super::{channels, BleTable, BLE_CMD_BUFFER, CS_BUFFER, EVT_QUEUE, HCI_ACL_DATA_BUFFER, TL_BLE_TABLE};
use crate::ipcc::Ipcc;
pub struct Ble;
impl Ble {
pub fn new(ipcc: &mut Ipcc) -> Self {
unsafe {
LST_init_head(EVT_QUEUE.as_mut_ptr());
TL_BLE_TABLE = MaybeUninit::new(BleTable {
pcmd_buffer: BLE_CMD_BUFFER.as_mut_ptr().cast(),
pcs_buffer: CS_BUFFER.as_mut_ptr().cast(),
pevt_queue: EVT_QUEUE.as_ptr().cast(),
phci_acl_data_buffer: HCI_ACL_DATA_BUFFER.as_mut_ptr().cast(),
});
}
ipcc.c1_set_rx_channel(channels::cpu2::IPCC_BLE_EVENT_CHANNEL, true);
Ble
}
}

View file

@ -0,0 +1,104 @@
//! CPU1 CPU2
//! | (SYSTEM) |
//! |----HW_IPCC_SYSTEM_CMD_RSP_CHANNEL-------------->|
//! | |
//! |<---HW_IPCC_SYSTEM_EVENT_CHANNEL-----------------|
//! | |
//! | (ZIGBEE) |
//! |----HW_IPCC_ZIGBEE_CMD_APPLI_CHANNEL------------>|
//! | |
//! |----HW_IPCC_ZIGBEE_CMD_CLI_CHANNEL-------------->|
//! | |
//! |<---HW_IPCC_ZIGBEE_APPLI_NOTIF_ACK_CHANNEL-------|
//! | |
//! |<---HW_IPCC_ZIGBEE_CLI_NOTIF_ACK_CHANNEL---------|
//! | |
//! | (THREAD) |
//! |----HW_IPCC_THREAD_OT_CMD_RSP_CHANNEL----------->|
//! | |
//! |----HW_IPCC_THREAD_CLI_CMD_CHANNEL-------------->|
//! | |
//! |<---HW_IPCC_THREAD_NOTIFICATION_ACK_CHANNEL------|
//! | |
//! |<---HW_IPCC_THREAD_CLI_NOTIFICATION_ACK_CHANNEL--|
//! | |
//! | (BLE) |
//! |----HW_IPCC_BLE_CMD_CHANNEL--------------------->|
//! | |
//! |----HW_IPCC_HCI_ACL_DATA_CHANNEL---------------->|
//! | |
//! |<---HW_IPCC_BLE_EVENT_CHANNEL--------------------|
//! | |
//! | (BLE LLD) |
//! |----HW_IPCC_BLE_LLD_CMD_CHANNEL----------------->|
//! | |
//! |<---HW_IPCC_BLE_LLD_RSP_CHANNEL------------------|
//! | |
//! |<---HW_IPCC_BLE_LLD_M0_CMD_CHANNEL---------------|
//! | |
//! | (MAC) |
//! |----HW_IPCC_MAC_802_15_4_CMD_RSP_CHANNEL-------->|
//! | |
//! |<---HW_IPCC_MAC_802_15_4_NOTIFICATION_ACK_CHANNEL|
//! | |
//! | (BUFFER) |
//! |----HW_IPCC_MM_RELEASE_BUFFER_CHANNE------------>|
//! | |
//! | (TRACE) |
//! |<----HW_IPCC_TRACES_CHANNEL----------------------|
//! | |
//!
pub mod cpu1 {
use crate::ipcc::IpccChannel;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_BLE_CMD_CHANNEL: IpccChannel = IpccChannel::Channel1;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_SYSTEM_CMD_RSP_CHANNEL: IpccChannel = IpccChannel::Channel2;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_THREAD_OT_CMD_RSP_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_ZIGBEE_CMD_APPLI_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_MAC_802_15_4_CMD_RSP_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_MM_RELEASE_BUFFER_CHANNEL: IpccChannel = IpccChannel::Channel4;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_THREAD_CLI_CMD_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_LLDTESTS_CLI_CMD_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_BLE_LLD_CMD_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_HCI_ACL_DATA_CHANNEL: IpccChannel = IpccChannel::Channel6;
}
pub mod cpu2 {
use crate::ipcc::IpccChannel;
pub const IPCC_BLE_EVENT_CHANNEL: IpccChannel = IpccChannel::Channel1;
pub const IPCC_SYSTEM_EVENT_CHANNEL: IpccChannel = IpccChannel::Channel2;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_THREAD_NOTIFICATION_ACK_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_ZIGBEE_APPLI_NOTIF_ACK_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_MAC_802_15_4_NOTIFICATION_ACK_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_LDDTESTS_M0_CMD_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_BLE_LLDÇM0_CMD_CHANNEL: IpccChannel = IpccChannel::Channel3;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_TRACES_CHANNEL: IpccChannel = IpccChannel::Channel4;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_THREAD_CLI_NOTIFICATION_ACK_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_LLDTESTS_CLI_RSP_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_BLE_LLD_CLI_RSP_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_BLE_LLD_RSP_CHANNEL: IpccChannel = IpccChannel::Channel5;
#[allow(dead_code)] // Not used currently but reserved
pub const IPCC_ZIGBEE_M0_REQUEST_CHANNEL: IpccChannel = IpccChannel::Channel5;
}

View file

@ -0,0 +1,49 @@
use super::PacketHeader;
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct Cmd {
pub cmd_code: u16,
pub payload_len: u8,
pub payload: [u8; 255],
}
impl Default for Cmd {
fn default() -> Self {
Self {
cmd_code: 0,
payload_len: 0,
payload: [0u8; 255],
}
}
}
#[repr(C, packed)]
#[derive(Copy, Clone, Default)]
pub struct CmdSerial {
pub ty: u8,
pub cmd: Cmd,
}
#[repr(C, packed)]
#[derive(Copy, Clone, Default)]
pub struct CmdPacket {
pub header: PacketHeader,
pub cmd_serial: CmdSerial,
}
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct AclDataSerial {
pub ty: u8,
pub handle: u16,
pub length: u16,
pub acl_data: [u8; 1],
}
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct AclDataPacket {
pub header: PacketHeader,
pub acl_data_serial: AclDataSerial,
}

View file

@ -0,0 +1,8 @@
/// the payload of [`Evt`] for a command status event
#[derive(Copy, Clone)]
#[repr(C, packed)]
pub struct CsEvt {
pub status: u8,
pub num_cmd: u8,
pub cmd_code: u16,
}

View file

@ -0,0 +1,30 @@
use core::mem::MaybeUninit;
use super::unsafe_linked_list::LST_init_head;
use super::{
MemManagerTable, BLE_SPARE_EVT_BUF, EVT_POOL, FREE_BUFF_QUEUE, LOCAL_FREE_BUF_QUEUE, POOL_SIZE, SYS_SPARE_EVT_BUF,
TL_MEM_MANAGER_TABLE,
};
pub struct MemoryManager;
impl MemoryManager {
pub fn new() -> Self {
unsafe {
LST_init_head(FREE_BUFF_QUEUE.as_mut_ptr());
LST_init_head(LOCAL_FREE_BUF_QUEUE.as_mut_ptr());
TL_MEM_MANAGER_TABLE = MaybeUninit::new(MemManagerTable {
spare_ble_buffer: BLE_SPARE_EVT_BUF.as_ptr().cast(),
spare_sys_buffer: SYS_SPARE_EVT_BUF.as_ptr().cast(),
ble_pool: EVT_POOL.as_ptr().cast(),
ble_pool_size: POOL_SIZE as u32,
pevt_free_buffer_queue: FREE_BUFF_QUEUE.as_mut_ptr(),
traces_evt_pool: core::ptr::null(),
traces_pool_size: 0,
});
}
MemoryManager
}
}

View file

@ -0,0 +1,318 @@
use core::mem::MaybeUninit;
use bit_field::BitField;
use self::ble::Ble;
use self::cmd::{AclDataPacket, CmdPacket};
use self::evt::CsEvt;
use self::mm::MemoryManager;
use self::sys::Sys;
use self::unsafe_linked_list::LinkedListNode;
use crate::ipcc::Ipcc;
mod ble;
mod channels;
mod cmd;
mod evt;
mod mm;
mod sys;
mod unsafe_linked_list;
pub type PacketHeader = LinkedListNode;
const TL_PACKET_HEADER_SIZE: usize = core::mem::size_of::<PacketHeader>();
const TL_EVT_HEADER_SIZE: usize = 3;
const TL_CS_EVT_SIZE: usize = core::mem::size_of::<CsEvt>();
const CFG_TL_BLE_EVT_QUEUE_LENGTH: usize = 5;
const CFG_TL_BLE_MOST_EVENT_PAYLOAD_SIZE: usize = 255;
const TL_BLE_EVENT_FRAME_SIZE: usize = TL_EVT_HEADER_SIZE + CFG_TL_BLE_MOST_EVENT_PAYLOAD_SIZE;
const POOL_SIZE: usize = CFG_TL_BLE_EVT_QUEUE_LENGTH * 4 * divc(TL_PACKET_HEADER_SIZE + TL_BLE_EVENT_FRAME_SIZE, 4);
const fn divc(x: usize, y: usize) -> usize {
(x + y - 1) / y
}
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct SafeBootInfoTable {
version: u32,
}
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct RssInfoTable {
version: u32,
memory_size: u32,
rss_info: u32,
}
/// # Version
/// - 0 -> 3 = Build - 0: Untracked - 15:Released - x: Tracked version
/// - 4 -> 7 = branch - 0: Mass Market - x: ...
/// - 8 -> 15 = Subversion
/// - 16 -> 23 = Version minor
/// - 24 -> 31 = Version major
/// # Memory Size
/// - 0 -> 7 = Flash ( Number of 4k sector)
/// - 8 -> 15 = Reserved ( Shall be set to 0 - may be used as flash extension )
/// - 16 -> 23 = SRAM2b ( Number of 1k sector)
/// - 24 -> 31 = SRAM2a ( Number of 1k sector)
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct WirelessFwInfoTable {
version: u32,
memory_size: u32,
thread_info: u32,
ble_info: u32,
}
impl WirelessFwInfoTable {
pub fn version_major(&self) -> u8 {
let version = self.version;
(version.get_bits(24..31) & 0xff) as u8
}
pub fn version_minor(&self) -> u8 {
let version = self.version;
(version.get_bits(16..23) & 0xff) as u8
}
pub fn subversion(&self) -> u8 {
let version = self.version;
(version.get_bits(8..15) & 0xff) as u8
}
/// size of FLASH, expressed in number of 4K sectors
pub fn flash_size(&self) -> u8 {
let memory_size = self.memory_size;
(memory_size.get_bits(0..7) & 0xff) as u8
}
/// size for SRAM2a, expressed in number of 1K sectors
pub fn sram2a_size(&self) -> u8 {
let memory_size = self.memory_size;
(memory_size.get_bits(24..31) & 0xff) as u8
}
/// size of SRAM2b, expressed in number of 1K sectors
pub fn sram2b_size(&self) -> u8 {
let memory_size = self.memory_size;
(memory_size.get_bits(16..23) & 0xff) as u8
}
}
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct DeviceInfoTable {
pub safe_boot_info_table: SafeBootInfoTable,
pub rss_info_table: RssInfoTable,
pub wireless_fw_info_table: WirelessFwInfoTable,
}
#[repr(C, packed)]
struct BleTable {
pcmd_buffer: *const CmdPacket,
pcs_buffer: *const u8,
pevt_queue: *const u8,
phci_acl_data_buffer: *mut AclDataPacket,
}
#[repr(C, packed)]
struct ThreadTable {
no_stack_buffer: *const u8,
cli_cmd_rsp_buffer: *const u8,
ot_cmd_rsp_buffer: *const u8,
}
#[repr(C, packed)]
struct SysTable {
pcmd_buffer: *mut CmdPacket,
sys_queue: *const LinkedListNode,
}
#[allow(dead_code)] // Not used currently but reserved
#[repr(C, packed)]
struct LldTestTable {
cli_cmd_rsp_buffer: *const u8,
m0_cmd_buffer: *const u8,
}
#[allow(dead_code)] // Not used currently but reserved
#[repr(C, packed)]
struct BleLldTable {
cmd_rsp_buffer: *const u8,
m0_cmd_buffer: *const u8,
}
#[allow(dead_code)] // Not used currently but reserved
#[repr(C, packed)]
struct ZigbeeTable {
notif_m0_to_m4_buffer: *const u8,
appli_cmd_m4_to_m0_buffer: *const u8,
request_m0_to_m4_buffer: *const u8,
}
#[repr(C, packed)]
struct MemManagerTable {
spare_ble_buffer: *const u8,
spare_sys_buffer: *const u8,
ble_pool: *const u8,
ble_pool_size: u32,
pevt_free_buffer_queue: *mut LinkedListNode,
traces_evt_pool: *const u8,
traces_pool_size: u32,
}
#[repr(C, packed)]
struct TracesTable {
traces_queue: *const u8,
}
#[repr(C, packed)]
struct Mac802_15_4Table {
pcmd_rsp_buffer: *const u8,
pnotack_buffer: *const u8,
evt_queue: *const u8,
}
/// reference table. Contains pointers to all other tables
#[repr(C, packed)]
#[derive(Copy, Clone)]
pub struct RefTable {
pub device_info_table: *const DeviceInfoTable,
ble_table: *const BleTable,
thread_table: *const ThreadTable,
sys_table: *const SysTable,
mem_manager_table: *const MemManagerTable,
traces_table: *const TracesTable,
mac_802_15_4_table: *const Mac802_15_4Table,
}
#[link_section = "TL_REF_TABLE"]
pub static mut TL_REF_TABLE: MaybeUninit<RefTable> = MaybeUninit::uninit();
#[link_section = "TL_DEVICE_INFO_TABLE"]
static mut TL_DEVICE_INFO_TABLE: MaybeUninit<DeviceInfoTable> = MaybeUninit::uninit();
#[link_section = "TL_BLE_TABLE"]
static mut TL_BLE_TABLE: MaybeUninit<BleTable> = MaybeUninit::uninit();
#[link_section = "TL_THREAD_TABLE"]
static mut TL_THREAD_TABLE: MaybeUninit<ThreadTable> = MaybeUninit::uninit();
#[link_section = "TL_SYS_TABLE"]
static mut TL_SYS_TABLE: MaybeUninit<SysTable> = MaybeUninit::uninit();
#[link_section = "TL_MEM_MANAGER_TABLE"]
static mut TL_MEM_MANAGER_TABLE: MaybeUninit<MemManagerTable> = MaybeUninit::uninit();
#[link_section = "TL_TRACES_TABLE"]
static mut TL_TRACES_TABLE: MaybeUninit<TracesTable> = MaybeUninit::uninit();
#[link_section = "TL_MAC_802_15_4_TABLE"]
static mut TL_MAC_802_15_4_TABLE: MaybeUninit<Mac802_15_4Table> = MaybeUninit::uninit();
#[allow(dead_code)] // Not used currently but reserved
#[link_section = "FREE_BUF_QUEUE"]
static mut FREE_BUFF_QUEUE: MaybeUninit<LinkedListNode> = MaybeUninit::uninit();
// not in shared RAM
static mut LOCAL_FREE_BUF_QUEUE: MaybeUninit<LinkedListNode> = MaybeUninit::uninit();
#[allow(dead_code)] // Not used currently but reserved
#[link_section = "TRACES_EVT_QUEUE"]
static mut TRACES_EVT_QUEUE: MaybeUninit<LinkedListNode> = MaybeUninit::uninit();
#[link_section = "CS_BUFFER"]
static mut CS_BUFFER: MaybeUninit<[u8; TL_PACKET_HEADER_SIZE + TL_EVT_HEADER_SIZE + TL_CS_EVT_SIZE]> =
MaybeUninit::uninit();
#[link_section = "EVT_QUEUE"]
static mut EVT_QUEUE: MaybeUninit<LinkedListNode> = MaybeUninit::uninit();
#[link_section = "SYSTEM_EVT_QUEUE"]
static mut SYSTEM_EVT_QUEUE: MaybeUninit<LinkedListNode> = MaybeUninit::uninit();
#[link_section = "SYS_CMD_BUF"]
static mut SYS_CMD_BUF: MaybeUninit<CmdPacket> = MaybeUninit::uninit();
#[link_section = "EVT_POOL"]
static mut EVT_POOL: MaybeUninit<[u8; POOL_SIZE]> = MaybeUninit::uninit();
#[link_section = "SYS_SPARE_EVT_BUF"]
static mut SYS_SPARE_EVT_BUF: MaybeUninit<[u8; TL_PACKET_HEADER_SIZE + TL_EVT_HEADER_SIZE + 255]> =
MaybeUninit::uninit();
#[link_section = "BLE_SPARE_EVT_BUF"]
static mut BLE_SPARE_EVT_BUF: MaybeUninit<[u8; TL_PACKET_HEADER_SIZE + TL_EVT_HEADER_SIZE + 255]> =
MaybeUninit::uninit();
#[link_section = "BLE_CMD_BUFFER"]
static mut BLE_CMD_BUFFER: MaybeUninit<CmdPacket> = MaybeUninit::uninit();
#[link_section = "HCI_ACL_DATA_BUFFER"]
// "magic" numbers from ST ---v---v
static mut HCI_ACL_DATA_BUFFER: MaybeUninit<[u8; TL_PACKET_HEADER_SIZE + 5 + 251]> = MaybeUninit::uninit();
pub struct TlMbox {
_sys: Sys,
_ble: Ble,
_mm: MemoryManager,
}
impl TlMbox {
/// initializes low-level transport between CPU1 and BLE stack on CPU2
pub fn init(ipcc: &mut Ipcc) -> TlMbox {
unsafe {
TL_REF_TABLE = MaybeUninit::new(RefTable {
device_info_table: TL_DEVICE_INFO_TABLE.as_ptr(),
ble_table: TL_BLE_TABLE.as_ptr(),
thread_table: TL_THREAD_TABLE.as_ptr(),
sys_table: TL_SYS_TABLE.as_ptr(),
mem_manager_table: TL_MEM_MANAGER_TABLE.as_ptr(),
traces_table: TL_TRACES_TABLE.as_ptr(),
mac_802_15_4_table: TL_MAC_802_15_4_TABLE.as_ptr(),
});
TL_SYS_TABLE = MaybeUninit::zeroed();
TL_DEVICE_INFO_TABLE = MaybeUninit::zeroed();
TL_BLE_TABLE = MaybeUninit::zeroed();
TL_THREAD_TABLE = MaybeUninit::zeroed();
TL_MEM_MANAGER_TABLE = MaybeUninit::zeroed();
TL_TRACES_TABLE = MaybeUninit::zeroed();
TL_MAC_802_15_4_TABLE = MaybeUninit::zeroed();
EVT_POOL = MaybeUninit::zeroed();
SYS_SPARE_EVT_BUF = MaybeUninit::zeroed();
BLE_SPARE_EVT_BUF = MaybeUninit::zeroed();
CS_BUFFER = MaybeUninit::zeroed();
BLE_CMD_BUFFER = MaybeUninit::zeroed();
HCI_ACL_DATA_BUFFER = MaybeUninit::zeroed();
}
ipcc.init();
let _sys = Sys::new(ipcc);
let _ble = Ble::new(ipcc);
let _mm = MemoryManager::new();
TlMbox { _sys, _ble, _mm }
}
pub fn wireless_fw_info(&self) -> Option<WirelessFwInfoTable> {
let info = unsafe { &(*(*TL_REF_TABLE.as_ptr()).device_info_table).wireless_fw_info_table };
// zero version indicates that CPU2 wasn't active and didn't fill the information table
if info.version != 0 {
Some(*info)
} else {
None
}
}
}

View file

@ -0,0 +1,24 @@
use core::mem::MaybeUninit;
use super::unsafe_linked_list::LST_init_head;
use super::{channels, SysTable, SYSTEM_EVT_QUEUE, SYS_CMD_BUF, TL_SYS_TABLE};
use crate::ipcc::Ipcc;
pub struct Sys;
impl Sys {
pub fn new(ipcc: &mut Ipcc) -> Self {
unsafe {
LST_init_head(SYSTEM_EVT_QUEUE.as_mut_ptr());
TL_SYS_TABLE = MaybeUninit::new(SysTable {
pcmd_buffer: SYS_CMD_BUF.as_mut_ptr(),
sys_queue: SYSTEM_EVT_QUEUE.as_ptr(),
});
}
ipcc.c1_set_rx_channel(channels::cpu2::IPCC_SYSTEM_EVENT_CHANNEL, true);
Sys
}
}

View file

@ -0,0 +1,123 @@
//! Unsafe linked list.
//! Translated from ST's C by `c2rust` tool.
#![allow(
dead_code,
mutable_transmutes,
non_camel_case_types,
non_snake_case,
non_upper_case_globals,
unused_assignments,
unused_mut
)]
use cortex_m::interrupt;
#[derive(Copy, Clone)]
#[repr(C, packed(4))]
pub struct LinkedListNode {
pub next: *mut LinkedListNode,
pub prev: *mut LinkedListNode,
}
impl Default for LinkedListNode {
fn default() -> Self {
LinkedListNode {
next: core::ptr::null_mut(),
prev: core::ptr::null_mut(),
}
}
}
pub unsafe fn LST_init_head(mut listHead: *mut LinkedListNode) {
(*listHead).next = listHead;
(*listHead).prev = listHead;
}
pub unsafe fn LST_is_empty(mut listHead: *mut LinkedListNode) -> bool {
interrupt::free(|_| ((*listHead).next) == listHead)
}
pub unsafe fn LST_insert_head(mut listHead: *mut LinkedListNode, mut node: *mut LinkedListNode) {
interrupt::free(|_| {
(*node).next = (*listHead).next;
(*node).prev = listHead;
(*listHead).next = node;
(*(*node).next).prev = node;
});
}
pub unsafe fn LST_insert_tail(mut listHead: *mut LinkedListNode, mut node: *mut LinkedListNode) {
interrupt::free(|_| {
(*node).next = listHead;
(*node).prev = (*listHead).prev;
(*listHead).prev = node;
(*(*node).prev).next = node;
});
}
pub unsafe fn LST_remove_node(mut node: *mut LinkedListNode) {
interrupt::free(|_| {
(*(*node).prev).next = (*node).next;
(*(*node).next).prev = (*node).prev;
});
}
pub unsafe fn LST_remove_head(mut listHead: *mut LinkedListNode, mut node: *mut *mut LinkedListNode) {
interrupt::free(|_| {
*node = (*listHead).next;
LST_remove_node((*listHead).next);
});
}
pub unsafe fn LST_remove_tail(mut listHead: *mut LinkedListNode, mut node: *mut *mut LinkedListNode) {
interrupt::free(|_| {
*node = (*listHead).prev;
LST_remove_node((*listHead).prev);
});
}
pub unsafe fn LST_insert_node_after(mut node: *mut LinkedListNode, mut ref_node: *mut LinkedListNode) {
interrupt::free(|_| {
(*node).next = (*ref_node).next;
(*node).prev = ref_node;
(*ref_node).next = node;
(*(*node).next).prev = node;
});
}
pub unsafe fn LST_insert_node_before(mut node: *mut LinkedListNode, mut ref_node: *mut LinkedListNode) {
interrupt::free(|_| {
(*node).next = ref_node;
(*node).prev = (*ref_node).prev;
(*ref_node).prev = node;
(*(*node).prev).next = node;
});
}
pub unsafe fn LST_get_size(mut listHead: *mut LinkedListNode) -> usize {
interrupt::free(|_| {
let mut size = 0;
let mut temp: *mut LinkedListNode = core::ptr::null_mut::<LinkedListNode>();
temp = (*listHead).next;
while temp != listHead {
size += 1;
temp = (*temp).next
}
size
})
}
pub unsafe fn LST_get_next_node(mut ref_node: *mut LinkedListNode, mut node: *mut *mut LinkedListNode) {
interrupt::free(|_| {
*node = (*ref_node).next;
});
}
pub unsafe fn LST_get_prev_node(mut ref_node: *mut LinkedListNode, mut node: *mut *mut LinkedListNode) {
interrupt::free(|_| {
*node = (*ref_node).prev;
});
}

View file

@ -0,0 +1,44 @@
#![no_std]
#![no_main]
#![feature(type_alias_impl_trait)]
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::ipcc::{Config, Ipcc};
use embassy_stm32::tl_mbox::TlMbox;
use {defmt_rtt as _, panic_probe as _};
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
info!("Hello World!");
let config = Config::default();
let mut ipcc = Ipcc::new(p.IPCC, config);
let mbox = TlMbox::init(&mut ipcc);
loop {
let wireless_fw_info = mbox.wireless_fw_info();
match wireless_fw_info {
None => error!("not yet initialized"),
Some(fw_info) => {
let version_major = fw_info.version_major();
let version_minor = fw_info.version_minor();
let subversion = fw_info.subversion();
let sram2a_size = fw_info.sram2a_size();
let sram2b_size = fw_info.sram2b_size();
info!(
"version {}.{}.{} - SRAM2a {} - SRAM2b {}",
version_major, version_minor, subversion, sram2a_size, sram2b_size
);
break;
}
}
}
loop {}
}