Skip to content

ESP32: add pin drive strength #8313

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

Closed

Conversation

jonathanhogg
Copy link
Contributor

@jonathanhogg jonathanhogg commented Feb 16, 2022

Add support for setting the ESP32 GPIO drive strength. There are four supported strengths:

  • 0 = Pin.DRIVE_WEAK: 5mA (max source/sink current) / 130 ohm (approx internal resistance)
  • 1 = Pin.DRIVE_LOW: 10mA / 60 ohm
  • 2 = Pin.DRIVE_MED: 20mA / 30 ohm
  • 3 = Pin.DRIVE_HIGH: 40mA / 15 ohm

I've used the standard 3 documented drive strength constant names from the machine.Pin module docs and added DRIVE_WEAK for the extra one that the ESP32 supports – decided to put it at the weaker end rather than having a DRIVE_HIGHEST constant as the ESP32 default is 2 and that seems to match most naturally to DRIVE_MED.

This was previously bundled up in PR #8284, but having used this functionality for a bit I've decided that it is sufficiently useful to be pulled out on its own and not tied to that (more controversial) PR.

Fixes #8315.

@jonathanhogg
Copy link
Contributor Author

I have verified all four drive strengths on real ESP32 hardware. The IDF docs suggest that the same drive strength values apply to S2, S3 and C3 variants, but I have no real hardware to test this on.

The maximum source/sink currents come from note 8 in table 24 of the ESP32 Datasheet; the approximate internal resistances come from my own tests and this useful forum post.

The drivers are non-linear so pushing them to the limit results in much higher apparent resistance. I've gone with roughly where they stand when running at the maximum recommended current. I've included these rough internal resistances in the docs because they can make a big difference to circuit design – e.g., in terms of resistor choice when driving an LED.

@dpgeorge
Copy link
Member

dpgeorge commented Mar 7, 2022

Thanks for this, the feature looks good.

The only problem is the name of the drive constants:

  • in the docs it specifies LOW_POWER, MED_POWER and HIGH_POWER
  • cc3200 and samd ports use the above constants
  • mimxrt uses DRIVER_OFF and POWER_0 - POWER_6

There was a discussion of the drive/power constants for mimxrt, but I'm not sure why it ended up being different to the docs. Probably because there are many values and it's hard to name them with low/med/high etc and understand the ordering.

I do actually prefer the names DRIVE_LOW, DRIVE_MED, DRIVE_HIGH, because it's clear what argument they should be used for, namely drive. This matches the pull constants like PULL_UP.


It would be good to make all of this consistent. Here is my suggestion: use constants DRIVE_0, DRIVE_1, DRIVE_2 etc (without a limit on the number of them). Then a port just uses 0 up to the maximum number of options that it has. It's very clear what the ordering are. And the word DRIVE_ matches the argument name drive.

@robert-hh what do you think?

@robert-hh
Copy link
Contributor

@dpgeorge It is always favorable to have a common API, and I can go with any name, shorter being better. I'll discuss it with @alphaFred, because that part was made by him.

@alphaFred
Copy link
Contributor

Hi @dpgeorge
@robert-hh relayed your message since that module was implemented by me. I would be fine with the name change. I totally agree - having a commons naming is much better.

Add support for configuring drive strength of output pins with `drive` 
keyword argument and `DRIVE_*` constants.
Add brief documentation of the new `drive` keyword argument.
Update documents with new common names for the drive strength constants.
@jonathanhogg jonathanhogg force-pushed the esp32_pin_drive_strength branch from ed15d7b to 59ffb6b Compare March 7, 2022 09:04
@jonathanhogg
Copy link
Contributor Author

Sounds good to me! I've updated my code and docs, and added a bonus commit updating the machine.Pin docs as well.

@dpgeorge
Copy link
Member

dpgeorge commented Mar 7, 2022

OK, so we go with DRIVE_n constants for all ports then.

@alphaFred
Copy link
Contributor

Yes. I will provide a PR for mimxrt soon, too.

@dpgeorge
Copy link
Member

dpgeorge commented Mar 7, 2022

Merged in 33083bf through 3ebc370 (with minor changes to the last commit to further update the constants in the docs).

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

Successfully merging this pull request may close these issues.

ESP32: port missing support for pin drive strength
4 participants