PaulStoffregen / OneWire

Library for Dallas/Maxim 1-Wire Chips
http://www.pjrc.com/teensy/td_libs_OneWire.html
579 stars 382 forks source link

When use ESP8266 and DS18B20 with parasite power - pin must be cofigured as push-pull #14

Open KAlexK opened 8 years ago

KAlexK commented 8 years ago

When use ESP8266 and DS18B20 with parasite power pin must be configured as push-pull (DRIVER(NORMAL)) before use. Otherwise power from external pull-up resistor will be not enough to drive DS18B20 in conversion stage. For example this not work: OneWire::OneWire(uint8_t pin) { pinMode(pin, INPUT); bitmask = PIN_TO_BITMASK(pin); baseReg = PIN_TO_BASEREG(pin);

if ONEWIRE_SEARCH

reset_search();

endif

}

But this will work: OneWire::OneWire(uint8_t pin) { pinMode(pin, OUTPUT); // Set to DRIVER(NORMAL) pinMode(pin, INPUT); bitmask = PIN_TO_BITMASK(pin); baseReg = PIN_TO_BASEREG(pin);

if ONEWIRE_SEARCH

reset_search();

endif

}

dersimn commented 7 years ago

Still not working.

I'm trying this with the SparkFun ESP8266 Thing - Dev Board. Getting the Device Address and stuff works fine, but temperature conversion in parasite power mode will output just some gibberish values.

My guess is that the ESP8266 is not powerful enough to supply the needed current during conversion, I guess a circuit according to the official data sheet (Page 7, Figure 6) could be a solution.

dersimn commented 7 years ago

At least for me @KAlexK's solution didn't work, because my sensors are connected via a pretty long piece of wire. I made a few changes to the library here to enable an additional pin, when additional power is requested, wire up your sensors according to the attached schematic, and specify the used pins when creating the OneWire object like this:

OneWire oneWire(ONE_WIRE_BUS, PULLUP_PIN);

Schematics

Testato commented 7 years ago

but the energy came from the pullup resistor, not from the mcu. Are you tried decrese the pullup resistor to 2.2k or less ?

dersimn commented 7 years ago

As far as I know, the energy is provided by the microcontroller pin when you call the write method with power=1, then it will be left on HIGH level instead of putting it to some listening mode - even 2.2kΩ wouldn't allow enough current to supply the sensor: 3.3V / 2.2kΩ = 1.5mA

Testato commented 7 years ago

Decrese to 1k or lower. I have no problem, i onlyneed found the correct pullup R value

dersimn commented 7 years ago

Again: The purpose of the pull-up is not for supplying energy to your sensors. The energy is provided by either the micro controller ("hacker solution") or the PNP transistor if you follow the recommendation from the data sheet (Page 7, Figure 6).

If it works for you, you probably have a better ESP8266 board that is able to provide more current.

pstolarz commented 7 years ago

Good catch @dersimn, but one note to:

The energy is provided by either the micro controller ("hacker solution") or the PNP transistor

Energy provisioning (via strong pull-up data wire bit banging OR via controlled power supply like in your case) is not hacker/tech. spec. approach, but depends on a type of GPIO controlling the data wire. For the open-drain output your approach is the only possible, since the open-drain cant provide power to the bus. However for push-pull output both approaches are possible, and in my opinion the bit banged strong pull-up is better for sake of its simplicity. If you need more info on this topic look here:

https://github.com/pstolarz/w1-gpio-cl

Dallas doc specifies your approach, since the 1-wire protocol assumes open-drain outputs only.

On the other hand OneWire lib contains buggy impl. of the open-drain handling, so I'd strongly recommend you to incorporate my pull-request #8 to properly handle the bit banged strong pull-up in your fork and then check if it works on your setup or not. You can also use nodeMCU 1-wire API since (as far as I know) it contains my fix already.

pavel-demin commented 5 years ago

Thanks @KAlexK for the idea of adding pinMode(pin, OUTPUT) to the code.

Looks like pinMode(pin, INPUT) sets the pin driver mode to OPEN_DRAIN and pinMode(pin, OUTPUT) sets the pin driver mode back to NORMAL.

Since I don't want to patch the OneWire library, I've just added pinMode(pin, OUTPUT) to the setup() function of my Arduino sketch and it's solved my problem with the parasite power.

pfeerick commented 5 years ago

Was just revisiting some code that recently stopped working due to ThingSpeak changing the requirements for how data is posted, and whilst my non-parasitic DS18B20 sensors are working again, I have a parasitic one which would not work at all (either giving me -127 or -85). I added the 4.7k pullup as it had never had one, and that made no difference. I was trying to find the reference I'd used before when using the parasitic sensors before, and stumbled upon this, and it works! :) I'm using the OneWire library and the DallasTemperature library, and I just added pinMode(pin, OUTPUT); to the code before starting to use the sensor, and it no longer registers -85*C :D Thank you! This may also be relevant to #58 ...

AlbanT commented 5 years ago

adding pinMode(pin, OUTPUT) to the code helped for me as well with my non parasitic DS18B20 sensors.

ChrisXenon commented 4 years ago

I am using Wemos D1 mimi and finding parasitic mode doesn't work. Has there been any progress in getting this to work out of the box (licbrary)? I don't understand all the bitmap sourcery (sic) and pasting it into my code causes permission errors during compilation.

dersimn commented 3 years ago

Well it looks like I made some effort for nothing.. here's the Hack:

1) Putting pinMode(pin, OUTPUT) somewhere before sensor.begin(); works, but: 2) It doesn't work with a 4.7kΩ pull-up resistor circuit you'll find all over the internet. It works for a Wemos D1 Mini on some pins and yeah.. I was a little bit stupid and should have "RTFM" before: Some pins have an internal pull-up resistor🤦🏻‍♂️ 3) Here's my circuit, as simple as that: Screenshot 2020-12-14 at 19 46 48

ChrisXenon commented 3 years ago

Thanks for sharing.