Author Topic: Improved/optimized DS18B20/1Wire read  (Read 22929 times)

hexium

  • Newbie
  • *
  • Posts: 3
Re: Improved/optimized DS18B20/1Wire read
« Reply #15 on: February 18, 2015, 07:37:32 AM »
Thank you very much for the prompt and accurate response!

lormic

  • Newbie
  • *
  • Posts: 1
Re: Improved/optimized DS18B20/1Wire read
« Reply #16 on: February 21, 2015, 07:22:02 PM »
Hi, I am new in the Arduino World. I am trying to use your code to read the temperatures of two DS18B20 sensors. Eventually I must read the tenfold of DS18B20 sensors. But for now I only get the temperature of one of the two sensors. The sketch only reads sensor 1 (see image attached). When I pull sensor 1 out of the breadboard the sketch returns the values of sensor 2. What am I doing wrong? (btw my sensors don't have the white wire, mine only have red, black and yellow wire)

ColinR

  • Full Member
  • ***
  • Posts: 176
Re: Improved/optimized DS18B20/1Wire read
« Reply #17 on: February 22, 2015, 12:41:18 AM »
The code as-is only reads the first sensor. I've been meaning to write multi-sensor code and haven't gotten around to it. I just haven't had the need with my microcontrollers. I use a 1Wire bus master on my Pi gateway for multidrop scenarios.

For multiple sensors, you'd declare a OneWire object, and each time you perform the search function, you should get the next ROM. When you want to go back to the first ROM, use the reset command and you may again iterate over them. Here is a good description of the command set of the OneWire library: http://www.pjrc.com/teensy/td_libs_OneWire.html

C
« Last Edit: February 22, 2015, 12:55:48 AM by ColinR »
CuPID Controls :: Open Source browser-based sensor and device control
Interfaceinnovations.org/cupidcontrols.html
cupidcontrols.com

ColinR

  • Full Member
  • ***
  • Posts: 176
Re: Improved/optimized DS18B20/1Wire read
« Reply #18 on: February 22, 2015, 12:57:19 AM »
Oh also, it's not mentioned specifically, but if you have multiple DS18B20s, you can use the Skip command before you issue a T convert to simultaneously issue convert commands to all devices on the bus. Saves loads of time. Just watch current draw.

C
CuPID Controls :: Open Source browser-based sensor and device control
Interfaceinnovations.org/cupidcontrols.html
cupidcontrols.com

ChemE

  • Sr. Member
  • ****
  • Posts: 402
  • Country: us
Re: Improved/optimized DS18B20/1Wire read
« Reply #19 on: August 23, 2016, 01:34:00 PM »
I just came across this thread and wanted to contribute my code.  I've been fooling with these sensors for years with an eye towards eventually letting a tiny uC take over temperature measurements for my home brewery.  As others have noted, the Dallas and OneWire libraries are bloated and slow to say the least so I boiled them down to bit banging and delays.  Nice features here include a framework intended to let the uC sleep or do other work while the temperature conversion is happening and elimination of the external pullup resistor.  Also the program size itself is the smallest by far I have ever seen.

NROO means No Resistor and Object Oriented:
https://github.com/cdl1051/DS18B20_NROO

This project only uses 686 bytes of flash so it can fit on even the smallest ATTiny.

Apprentice17

  • Newbie
  • *
  • Posts: 5
Re: Improved/optimized DS18B20/1Wire read
« Reply #20 on: January 07, 2019, 09:14:02 AM »
@Colin R: you mentioned one can iterate over the number of sensors and then reset to go on. Isn't it better to create an array with all the detected sensors and declare them as sensor1 sensor2... instead or searching them again, and again, and again?
At least in case of power consumption I could imagine an sensor-arra could save some energy and might be faster.

But I have no idea how to implement this, yet.

I really like your code, as it frees ressources so I can do multiple things instead of waiting ;)
But as I hav econnected two sensors right now (and later on it might be 3-4 sensors) I wonder how to scale it in a proper way.
Any suggestions?

TomWS

  • Hero Member
  • *****
  • Posts: 1892
Re: Improved/optimized DS18B20/1Wire read
« Reply #21 on: January 07, 2019, 11:21:36 AM »
@Colin R: you mentioned one can iterate over the number of sensors and then reset to go on. Isn't it better to create an array with all the detected sensors and declare them as sensor1 sensor2... instead or searching them again, and again, and again?
At least in case of power consumption I could imagine an sensor-arra could save some energy and might be faster.
I'll have to look at my code, but this is exactly how my DS sensor library works.  It's a wrapper for standard one wire code and the intent is to do the search once in setup, create an array of found sensors, and then, during read, do a 'bulk read' as ColinR suggested and then, as I want to report each result, I simply do a .getTemp(i) where 'i' is the index into the table of found sensors.  You should be able to implement fairly easily with your own wrapper using any OneWire library.

HeneryH

  • Full Member
  • ***
  • Posts: 219
Re: Improved/optimized DS18B20/1Wire read
« Reply #22 on: January 07, 2019, 06:24:35 PM »
I'm using one of the standard Dallas libraries and it works well for me (not time sensitive in my case) except it is uses more power than I'd like.  I had to double up my SuperCaps on the solar unit and even still if I have two cloudy days it will sometimes get too low on power. 

Then since I have a very basic power circuit it never comes back up properly on recharge.  I'd have to add some circuitry to hold the Mote in reset until a threadhold is met on the recharge curve.  Currently I need to manually reset the unit after a low-power event and I had hoped to seal it in a glass box which makes a reset hard.

Sergegsx

  • Jr. Member
  • **
  • Posts: 87
  • Country: es
Re: Improved/optimized DS18B20/1Wire read
« Reply #23 on: January 08, 2019, 01:24:34 AM »
I'm using one of the standard Dallas libraries and it works well for me (not time sensitive in my case) except it is uses more power than I'd like.  I had to double up my SuperCaps on the solar unit and even still if I have two cloudy days it will sometimes get too low on power. 

Then since I have a very basic power circuit it never comes back up properly on recharge.  I'd have to add some circuitry to hold the Mote in reset until a threadhold is met on the recharge curve.  Currently I need to manually reset the unit after a low-power event and I had hoped to seal it in a glass box which makes a reset hard.

Please let us know if you implement this minimum voltage threshold. I am interested as I have the same issue. thank you.

Apprentice17

  • Newbie
  • *
  • Posts: 5
Re: Improved/optimized DS18B20/1Wire read
« Reply #24 on: January 08, 2019, 02:28:11 AM »
@TomWS: Sounds great. Where do I find your lib? And do you have an example on how to implement (two or more sensors)?
How can I ensure I always get the same order for the sensors?
Let's say sensor 1 is CPU, sensor 2 is GPU. I need to make sure the IDs don't switch. Didn't get the criterion on how the searchresult is enumerated.

On ColinR's code I got CPU as Sensor 1. When I connected a second sensor (GPU-Sensor) this was sensor 1 and I couldn't manage to read the CPU sensor anymore.


As I'm working with an rotary encoder to create my menu, I cannot use the original Dallas-lib as I wouldn't be able to read out the input while it's waiting for the results...

//Edit:
User an 1-wire finder:

Looking for 1-Wire devices...
Found '1-Wire' device with address:
0x10, 0x90, 0x51, 0x59, 0x03, 0x08, 0x00, 0xCB
Found '1-Wire' device with address:
0x10, 0x97, 0x1A, 0x59, 0x03, 0x08, 0x00, 0xD7
That's it.

So this are both my sensors. I'm not sure why both of them start with 0x10. Does it declare what kind of device it is? Or how many adresses it has?
So 0x90 and 0x97 might be the first adresses of my sensors?

//Edit2: After reading the datasheet and searching the web, I guess the whole line (8 hex values) is one 64bit address, is it? So the 0x10 might be the beginning of every DS1820?
« Last Edit: January 08, 2019, 05:41:25 AM by Apprentice17 »

ChemE

  • Sr. Member
  • ****
  • Posts: 402
  • Country: us
Re: Improved/optimized DS18B20/1Wire read
« Reply #25 on: January 08, 2019, 06:17:42 AM »
From the datasheet: https://datasheets.maximintegrated.com/en/ds/DS18B20.pdf

64-BIT Lasered ROM code
Each DS18B20 contains a unique 64–bit code (see Figure 8 ) stored in ROM. The least significant 8 bits of the ROM code contain the DS18B20’s 1-Wire family code: 28h. The next  48  bits  contain  a  unique  serial  number.  The  most  significant 8 bits contain a cyclic redundancy check (CRC) byte  that  is  calculated  from  the  first  56  bits  of  the  ROM  code.  A  detailed  explanation  of  the  CRC  bits  is  provided  in the CRC Generation section. The 64-bit ROM code and associated ROM function control logic allow the DS18B20 to operate as a 1-Wire device using the protocol detailed in the 1-Wire Bus System section.

Not sure why you would be getting 0x10 back for the 1-Wire family code

ChemE

  • Sr. Member
  • ****
  • Posts: 402
  • Country: us
Re: Improved/optimized DS18B20/1Wire read
« Reply #26 on: January 08, 2019, 06:29:35 AM »
After doing a bit more digging it seems that the DS18S20's 1-Wire family code is 0x10 while the DS18B20 uses 0x28 as its family code.  Mystery solved.

From https://www.maximintegrated.com/en/app-notes/index.mvp/id/4377 ...
The 8-bit family code in the ROM code is also different for these two devices. The family code for the DS18B20 is 28h; the DS18S20 retains the same family code as the original DS1820, which is 10h.
« Last Edit: January 08, 2019, 06:31:15 AM by ChemE »

Apprentice17

  • Newbie
  • *
  • Posts: 5
Re: Improved/optimized DS18B20/1Wire read
« Reply #27 on: January 08, 2019, 07:35:36 AM »
DS18S20 is what I've ordered. On the case it's labeled DALLAS DS1820. So you seem to prove well ;)
Now I can go on trying to get both sensor values. Maybe TomWS' lib will help me later on...

TomWS

  • Hero Member
  • *****
  • Posts: 1892
Re: Improved/optimized DS18B20/1Wire read
« Reply #28 on: January 08, 2019, 08:03:04 AM »
@TomWS: Sounds great. Where do I find your lib? And do you have an example on how to implement (two or more sensors)?
Attached below.  Note that this is barebones and unsupported.  You're free to use it however you want...
Quote
How can I ensure I always get the same order for the sensors?
Let's say sensor 1 is CPU, sensor 2 is GPU. I need to make sure the IDs don't switch. Didn't get the criterion on how the searchresult is enumerated.
The search protocol will always produce the same results for the same set of sensors as it is based on the bit ordering of the 64 bit serial number.  Once you get a set of results and identify which sensor is 1st, 2nd, etc.  I will not change unless you add another sensor.   However, the serial numbers are constant and, once you know the serial number for a sensor, it may change its position in the table, but will always relate to the same unique sensor.

As ChemE pointed out, the first byte relates to the family or device code of the one wire product.

However, the wrapper supposedly deals with this.  Since I've only used DS18B20s, I can not confirm that it works properly for any other OW type.

Tom
« Last Edit: January 08, 2019, 08:56:05 AM by TomWS »

Apprentice17

  • Newbie
  • *
  • Posts: 5
Re: Improved/optimized DS18B20/1Wire read
« Reply #29 on: January 14, 2019, 03:02:00 AM »
Got ColinR's code converted for using my sensors both:

1.
Read out hex-adresses for sensors using any onewire-scanner-sketch I got my adresses:
0x10, 0x90, 0x51, 0x59, 0x03, 0x08, 0x00, 0xCB
and
0x10, 0x97, 0x1A, 0x59, 0x03, 0x08, 0x00, 0xD7

2.
Converted the strings to decimal values:
0x10 = 16
0x90 = 144
0x51 = 81
0x59 = 89
0x03 = 3
0x08 = 8
0x00 = 0
0xCB = 203


0x10, 0x97, 0x1A, 0x59, 0x03, 0x08, 0x00, 0xD7
0x10 = 16
0x97 = 151
0x1A = 26
0x59 = 89
0x03 = 3
0x08 = 8
0x00 = 0
0xD7 = 215

HEX => DECIMAL
0x10, 0x90, 0x51, 0x59, 0x03, 0x08, 0x00, 0xCB => 16, 144, 81, 89, 3, 8, 0, 203
0x10, 0x97, 0x1A, 0x59, 0x03, 0x08, 0x00, 0xD7 =>16, 151, 26, 89, 3, 8, 0, 215

3.
Now I created the arrays for MY sensors manually:
byte dsaddr[] = {16, 144, 81, 89, 3, 8, 0, 203};
byte dsaddr2[] = {16, 151, 26, 89, 3, 8, 0, 215};

Notice: I filled in the decimal adresses of _my_ sensors (your's might be slightly different...).



4.
Start reading temperatures for both sensors:
dssetresolution(myds,dsaddr,resolution);
dssetresolution(myds,dsaddr2,resolution);


5.
Read temperatures:
lcd.setCursor(0,0);
lcd.print("temp1: ");
lcd.print(dsreadtemp(myds,dsaddr, resolution));

lcd.setCursor(0,1);
lcd.print("temp2: ");
lcd.print(dsreadtemp(myds,dsaddr2, resolution));


@ColinR:
lcd.setCursor(0,3);
lcd.print("thanks 4 your snippet");

@TomWS: Didn't get your code up and running yet, as I just had the idea to convert the adresses manually, Colin's code does the job ;)