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

Unclear behaviour of GpioPin<Output<OpenDrain>, _>::is_high() for ESP32 #1285

Closed
szubinskik opened this issue Mar 13, 2024 · 6 comments
Closed
Labels
bug Something isn't working peripheral:gpio GPIO peripheral

Comments

@szubinskik
Copy link

Prerequisites:

  • ESP-WROOM-32 module
  • 4.7 kOhm resistor

Problem:
Plug the resistor to 3V and GPIO4 pins of the ESP module. Then consider the following code:

#![no_std]
#![no_main]

use esp_backtrace as _;
use esp_println::println;
use esp_hal::{clock::ClockControl, gpio::IO, peripherals::Peripherals, prelude::*};

#[entry]
fn main() -> ! {
    let peripherals = Peripherals::take();
    let system = peripherals.SYSTEM.split();
    let clocks = ClockControl::boot_defaults(system.clock_control).freeze();

    let io = IO::new(peripherals.GPIO, peripherals.IO_MUX);
    let mut pin = io.pins.gpio4.into_open_drain_output();

    println!("{}", pin.is_high().unwrap());

    loop {
    }
}

Obviously, there is voltage applied to the pin, yet the is_high() method returns false. Same setup, but for let mut pin = io.pins.gpio4.into_floating_input(); prints true. Is this behaviour intended?

@sisoteuz
Copy link
Contributor

Seems the problem is more related to hardware than software (is_high function reads the register).

Have you tried to set the internal pull up resistor in place of your own (which I assume is wired as a pull up).

You can do so with pin.internal_pull_up(true).

That might clear some doubts about the internal circuitry potentially affecting the results.

@szubinskik
Copy link
Author

Well, with this simple schema:
obraz

turning the internal resistor on (pin.internal_pull_up(true)) does not change a thing.

@bjoernQ bjoernQ added the bug Something isn't working label Mar 14, 2024
@bjoernQ
Copy link
Contributor

bjoernQ commented Mar 14, 2024

Ok let's try something even simpler

#![no_std]
#![no_main]

use esp_backtrace as _;
use esp_hal::{clock::ClockControl, gpio::IO, peripherals::Peripherals, prelude::*};
use esp_println::println;

#[entry]
fn main() -> ! {
    let peripherals = Peripherals::take();
    let system = peripherals.SYSTEM.split();
    let _clocks = ClockControl::boot_defaults(system.clock_control).freeze();

    let io = IO::new(peripherals.GPIO, peripherals.IO_MUX);
    let mut pin1 = io.pins.gpio4.into_open_drain_output();
    pin1.internal_pull_up(true);
    let mut pin2 = io.pins.gpio5.into_open_drain_output();
    pin2.internal_pull_up(true);

    pin1.set_high().unwrap();
    pin2.set_high().unwrap();

    println!("pin1 = {}", pin1.is_high().unwrap());
    println!("pin2 = {}", pin2.is_high().unwrap());

    loop {}
}

This configures GPIO4 and 5 into open-drain and enables internal pull-ups. So for this test we just need to connect GPIO4 and 5.

Running this code on e.g. EPS32-C3 and ESP32-S3 prints the expected

pin1 = true
pin2 = true

Setting any of the pins to low will show low for both - as expected.

However, I can confirm it's always false on ESP32 - seems like a bug to me (on ESP32).

Thanks for bringing this up!

@bjoernQ
Copy link
Contributor

bjoernQ commented Mar 20, 2024

@szubinskik with #1315 merged it will hopefully work for you, additionally using another pin (which is not an RTC pin) should also help

@szubinskik
Copy link
Author

Thanks for your effort! Gonna verify this and close the issue in case it works

@jessebraham jessebraham added the peripheral:gpio GPIO peripheral label Apr 3, 2024
@MabezDev
Copy link
Member

Closing this, please let us know if your issue wasn't resolved @szubinskik :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working peripheral:gpio GPIO peripheral
Projects
Archived in project
Development

No branches or pull requests

5 participants