Merge pull request #4194 from i509VCB/update-metapac2

mspm0: generate features per chip + package
This commit is contained in:
Dario Nieuwenhuis
2025-05-18 21:20:11 +02:00
committed by GitHub
18 changed files with 326 additions and 43 deletions

View File

@@ -46,14 +46,14 @@ cortex-m = "0.7.6"
critical-section = "1.2.0"
# mspm0-metapac = { version = "" }
mspm0-metapac = { git = "https://github.com/mspm0-rs/mspm0-data-generated/", tag = "mspm0-data-119240dd23ef5748d2a7bef219ca298d37ba604a" }
mspm0-metapac = { git = "https://github.com/mspm0-rs/mspm0-data-generated/", tag = "mspm0-data-66a55c7bf38a2201ff48c299843e741f2d537f0b" }
[build-dependencies]
proc-macro2 = "1.0.94"
quote = "1.0.40"
# mspm0-metapac = { version = "", default-features = false, features = ["metadata"] }
mspm0-metapac = { git = "https://github.com/mspm0-rs/mspm0-data-generated/", tag = "mspm0-data-119240dd23ef5748d2a7bef219ca298d37ba604a", default-features = false, features = ["metadata"] }
mspm0-metapac = { git = "https://github.com/mspm0-rs/mspm0-data-generated/", tag = "mspm0-data-66a55c7bf38a2201ff48c299843e741f2d537f0b", default-features = false, features = ["metadata"] }
[features]
default = ["rt"]
@@ -120,14 +120,138 @@ time-driver-tima0 = ["_time-driver"]
time-driver-tima1 = ["_time-driver"]
#! ## Chip-selection features
#! Select your chip by specifying the model as a feature, e.g. `mspm0g350x`.
#! Select your chip by specifying the model as a feature, e.g. `mspm0g3507pm`.
#! Check the `Cargo.toml` for the latest list of supported chips.
#!
#! **Important:** Do not forget to adapt the target chip in your toolchain,
#! e.g. in `.cargo/config.toml`.
mspm0c110x = [ "mspm0-metapac/mspm0c110x" ]
mspm0g350x = [ "mspm0-metapac/mspm0g350x" ]
mspm0g351x = [ "mspm0-metapac/mspm0g351x" ]
mspm0l130x = [ "mspm0-metapac/mspm0l130x" ]
mspm0l222x = [ "mspm0-metapac/mspm0l222x" ]
mspm0c1103dgs20 = ["mspm0-metapac/mspm0c1103dgs20"]
mspm0c1103dsg = ["mspm0-metapac/mspm0c1103dsg"]
mspm0c1103dyy = ["mspm0-metapac/mspm0c1103dyy"]
mspm0c1103ruk = ["mspm0-metapac/mspm0c1103ruk"]
mspm0c1104dgs20 = ["mspm0-metapac/mspm0c1104dgs20"]
mspm0c1104dsg = ["mspm0-metapac/mspm0c1104dsg"]
mspm0c1104dyy = ["mspm0-metapac/mspm0c1104dyy"]
mspm0c1104ruk = ["mspm0-metapac/mspm0c1104ruk"]
mspm0c1104ycj = ["mspm0-metapac/mspm0c1104ycj"]
mspm0g1105dgs28 = ["mspm0-metapac/mspm0g1105dgs28"]
mspm0g1105pm = ["mspm0-metapac/mspm0g1105pm"]
mspm0g1105pt = ["mspm0-metapac/mspm0g1105pt"]
mspm0g1105rge = ["mspm0-metapac/mspm0g1105rge"]
mspm0g1105rgz = ["mspm0-metapac/mspm0g1105rgz"]
mspm0g1105rhb = ["mspm0-metapac/mspm0g1105rhb"]
mspm0g1106dgs28 = ["mspm0-metapac/mspm0g1106dgs28"]
mspm0g1106pm = ["mspm0-metapac/mspm0g1106pm"]
mspm0g1106pt = ["mspm0-metapac/mspm0g1106pt"]
mspm0g1106rge = ["mspm0-metapac/mspm0g1106rge"]
mspm0g1106rgz = ["mspm0-metapac/mspm0g1106rgz"]
mspm0g1106rhb = ["mspm0-metapac/mspm0g1106rhb"]
mspm0g1107dgs28 = ["mspm0-metapac/mspm0g1107dgs28"]
mspm0g1107pm = ["mspm0-metapac/mspm0g1107pm"]
mspm0g1107pt = ["mspm0-metapac/mspm0g1107pt"]
mspm0g1107rge = ["mspm0-metapac/mspm0g1107rge"]
mspm0g1107rgz = ["mspm0-metapac/mspm0g1107rgz"]
mspm0g1107rhb = ["mspm0-metapac/mspm0g1107rhb"]
mspm0g1107ycj = ["mspm0-metapac/mspm0g1107ycj"]
mspm0g1505pm = ["mspm0-metapac/mspm0g1505pm"]
mspm0g1505pt = ["mspm0-metapac/mspm0g1505pt"]
mspm0g1505rge = ["mspm0-metapac/mspm0g1505rge"]
mspm0g1505rgz = ["mspm0-metapac/mspm0g1505rgz"]
mspm0g1505rhb = ["mspm0-metapac/mspm0g1505rhb"]
mspm0g1506pm = ["mspm0-metapac/mspm0g1506pm"]
mspm0g1506pt = ["mspm0-metapac/mspm0g1506pt"]
mspm0g1506rge = ["mspm0-metapac/mspm0g1506rge"]
mspm0g1506rgz = ["mspm0-metapac/mspm0g1506rgz"]
mspm0g1506rhb = ["mspm0-metapac/mspm0g1506rhb"]
mspm0g1507pm = ["mspm0-metapac/mspm0g1507pm"]
mspm0g1507pt = ["mspm0-metapac/mspm0g1507pt"]
mspm0g1507rge = ["mspm0-metapac/mspm0g1507rge"]
mspm0g1507rgz = ["mspm0-metapac/mspm0g1507rgz"]
mspm0g1507rhb = ["mspm0-metapac/mspm0g1507rhb"]
mspm0g1507ycj = ["mspm0-metapac/mspm0g1507ycj"]
mspm0g1519rgz = ["mspm0-metapac/mspm0g1519rgz"]
mspm0g1519rhb = ["mspm0-metapac/mspm0g1519rhb"]
mspm0g3105dgs20 = ["mspm0-metapac/mspm0g3105dgs20"]
mspm0g3105dgs28 = ["mspm0-metapac/mspm0g3105dgs28"]
mspm0g3105rhb = ["mspm0-metapac/mspm0g3105rhb"]
mspm0g3106dgs20 = ["mspm0-metapac/mspm0g3106dgs20"]
mspm0g3106dgs28 = ["mspm0-metapac/mspm0g3106dgs28"]
mspm0g3106rhb = ["mspm0-metapac/mspm0g3106rhb"]
mspm0g3107dgs20 = ["mspm0-metapac/mspm0g3107dgs20"]
mspm0g3107dgs28 = ["mspm0-metapac/mspm0g3107dgs28"]
mspm0g3107rhb = ["mspm0-metapac/mspm0g3107rhb"]
mspm0g3505dgs28 = ["mspm0-metapac/mspm0g3505dgs28"]
mspm0g3505pm = ["mspm0-metapac/mspm0g3505pm"]
mspm0g3505pt = ["mspm0-metapac/mspm0g3505pt"]
mspm0g3505rgz = ["mspm0-metapac/mspm0g3505rgz"]
mspm0g3505rhb = ["mspm0-metapac/mspm0g3505rhb"]
mspm0g3506dgs28 = ["mspm0-metapac/mspm0g3506dgs28"]
mspm0g3506pm = ["mspm0-metapac/mspm0g3506pm"]
mspm0g3506pt = ["mspm0-metapac/mspm0g3506pt"]
mspm0g3506rgz = ["mspm0-metapac/mspm0g3506rgz"]
mspm0g3506rhb = ["mspm0-metapac/mspm0g3506rhb"]
mspm0g3507dgs28 = ["mspm0-metapac/mspm0g3507dgs28"]
mspm0g3507pm = ["mspm0-metapac/mspm0g3507pm"]
mspm0g3507pt = ["mspm0-metapac/mspm0g3507pt"]
mspm0g3507rgz = ["mspm0-metapac/mspm0g3507rgz"]
mspm0g3507rhb = ["mspm0-metapac/mspm0g3507rhb"]
mspm0g3519pm = ["mspm0-metapac/mspm0g3519pm"]
mspm0g3519pn = ["mspm0-metapac/mspm0g3519pn"]
mspm0g3519pz = ["mspm0-metapac/mspm0g3519pz"]
mspm0g3519rgz = ["mspm0-metapac/mspm0g3519rgz"]
mspm0g3519rhb = ["mspm0-metapac/mspm0g3519rhb"]
mspm0l1105dgs20 = ["mspm0-metapac/mspm0l1105dgs20"]
mspm0l1105dgs28 = ["mspm0-metapac/mspm0l1105dgs28"]
mspm0l1105dyy = ["mspm0-metapac/mspm0l1105dyy"]
mspm0l1105rge = ["mspm0-metapac/mspm0l1105rge"]
mspm0l1105rtr = ["mspm0-metapac/mspm0l1105rtr"]
mspm0l1106dgs20 = ["mspm0-metapac/mspm0l1106dgs20"]
mspm0l1106dgs28 = ["mspm0-metapac/mspm0l1106dgs28"]
mspm0l1106dyy = ["mspm0-metapac/mspm0l1106dyy"]
mspm0l1106rge = ["mspm0-metapac/mspm0l1106rge"]
mspm0l1106rhb = ["mspm0-metapac/mspm0l1106rhb"]
mspm0l1106rtr = ["mspm0-metapac/mspm0l1106rtr"]
mspm0l1227pm = ["mspm0-metapac/mspm0l1227pm"]
mspm0l1227pn = ["mspm0-metapac/mspm0l1227pn"]
mspm0l1227pt = ["mspm0-metapac/mspm0l1227pt"]
mspm0l1227rge = ["mspm0-metapac/mspm0l1227rge"]
mspm0l1227rgz = ["mspm0-metapac/mspm0l1227rgz"]
mspm0l1227rhb = ["mspm0-metapac/mspm0l1227rhb"]
mspm0l1228pm = ["mspm0-metapac/mspm0l1228pm"]
mspm0l1228pn = ["mspm0-metapac/mspm0l1228pn"]
mspm0l1228pt = ["mspm0-metapac/mspm0l1228pt"]
mspm0l1228rge = ["mspm0-metapac/mspm0l1228rge"]
mspm0l1228rgz = ["mspm0-metapac/mspm0l1228rgz"]
mspm0l1228rhb = ["mspm0-metapac/mspm0l1228rhb"]
mspm0l1303rge = ["mspm0-metapac/mspm0l1303rge"]
mspm0l1304dgs20 = ["mspm0-metapac/mspm0l1304dgs20"]
mspm0l1304dgs28 = ["mspm0-metapac/mspm0l1304dgs28"]
mspm0l1304dyy = ["mspm0-metapac/mspm0l1304dyy"]
mspm0l1304rge = ["mspm0-metapac/mspm0l1304rge"]
mspm0l1304rhb = ["mspm0-metapac/mspm0l1304rhb"]
mspm0l1304rtr = ["mspm0-metapac/mspm0l1304rtr"]
mspm0l1305dgs20 = ["mspm0-metapac/mspm0l1305dgs20"]
mspm0l1305dgs28 = ["mspm0-metapac/mspm0l1305dgs28"]
mspm0l1305dyy = ["mspm0-metapac/mspm0l1305dyy"]
mspm0l1305rge = ["mspm0-metapac/mspm0l1305rge"]
mspm0l1305rtr = ["mspm0-metapac/mspm0l1305rtr"]
mspm0l1306dgs20 = ["mspm0-metapac/mspm0l1306dgs20"]
mspm0l1306dgs28 = ["mspm0-metapac/mspm0l1306dgs28"]
mspm0l1306dyy = ["mspm0-metapac/mspm0l1306dyy"]
mspm0l1306rge = ["mspm0-metapac/mspm0l1306rge"]
mspm0l1306rhb = ["mspm0-metapac/mspm0l1306rhb"]
mspm0l1343dgs20 = ["mspm0-metapac/mspm0l1343dgs20"]
mspm0l1344dgs20 = ["mspm0-metapac/mspm0l1344dgs20"]
mspm0l1345dgs28 = ["mspm0-metapac/mspm0l1345dgs28"]
mspm0l1346dgs28 = ["mspm0-metapac/mspm0l1346dgs28"]
mspm0l2227pm = ["mspm0-metapac/mspm0l2227pm"]
mspm0l2227pn = ["mspm0-metapac/mspm0l2227pn"]
mspm0l2227pt = ["mspm0-metapac/mspm0l2227pt"]
mspm0l2227rgz = ["mspm0-metapac/mspm0l2227rgz"]
mspm0l2228pm = ["mspm0-metapac/mspm0l2228pm"]
mspm0l2228pn = ["mspm0-metapac/mspm0l2228pn"]
mspm0l2228pt = ["mspm0-metapac/mspm0l2228pt"]
mspm0l2228rgz = ["mspm0-metapac/mspm0l2228rgz"]
msps003f3pw20 = ["mspm0-metapac/msps003f3pw20"]
msps003f4pw20 = ["mspm0-metapac/msps003f4pw20"]

28
embassy-mspm0/README.md Normal file
View File

@@ -0,0 +1,28 @@
# Embassy MSPM0 HAL
The embassy-mspm0 HAL aims to provide a safe, idiomatic hardware abstraction layer for all MSPM0 and MSPS003 chips.
* [Documentation](https://docs.embassy.dev/embassy-mspm0/) (**Important:** use docs.embassy.dev rather than docs.rs to see the specific docs for the chip youre using!)
* [Source](https://github.com/embassy-rs/embassy/tree/main/embassy-mspm0)
* [Examples](https://github.com/embassy-rs/embassy/tree/main/examples)
## Embedded-hal
The `embassy-mspm0` HAL implements the traits from [embedded-hal](https://crates.io/crates/embedded-hal) (1.0) and [embedded-hal-async](https://crates.io/crates/embedded-hal-async), as well as [embedded-io](https://crates.io/crates/embedded-io) and [embedded-io-async](https://crates.io/crates/embedded-io-async).
## A note on feature flag names
Feature flag names for chips do not include temperature rating or distribution format.
Usually chapter 10 of your device's datasheet will explain the device nomenclature and how to decode it. Feature names in embassy-mspm0 only use the following from device nomenclature:
- MCU platform
- Product family
- Device subfamily
- Flash memory
- Package type
This means for a part such as `MSPM0G3507SPMR`, the feature name is `mspm0g3507pm`. This also means that `MSPM0G3507QPMRQ1` uses the feature `mspm0g3507pm`, since the Q1 parts are just qualified variants of the base G3507 with a PM (QFP-64) package.
## Interoperability
This crate can run on any executor.

View File

@@ -7,7 +7,7 @@ use std::sync::LazyLock;
use std::{env, fs};
use common::CfgSet;
use mspm0_metapac::metadata::METADATA;
use mspm0_metapac::metadata::{ALL_CHIPS, METADATA};
use proc_macro2::{Ident, Literal, Span, TokenStream};
use quote::{format_ident, quote};
@@ -24,6 +24,27 @@ fn generate_code() {
cfgs.declare_all(&["gpio_pb", "gpio_pc", "int_group1"]);
let chip_name = match env::vars()
.map(|(a, _)| a)
.filter(|x| x.starts_with("CARGO_FEATURE_MSPM0") || x.starts_with("CARGO_FEATURE_MSPS"))
.get_one()
{
Ok(x) => x,
Err(GetOneError::None) => panic!("No mspm0xx/mspsxx Cargo feature enabled"),
Err(GetOneError::Multiple) => panic!("Multiple mspm0xx/mspsxx Cargo features enabled"),
}
.strip_prefix("CARGO_FEATURE_")
.unwrap()
.to_ascii_lowercase()
.replace('_', "-");
eprintln!("chip: {chip_name}");
cfgs.enable_all(&get_chip_cfgs(&chip_name));
for chip in ALL_CHIPS {
cfgs.declare_all(&get_chip_cfgs(&chip));
}
let mut singletons = get_singletons(&mut cfgs);
time_driver(&mut singletons, &mut cfgs);
@@ -44,6 +65,60 @@ fn generate_code() {
rustfmt(&out_file);
}
fn get_chip_cfgs(chip_name: &str) -> Vec<String> {
let mut cfgs = Vec::new();
// GPIO on C110x is special as it does not belong to an interrupt group.
if chip_name.starts_with("mspm0c110") || chip_name.starts_with("msps003f") {
cfgs.push("mspm0c110x".to_string());
}
// Family ranges (temporary until int groups are generated)
//
// TODO: Remove this once int group stuff is generated.
if chip_name.starts_with("mspm0g110") {
cfgs.push("mspm0g110x".to_string());
}
if chip_name.starts_with("mspm0g150") {
cfgs.push("mspm0g150x".to_string());
}
if chip_name.starts_with("mspm0g310") {
cfgs.push("mspm0g310x".to_string());
}
if chip_name.starts_with("mspm0g350") {
cfgs.push("mspm0g350x".to_string());
}
if chip_name.starts_with("mspm0g351") {
cfgs.push("mspm0g351x".to_string());
}
if chip_name.starts_with("mspm0l110") {
cfgs.push("mspm0l110x".to_string());
}
if chip_name.starts_with("mspm0l122") {
cfgs.push("mspm0l122x".to_string());
}
if chip_name.starts_with("mspm0l130") {
cfgs.push("mspm0l130x".to_string());
}
if chip_name.starts_with("mspm0l134") {
cfgs.push("mspm0l134x".to_string());
}
if chip_name.starts_with("mspm0l222") {
cfgs.push("mspm0l222x".to_string());
}
cfgs
}
#[derive(Debug, Clone)]
struct Singleton {
name: String,
@@ -146,7 +221,7 @@ fn make_valid_identifier(s: &str) -> Singleton {
}
fn generate_pincm_mapping() -> TokenStream {
let pincms = METADATA.pincm_mappings.iter().map(|mapping| {
let pincms = METADATA.pins.iter().map(|mapping| {
let port_letter = mapping.pin.strip_prefix("P").unwrap();
let port_base = (port_letter.chars().next().unwrap() as u8 - b'A') * 32;
// This assumes all ports are single letter length.
@@ -174,11 +249,11 @@ fn generate_pincm_mapping() -> TokenStream {
}
fn generate_pin() -> TokenStream {
let pin_impls = METADATA.pincm_mappings.iter().map(|pincm_mapping| {
let name = Ident::new(&pincm_mapping.pin, Span::call_site());
let port_letter = pincm_mapping.pin.strip_prefix("P").unwrap();
let pin_impls = METADATA.pins.iter().map(|pin| {
let name = Ident::new(&pin.pin, Span::call_site());
let port_letter = pin.pin.strip_prefix("P").unwrap();
let port_letter = port_letter.chars().next().unwrap();
let pin_number = Literal::u8_unsuffixed(pincm_mapping.pin[2..].parse::<u8>().unwrap());
let pin_number = Literal::u8_unsuffixed(pin.pin[2..].parse::<u8>().unwrap());
let port = Ident::new(&format!("Port{}", port_letter), Span::call_site());

View File

@@ -10,7 +10,7 @@ use embassy_sync::waitqueue::AtomicWaker;
use crate::pac::gpio::vals::*;
use crate::pac::gpio::{self};
#[cfg(all(feature = "rt", feature = "mspm0c110x"))]
#[cfg(all(feature = "rt", mspm0c110x))]
use crate::pac::interrupt;
use crate::pac::{self};
@@ -1120,7 +1120,7 @@ impl Iterator for BitIter {
}
// C110x has a dedicated interrupt just for GPIOA, as it does not have a GROUP1 interrupt.
#[cfg(all(feature = "rt", feature = "mspm0c110x"))]
#[cfg(all(feature = "rt", mspm0c110x))]
#[interrupt]
fn GPIOA() {
gpioa_interrupt();

View File

@@ -0,0 +1,51 @@
use crate::pac;
use crate::pac::interrupt;
#[cfg(feature = "rt")]
#[interrupt]
fn GROUP0() {
use mspm0_metapac::Group0;
let group = pac::CPUSS.int_group(0);
// Must subtract by 1 since NO_INTR is value 0
let iidx = group.iidx().read().stat().to_bits() - 1;
let Ok(group) = pac::Group0::try_from(iidx as u8) else {
debug!("Invalid IIDX for group 0: {}", iidx);
return;
};
match group {
Group0::WWDT0 => todo!("implement WWDT0"),
Group0::WWDT1 => todo!("implement WWDT1"),
Group0::DEBUGSS => todo!("implement DEBUGSS"),
Group0::FLASHCTL => todo!("implement FLASHCTL"),
Group0::SYSCTL => todo!("implement SYSCTL"),
}
}
#[cfg(feature = "rt")]
#[interrupt]
fn GROUP1() {
use mspm0_metapac::Group1;
let group = pac::CPUSS.int_group(1);
// Must subtract by 1 since NO_INTR is value 0
let iidx = group.iidx().read().stat().to_bits() - 1;
let Ok(group) = pac::Group1::try_from(iidx as u8) else {
debug!("Invalid IIDX for group 1: {}", iidx);
return;
};
match group {
Group1::GPIOA => crate::gpio::gpioa_interrupt(),
Group1::GPIOB => crate::gpio::gpiob_interrupt(),
Group1::COMP0 => todo!("implement COMP0"),
Group1::COMP1 => todo!("implement COMP1"),
Group1::COMP2 => todo!("implement COMP2"),
Group1::TRNG => todo!("implement TRNG"),
}
}

View File

@@ -1,6 +1,11 @@
#![no_std]
// Doc feature labels can be tested locally by running RUSTDOCFLAGS="--cfg=docsrs" cargo +nightly doc
#![cfg_attr(docsrs, feature(doc_auto_cfg, doc_cfg_hide), doc(cfg_hide(doc, docsrs)))]
#![cfg_attr(
docsrs,
doc = "<div style='padding:30px;background:#810;color:#fff;text-align:center;'><p>You might want to <a href='https://docs.embassy.dev/embassy-mspm0'>browse the `embassy-mspm0` documentation on the Embassy website</a> instead.</p><p>The documentation here on `docs.rs` is built for a single chip only, while on the Embassy website you can pick your exact chip from the top menu. Available peripherals and their APIs change depending on the chip.</p></div>\n\n"
)]
#![doc = include_str!("../README.md")]
// This mod MUST go first, so that the others see its macros.
pub(crate) mod fmt;
@@ -35,11 +40,11 @@ pub mod mode {
mod time_driver;
// Interrupt group handlers.
#[cfg_attr(feature = "mspm0c110x", path = "int_group/c110x.rs")]
#[cfg_attr(feature = "mspm0g350x", path = "int_group/g350x.rs")]
#[cfg_attr(feature = "mspm0g351x", path = "int_group/g351x.rs")]
#[cfg_attr(feature = "mspm0l130x", path = "int_group/l130x.rs")]
#[cfg_attr(feature = "mspm0l222x", path = "int_group/l222x.rs")]
#[cfg_attr(mspm0c110x, path = "int_group/c110x.rs")]
#[cfg_attr(mspm0g350x, path = "int_group/g350x.rs")]
#[cfg_attr(mspm0g351x, path = "int_group/g351x.rs")]
#[cfg_attr(mspm0l130x, path = "int_group/l130x.rs")]
#[cfg_attr(mspm0l222x, path = "int_group/l222x.rs")]
mod int_group;
pub(crate) mod _generated {
@@ -109,7 +114,7 @@ pub fn init(_config: Config) -> Peripherals {
_generated::enable_group_interrupts(cs);
#[cfg(feature = "mspm0c110x")]
#[cfg(mspm0c110x)]
unsafe {
use crate::_generated::interrupt::typelevel::Interrupt;
crate::interrupt::typelevel::GPIOA::enable();