Skip to content

pac extension traits and unmacro #3

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jun 21, 2025
Merged

pac extension traits and unmacro #3

merged 1 commit into from
Jun 21, 2025

Conversation

burrbull
Copy link
Contributor

Only g4 for now.

@usbalbin
Copy link
Owner

This looks really, really nice from a quick glance! Let me know when you want me to take a closer look :)

@burrbull
Copy link
Contributor Author

@usbalbin I don't think it is good idea to define pins here.
Here should be core part (structures and traits) which depends on PACs only.

In hals should be pin definitions and wrappers for initializers of structures defined here.
HAL depends on stm32-hrtim.
This repo should have HAL only in dev-dependencies.

@usbalbin
Copy link
Owner

Good idea! That makes sense

@usbalbin
Copy link
Owner

So something roughly like #6?

@burrbull
Copy link
Contributor Author

Yes. It looks more reasonable for me.

This was referenced Apr 26, 2025
@usbalbin usbalbin changed the base branch from the_code to main May 2, 2025 11:21
@burrbull
Copy link
Contributor Author

burrbull commented May 2, 2025

Rebased. But no guaranty there is nothing missed.

@burrbull burrbull force-pushed the ext branch 3 times, most recently from 17d4dcc to 3697fff Compare June 14, 2025 06:37
@burrbull burrbull marked this pull request as ready for review June 14, 2025 06:37
@burrbull
Copy link
Contributor Author

rebased

Comment on lines +7 to +8
stm32f3 = { version = "0.16.0", optional = true }
stm32h7 = { version = "0.16.0", optional = true }
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice! :)

#[cfg(feature = "hrtim_v2")]
use pac::hrtim_timf as timf;

#[derive(Clone, Copy, Debug, PartialEq, Eq)]
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]

Is it possible to derive defmt::Format for these?

F = 5,
}

pub trait Instance: Deref<Target = Self::RB> {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would you mind writing some very brief doc comment? For example, what is the difference of Instance vs InstanceX? :)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The difference is that second one is not implemented for master timer. Although the names are not very good.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So something like

Suggested change
pub trait Instance: Deref<Target = Self::RB> {
/// Any HR Timer A-F or Master
pub trait Instance: Deref<Target = Self::RB> {

let common = unsafe { &*HRTIM_COMMON::ptr() };
common.cr1().modify(|_, w| match TIM::TIMX {
Timer::Master => w.mudis().clear_bit(),
Timer::Tim(v) => w.tudis(v as _).clear_bit(),
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This really is very nice!

pub trait $TrR {
$(fn $f(&self $(, $n: $e)?) -> $fr;)*
}
impl<REG: reg::$TrR> $TrR for R<REG> {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just curious, what does these do?

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this somehow to abstract away the calls to the different functions of all timers?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just curious, what does these do?

What is the question about? The goal of these wrapper traits?

Maybe it is not the best solution but the best that I've found to abstract over similar but not identical registers across different peripherals. It requires fields to be reexported (derived in SVD) to work.

The idea is to use unique REGrs register specification as associated type.
In current implementation you need 4 traits for each RW register: 2 traits for read and write implemented on REGrs + 1 wrapper for R<REGrs> and 1 wrapper for W<REGrs.

Alternative options:

  1. It can work without wrapper traits but you need to call it as path_to::REGrs::field(&r) or something like this. Which is annoying and different syntax. Works but not good.
  2. You could make implementations directly on R<REGrs> and W<REGrs. But in this case rust can't infer types and require where everywhere. Very bad.

But option 3=1+2 works.
The magic is in impl<REG: reg::RegRead> RegRead for R<REG> line.

Something like

trait Instance {
    type REG: RegRead + RegWrite; // it can be single `Reg` trait
}

allows to use canonical svd2rust API (reg.write(|w| w.field().variant()), reg.read().field().variant()) for any generic PER: Instance peripheral.

Copy link
Owner

@usbalbin usbalbin Jun 20, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can not quite say I understand all implications of the above, but does seem to make a lot of sense :)

Thank you for the explanation

Copy link
Owner

@usbalbin usbalbin left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is very nice! Thanks a lot for this! :)

Since this changes quite a bit of(most) things, I would like to run some tests on some hardware just to confirm that at least some of the most basic things still work. I will try to do this in the coming days, hopefully.

In the meantime, CI seems to be a bit angry about capture.rs.

@burrbull
Copy link
Contributor Author

In the meantime, CI seems to be a bit angry about capture.rs.

stm32g4xx-hal hrtim branch depends on wrong stm32-hrtim.

Not sure how to solve this. Maybe use some script to add patch section in Cargo.toml in CI?

@burrbull
Copy link
Contributor Author

Why CI does not run automatically?

@usbalbin
Copy link
Owner

Why CI does not run automatically?

Correct me if I am wrong but I think a user gets "approved" for CI only after having their first PR merged

stm32g4xx-hal hrtim branch depends on wrong stm32-hrtim.

Oh sorry did not realise that

@usbalbin
Copy link
Owner

image

If you want to not count as a first time contributor, you could probably open a PR adding a dot or something to the README

@usbalbin
Copy link
Owner

I ran the tests added in stm32-rs/stm32g4xx-hal#192 for this branch and they pass. They dont test much but at least it is something :)

I am happy to merge this now unless you have something more to add

@burrbull
Copy link
Contributor Author

I am happy to merge this now unless you have something more to add

Nothing for now. At least until new stm32-rs release.

@usbalbin usbalbin merged commit 558357b into usbalbin:main Jun 21, 2025
10 checks passed
@usbalbin
Copy link
Owner

Thank you!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants