Skip to content
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

Rp2350 b support #4723

Closed
wants to merge 9 commits into from
Closed

Rp2350 b support #4723

wants to merge 9 commits into from

Conversation

amken3d
Copy link

@amken3d amken3d commented Feb 2, 2025

Adding support for the RP2350B
a. Support for Pins 31 thru 47
b. Updated ADC
c. Updated PWM
d. Updated Pico2, elecrow and tiny2350 json to add rp2350a buildtag
e. Added Amken Max14 board (Intelligent motor controller board in Alpha testing stages)

All test pass using make test
ok github.com/tinygo-org/tinygo/builder (cached)
ok github.com/tinygo-org/tinygo/cgo (cached)
ok github.com/tinygo-org/tinygo/compileopts (cached)
ok github.com/tinygo-org/tinygo/compiler (cached)
ok github.com/tinygo-org/tinygo/interp (cached)
ok github.com/tinygo-org/tinygo/transform (cached)
ok github.com/tinygo-org/tinygo 60.810s

a. Support for Pins 31 thru 47
b. Updated ADC
c. Updated PWM
d. Updated Pico2, elecrow and tiny2350 json to add rp2350a buildtag
e. Added Amken Max14 board
a. Updated ADC
b. including tiny2350.json updates
@@ -2,7 +2,7 @@
"inherits": [
"rp2350"
],
"build-tags": ["pico2"],
"build-tags": ["pico2", "rp2350a"],
Copy link
Member

Choose a reason for hiding this comment

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

I wonder if we should deprecate the existing rp2350 target in favor of a new rp2350a.json so specific boards can just inherit from either rp2350a or rp2350b depending on which chip they are using? That just seems a bit more straightforward to me.

If we really do not want to remove the rp2350 target completely, it could inherit from rp2350a.

Copy link
Contributor

@eliasnaur eliasnaur Feb 6, 2025

Choose a reason for hiding this comment

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

FWIW, I argue for the other way around: define only the rp2350 that covers both rp2350a and rp2350b by exposing all the extra pins etc (rp2350b in this PR). It's then up to boards and/or particular applications to know which model they're running on.

Copy link
Member

Choose a reason for hiding this comment

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

It is not completely clear that we can do that with just pin mapping, since it appears that there are also things like additional ADC channels that only exist on the "B" version. But perhaps that does not matter for compilation as long as you do not try to use a thing that does not exist on the board you are targeting?

I personally still think being explicit about which variation you are using with our current build tags based system is probably a good thing.

Copy link
Contributor

Choose a reason for hiding this comment

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

(Still FWIW) I see your point about being explicit, however consider the advantage of portable firmware builds. That is, assuming (1) that model A is a subset of B, and (2) the added pins/units can easily be detected from registers, I consider it a win that you can build 1 firmware image for both variants.

As a personal example, I'm building on rp2350a but may run out of pins for a future hardware revision and upgrade to rp2350b. I'd love to have 1 firmware image for both boards.

Copy link
Contributor

Choose a reason for hiding this comment

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

I support being able to build 1 firmware for both- if it means an extra register read so be it :)

Copy link
Author

Choose a reason for hiding this comment

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

You still need two build tags as the pin alignment is different. ADC0 starts at GPIO26 for A and at GPIO40 for B variant.


// Period returns the used PWM period in nanoseconds.
func (p *pwmGroup) Period() uint64 {
periodPerCycle := cpuPeriod()
Copy link
Contributor

Choose a reason for hiding this comment

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

Given #4674 (comment), I don't think cpuPeriod should be used anymore; its calculation 1e9/CPUFrequency() won't be integer at 133MHz or 150MHz.

Copy link
Contributor

Choose a reason for hiding this comment

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

Why should we not use it anymore?

Copy link
Contributor

@eliasnaur eliasnaur Feb 8, 2025

Choose a reason for hiding this comment

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

cpuPeriod's value is 1e9/CPUFrequency() which for 125MHz is a nice round 8, but for 133MHz or 150MHz is not and thus PWM accuracy will suffer.

Copy link
Author

Choose a reason for hiding this comment

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

You will like the change that this new commit introduces. You can select from a wide variety of good frequencies all the way upto 300Mhz, many of which produce clean CPU periods.

Copy link
Contributor

Choose a reason for hiding this comment

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

Thank you! However, do you know whether CPUFrequency is still constant enough to satisfy the constraints of delay.Sleep? See #4674 (comment)

Copy link
Author

Choose a reason for hiding this comment

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

I will take a look at it again.
My simplistic solution was that if you cared about "uneven" frequency, just change it to one where it is even. I provided the following carefully selected options
[50,100,125,133,150,175,200,225,240,250,275,300]
But to your point, there are some on this list which are not factors of 2

Copy link
Contributor

Choose a reason for hiding this comment

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

I see. To be clear, the current frequency, 125MHz, that both rp2040 and rp2350 run on work fine with cpuPeriod. I bring this is up now because you're in the area, and I'd like to bump both variants to their datasheet maximum (133MHz and 150MHz) in a future PR. I don't want to use frequencies outside datasheet guaranteed frequencies.

Copy link
Author

Choose a reason for hiding this comment

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

133 and 150 are for the reference design of the Pico. Anyway the datasheet says "Most chips in most normal
environments can run significantly faster than the quoted maximum, and therefore support overclocking" pg 512. The speeds that they choose is a function of the crystal that they used. In my boards, I use a much higher quality cmos oscillator at 40mhz, which i share with the CAN controller as well, which has error in the <10ppm range. In practical applications, even on the pico, you can run 300 mhz without the chip complaining or overheating. I have run rp2040 at 500Mhz with a higher core voltage. The datasheet even tells you how to do it.

Copy link
Contributor

Choose a reason for hiding this comment

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

Sure, I'm not saying overclocking is impossible or undesirable. I'm only saying that the PWM divider calculations should handle frequencies that don't nicely divide 1e9, as cpuPeriod assumes.

Copy link
Author

Choose a reason for hiding this comment

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

Yes. Agreed. I will do that. Thanks for reminding.

@@ -1,4 +1,4 @@
//go:build rp2040 || rp2350 || ae_rp2040 || badger2040 || challenger_rp2040 || feather_rp2040 || gopher_badge || kb2040 || macropad_rp2040 || nano_rp2040 || pico || qtpy_rp2040 || thingplus_rp2040 || thumby || tufty2040 || waveshare_rp2040_zero || xiao_rp2040
//go:build rp2040 || rp2350a || ae_rp2040 || badger2040 || challenger_rp2040 || feather_rp2040 || gopher_badge || kb2040 || macropad_rp2040 || nano_rp2040 || pico || qtpy_rp2040 || thingplus_rp2040 || thumby || tufty2040 || waveshare_rp2040_zero || xiao_rp2040
Copy link
Contributor

@soypat soypat Feb 8, 2025

Choose a reason for hiding this comment

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

i feel like most of these tags are superfluous, no? Shouldn't it work with just rp2040 || rp2350a ?

Copy link
Author

Choose a reason for hiding this comment

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

I removed the board tags.

Updated all boards to remove xoscFreq const and added an init function to initialize SysClockFrequency (new var) and xoscFreq (changed from const to var). The upshot is that system frequency is now changable in runtime. Added a predefined frequencies map created using the sdk's vcocalc logic.
@amken3d
Copy link
Author

amken3d commented Feb 9, 2025

Tested on Pico and Pico2. Good stable overclocking is achieved on both
Console output :
Hello,
sysClockFrequency 300
Updated sysClockFrequency 200
CPU period: 5000000
Running at full speed 300
CPU period: 3333333
Hello,
sysClockFrequency 300

Frequency can now be set at runtime. :)
Enjoy running your Pico's at double the speed.

@deadprogram
Copy link
Member

@amken3d please note build failures in latest commit.

@amken3d
Copy link
Author

amken3d commented Feb 9, 2025

@deadprogram Is there some caching in circleci? I am able to build cleanly with gopher_board selected as target. I updated the board file in [28f938f], but the smoke test keep failing at that spot.

machine

/root/project/src/machine/board_gopher-badge.go:19:15: undefined: GPIO13
/root/project/src/machine/board_gopher-badge.go:21:18: undefined: GPIO2
/root/project/src/machine/board_gopher-badge.go:22:18: undefined: GPIO15
/root/project/src/machine/board_gopher-badge.go:23:18: undefined: GPIO15
/root/project/src/machine/board_gopher-badge.go:25:21: undefined: GPIO10
/root/project/src/machine/board_gopher-badge.go:26:21: undefined: GPIO11
/root/project/src/machine/board_gopher-badge.go:27:21: undefined: GPIO25
/root/project/src/machine/board_gopher-badge.go:28:21: undefined: GPIO24
/root/project/src/machine/board_gopher-badge.go:29:21: undefined: GPIO22
/root/project/src/machine/board_gopher-badge.go:30:21: undefined: GPIO23
/root/project/src/machine/board_gopher-badge.go:32:22: undefined: GPIO21
/root/project/src/machine/board_gopher-badge.go:33:22: undefined: GPIO19
/root/project/src/machine/board_gopher-badge.go:34:22: undefined: GPIO16
/root/project/src/machine/board_gopher-badge.go:35:22: undefined: GPIO17
/root/project/src/machine/board_gopher-badge.go:36:22: undefined: GPIO18
/root/project/src/machine/board_gopher-badge.go:37:22: undefined: GPIO20
/root/project/src/machine/board_gopher-badge.go:38:22: undefined: GPIO12
/root/project/src/machine/board_gopher-badge.go:40:23: undefined: GPIO14
/root/project/src/machine/board_gopher-badge.go:41:23: undefined: GPIO3
/root/project/src/machine/board_gopher-badge.go:46:21: undefined: GPIO0
/root/project/src/machine/board_gopher-badge.go:47:21: undefined: GPIO1
/root/project/src/machine/board_gopher-badge.go:55:21: undefined: GPIO18
/root/project/src/machine/board_gopher-badge.go:56:21: undefined: GPIO19
/root/project/src/machine/board_gopher-badge.go:57:21: undefined: GPIO16
/root/project/src/machine/board_gopher-badge.go:66:2: undefined: SysClockFrequency
/root/project/src/machine/board_gopher-badge.go:66:22: undefined: Freq133MHz
/root/project/src/machine/board_gopher-badge.go:67:2: undefined: xoscFreq
/root/project/src/machine/board_gopher-badge.go:67:13: undefined: Freq12MHz
/root/project/src/machine/board_gopher-badge.go:83:17: undefined: GPIO0
/root/project/src/machine/board_gopher-badge.go:84:17: undefined: GPIO1
/root/project/src/machine/board_gopher-badge.go:85:17: undefined: GPIO4
/root/project/src/machine/board_gopher-badge.go:86:17: undefined: GPIO5
make: *** [GNUmakefile:587: smoketest] Error 1

@amken3d
Copy link
Author

amken3d commented Feb 9, 2025

@deadprogram , need some help. I am not able to figure out why it fails. make test runs clean on my end.
ok github.com/tinygo-org/tinygo/builder 2.770s
ok github.com/tinygo-org/tinygo/cgo (cached)
ok github.com/tinygo-org/tinygo/compileopts (cached)
ok github.com/tinygo-org/tinygo/compiler 1.225s
ok github.com/tinygo-org/tinygo/interp (cached)
ok github.com/tinygo-org/tinygo/transform 0.087s
ok github.com/tinygo-org/tinygo 76.003s

@deadprogram
Copy link
Member

@deadprogram
Copy link
Member

deadprogram commented Feb 9, 2025

The build failures are related to missing pin mappings when building gopher_badge for WASM target e.g. for the TinyGo playground.

@@ -2,6 +2,11 @@

package machine

func init() {
SysClockFrequency = Freq133MHz
Copy link
Contributor

Choose a reason for hiding this comment

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

This exposes new API on machine package. Why would we want to expose a variable that can be modified by users? Is CPUFrequency() not good enough for your applications?

Copy link
Author

Choose a reason for hiding this comment

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

CPUFrequency() only gave me what the current sysClk frequency was and not the ability to overclock or under clock. There are several use cases for being able to change system frequency at runtime like peri synchronization, power management etc. This change makes changing clock speeds on the fly possible.

Copy link
Contributor

Choose a reason for hiding this comment

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

I don't think changing clock frequency at runtime is in scope of this PR. If for nothing else, runtime clock support doesn't answer the question of what to do about all the code that assumes CPUFrequency never changes.

Copy link
Member

Choose a reason for hiding this comment

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

I would agree that any changes about clock frequency should be in a separate PR.

@@ -2,6 +2,11 @@

package machine

func init() {
Copy link
Contributor

Choose a reason for hiding this comment

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

Avoid init functions in machine package always unless absolutely required. I'd like to understand the problem you are trying to solve so I can propose a better way of doing this.

@soypat
Copy link
Contributor

soypat commented Feb 10, 2025

@amken3d Please take a look at my propsed strategy for adding the RP2350B here: #4728

My ultimate motivation for this PR I'm showing you is avoiding adding extraneous complexity to the machine package. I want to keep this maintainable. Thank you for understanding :)

@amken3d
Copy link
Author

amken3d commented Feb 10, 2025

@soypat , Thanks for the review and PR. Your changes for the ADC looks fine to me. My PR does include other things as well. Do you plan to address those as well?

@deadprogram
Copy link
Member

@amken3d @soypat seems from a superficial overview that since the pins and ADC are addressed already in PR #4728 the only thing really "missing" is the PWM support, which would appear to be similar to the ADC changes? Probably another commit to #4728 would do it?

After that, adding the new board support could be done in a separate PR @amken3d

Then any changes to clock speed can be discussed in yet another separate PR/issue. @cibomahto I think had some ideas on how to do this, before it got pulled into a bigger set of objectives and dropped.

@amken3d
Copy link
Author

amken3d commented Feb 10, 2025

@deadprogram , thanks for the guidance. I will close this PR for now.

@amken3d amken3d closed this Feb 10, 2025
@soypat
Copy link
Contributor

soypat commented Feb 12, 2025

Got intellisense back working. Will try to get around to porting your changes @amken3d. Thank you so much for the work you put in :D

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.

4 participants