OneWire Controller for the Basic Stamp, PICAXE and Arduino


Introduction.

Popular processors such as the Basic Stamp 2 (BS2-IC) and the PICAXE series fetch each command from memory, decode it and then execute it. Thus, they are too slow to meet the stringent requirements required for interfacing with the Dallas 1-W family of devices.

The ONEWIRE Controller permits a conventional Basic Stamp, PICAXE or similar to interface with up to seven Dallas 1-wire devices, with each device on a separate run. Communication between the Stamp and the ONEWIRE Controller uses RS232 serial communication. The baud rate may be set to either 9600 or to 2400 for the PICAXE with a strap.

This design permits the hobbyist to interface with any Dallas 1-wire device including DS18S20, DS18B20, DS1822 temperature sensors, DS2438 temperature and A/D, DS2423 dual 32-bit counter and DS2450 Quad 16-bit A/D.

Each of the seven channels accommodates one Dallas 1-W devices. This design does not support multiple devices on the same channel.

The design consists of a single programmed PIC (14-pin DIP). It is shipped as a kit which includes seven 4.7K resistors used as pullup resistors on each of the 1-wire channels, a status LED, lengths of 22 awg solid suitable for use with a solder less breadboard and a schematic.


This design is now available as a kit. $14.95. See below

Command Set.

The Stamp's command set for interfacing with Dallas 1-W devices is minimal;

Note that the Dallas 1-W channels are 0 through 6.

These commands are then used to interface with virtually any Dallas 1-W device.

The following segment of Basic Stamp 2 code illustrates how these commands may be used to perform a temperature measurement using a DS18B20. The complete routine appears at the bottom of this discussion.

    SEROUT 8, BaudMode, 10, ["P0", "W0cc", "S044"]  'perform temp meas
                                           ' note strong pullup
    PAUSE 1100          ' wait for conversion to complete

    SEROUT 8, BaudMode, 10, ["P0", "W0cc", "W0be"]   ' send temperature data

    SEROUT 8, BaudMode, 10, ["R0"]   ' fetch data
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.LOWBYTE]
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R0"]   ' fetch data
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.HIGHBYTE]
    PAUSE 100

The design includes a status LED which blips about every second to indicate the processor is alive and running. It rapidly flashes a number of times to indicate data is being sent to the Stamp.

A source of +5 VDC is required. The current drain is less than 10 mA.


			+5 VDC -------  ONEWIRE         LED ---------->|--- GRD
			GRD ----------  CONTROLLER
			                                0 -------- To Dallas 1-W devices
			BAUD ---------                  1 --------
			RX ---------->                  2 --------
			TX <----------               3 --------
                                            4 --------
            /MCLR --------                  5 --------
                                            6 --------

Baud - Open for 9600 baud, Ground for 2400
/MCLR - Momentarily ground to reset

Routines to interface with a DS18B20 temperature sensor, DS2438 temperature sensors and A/D and DS2423 Dual Counter for the Basic Stamp and the PICAXE-18X appear below.

An excellent tutorial with sample code for the Arduino appears at http://sheepdogguides.com/arduino/asw1onew1.htm.


Basic Stamp (BS2) Routines

DS18B20_1.BS2

' {$STAMP BS2}
' {$PBASIC 2.5}
' DS18B20_1.BS2  (Basic Stamp 2)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with a DS18B20 on
' Channel 0.
'
' BS2-IC                          ONEWIRE PIC       +5 VDC
'                                                    |
' P8 (term 13) -----------------> "RX" (term 5)     4.7K        DS18B20
' P7 (term 12) <----------------- "TX" (term 6)      |
'                                 "0" (term 13) ----------------- DQ (term 2)
'                        OPEN --- "BAUD"                 GRD ---- (term 1)
'                                                        GRD ---- (term 3)
'
' 9600 baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06


    BaudMode  CON  84          '9600 True

    X VAR Word
    Y VAR Word
    SignBit VAR Byte
    Whole VAR Byte
    Fract VAR Byte

    DIR7 = 0  ' serial input
    DIR8 = 1  ' serial output
    OUT8 = 0  ' be sure SerOut pin is stable at zero
    PAUSE 1000

  DO
AGN:
    SEROUT 8, BaudMode, 10, ["P0", "W0cc", "S044"]  'perform temp meas
                                           ' note strong pullup
    PAUSE 1100          ' wait for conversion to complete

    SEROUT 8, BaudMode, 10, ["P0", "W0cc", "W0be"]   ' send temperature data

    SEROUT 8, BaudMode, 10, ["R0"]   ' fetch data
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.LOWBYTE]
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R0"]   ' fetch data
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.HIGHBYTE]
    PAUSE 100
    ' now do the calculations
    SignBit = X / 256 / 128
    IF SignBit = 1 THEN ' its negative
       X = X ^ $ffff + 1 ' take the two's comp
    ENDIF
    ' multiply by 6.25 - This is 100 * Tc
    Y = X / 4   ' 0.25
    X = X * 6 + Y
    Whole = X / 100
    Fract = X // 100
    IF SignBit = 1 THEN
       DEBUG "-", DEC Whole, ".", DEC2 Fract, CR
    ELSE
       DEBUG DEC Whole, ".", DEC2 Fract, CR
    ENDIF

    PAUSE 3000 ' wait 3 secs

  LOOP

TimeOut:
    DEBUG "Timeout Error", CR
    GOTO AGN

DS2438_1.BS2

' {$STAMP BS2}
' {$PBASIC 2.5}
' DS2438_1.BS2  (Basic Stamp 2)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with a DS2438 A/D and Temperature
' sensor ON Channel 2.
'
' Measures and displays Vdd, Vad and Tc.
'
' BS2-IC                          ONEWIRE PIC                  DS2438
'
' P8 (term 13) -----------------> "RX" (term 5)          +5 VDC --- Vdd (term 5)
' P7 (term 12) <----------------- "TX" (term 6)          GRD ------ GRD (term 1)
'                                 "2" (term 3)  ---------***----- DQ (term 8)
'                      OPEN ----- "BAUD"              Vsensor --- Vad (term 4)
'
' 9600 Baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06


    BaudMode  CON    84        '9600 True

    N VAR Byte
    X VAR Word
    Y VAR Word
    SignBit VAR Byte
    Whole VAR Byte
    Fract VAR Byte

    VSource VAR Byte

    DIR7 = 0  ' serial input
    DIR8 = 1  ' serial output
    OUT8 = 0  ' be sure SerOut pin is stable at zero
    PAUSE 1000

  DO
    VSource = 0    ' Vdd
    GOSUB MeasVoltage
    VSource = 1    ' Vad
    GOSUB MeasVoltage
    GOSUB MeasTemp

    PAUSE 5000
  LOOP

MeasVoltage:
    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W24e", "W200"]   ' setup for Vdd  or A/D

    IF VSource = 0 THEN
        SEROUT 8, BaudMode, 10, ["W208"] '
    ELSE
        SEROUT 8, BaudMode, 10, ["W200"] '
    ENDIF

    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W2b4"]  '  perform A/D

    PAUSE 1000    ' wait for A/D to complete

    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W2b8", "W200"]  '  recall to scratchpad
    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W2be", "W200"]  '  read scratchpad

    FOR N = 1 TO 3
       PAUSE 100
       SEROUT 8, BaudMode, 10, ["R2"] '
    NEXT

    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R2"] '
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.LOWBYTE]
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R2"] '
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.HIGHBYTE]
    PAUSE 100

    ' now do the calculations

    Whole = X / 100
    Fract = X // 100

    IF VSource = 0 THEN
       DEBUG "Vdd = ", DEC Whole, ".", DEC2 Fract, CR
    ELSE
       DEBUG "Vad = ", DEC Whole, ".", DEC2 Fract, CR
    ENDIF

    RETURN

MeasTemp:

    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W24e", "W200"]  ' setup for temperature meas
    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W244"]  '  perform temp measurement

    PAUSE 1000

    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W2b8", "W200"]  '  recall to scratchpad
    SEROUT 8, BaudMode, 10, ["P2", "W2cc", "W2be", "W200"]  '  read scratchpad

    SEROUT 8, BaudMode, 10, ["R2"] '
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R2"] '
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.LOWBYTE] ' byte 2
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R2"] '          ' byte 3
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.HIGHBYTE]
    PAUSE 100

    ' now do the calculations
    signbit = X / 256 / 128
    IF SignBit = 1 THEN ' its negative
       X = X ^ $ffff + 1 ' take the two's comp
    ENDIF

    X = X / 8

    ' multiply by 3.125 - This is 100 * Tc
    Y = X / 8   ' 0.125
    X = X * 3 + Y
    Whole = X / 100
    Fract = X // 100

    DEBUG "Tc = "
    IF SignBit = 1 THEN
       DEBUG "-", DEC Whole, ".", DEC2 Fract, CR
    ELSE
       DEBUG DEC Whole, ".", DEC2 Fract, CR
    ENDIF

    RETURN

TimeOut:
    DEBUG "Timeout Error", CR
    RETURN

DS2423_1.BS2

' {$STAMP BS2}
' {$PBASIC 2.5}
' DS18B20_1.BS2  (Basic Stamp 2)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with a DS2423 Dual 32-bit
' counter on Channel 1.
'
' BS2-IC                          ONEWIRE PIC                    DS2423
'
' P8 (term 13) -----------------> "RX" (term 5)
' P7 (term 12) <----------------- "TX" (term 6)            GRD ---- GRD (term 1)
'                                 "1" -------------------***------- DQ (term 2)
'                      OPEN ----- "BAUD"                 +5 VDC --- Vdd (term 3)
'
' 9600 Baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06


    BaudMode  CON  84          '9600 True

    N VAR Byte
    X VAR Word
    Y VAR Word

    CounterNum VAR Byte


    DIR7 = 0  ' serial input
    DIR8 = 1  ' serial output
    OUT8 = 0  ' be sure SerOut pin is stable at zero
    PAUSE 1000

  DO
    CounterNum = 0
    GOSUB ReadCounter
    DEBUG "Counter 0 = ", HEX4 Y, " ", HEX4 X, CR
    CounterNum = 1
    GOSUB ReadCounter
    DEBUG "Counter 1 = ", HEX4 Y, " ", HEX4 X, CR
    PAUSE 3000
  LOOP

ReadCounter:
    SEROUT 8, BaudMode, 10, ["P1", "W1cc", "W1a5"]
    IF CounterNum = 0 THEN
       SEROUT 8, BaudMode, 10, ["W1c0"]
    ELSE
       SEROUT 8, BaudMode, 10, ["W1e0"]
    ENDIF

    SEROUT 8, BaudMode, 10, ["W101"]

    FOR N = 1 TO 32
       SEROUT 8, Baudmode, 10, ["R1"]
       PAUSE 100
    NEXT


    SEROUT 8, BaudMode, 10, ["R1"]   ' fetch data
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.LOWBYTE]
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R1"]
    SERIN 7, Baudmode, 1500, TimeOut, [DEC X.HIGHBYTE]
    PAUSE 100

    SEROUT 8, BaudMode, 10, ["R1"]
    SERIN 7, Baudmode, 1500, TimeOut, [DEC Y.LOWBYTE]
    PAUSE 100
    SEROUT 8, BaudMode, 10, ["R1"]
    SERIN 7, Baudmode, 1500, TimeOut, [DEC Y.HIGHBYTE]
    PAUSE 100

    RETURN

TimeOut:
    DEBUG "Timeout Error", CR
    RETURN


PICAXE-18X Routines.

DS18B20_1.BAS

' DS18B20_1.BAS  (PICAXE-18X)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with DS18B20s on
' on Channels 0, 4 and 5.
'
' PICAXE-18X                        ONEWIRE PIC       +5 VDC
'                                                      |
' Out0 (term 6) ----------------> "RX" (term 5)     4.7K        DS18B20
' In0 (term 15) <---------------- "TX" (term 6)      |
'                                 "0" (term 13) ----------------- DQ (term 2)
'                        GRD --- "BAUD"                 GRD ---- (term 1)
'                                                       GRD ---- (term 3)
'
'                                        (DS18B20s also on Channels 4 and 5)
' 2400 baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06


    Symbol H = B0
    Symbol L = B1
    Symbol SignBit = B2
    Symbol Chan = B3
    Symbol X = W2
    Symbol Y = W3

    Symbol Whole = B8
    Symbol Fract = B9


    High 1		' Be sure Tx Pin is idle for some time
    Pause 5000	' wait for PICAXE LCD to boot

Top:
    Chan = 0
    GoSub MeasTemp	' measures and displays temperature
    Chan = 4
    GoSub MeasTemp
    Chan = 5
    GoSub MeasTemp
    Pause 3000
    Goto Top

MeasTemp:

    SerOut 0, T2400, ("P", #Chan, "W", #Chan, "cc", "S", #Chan, "44")  'perform temp meas
                                    ' note strong pullup
    Pause 1100          ' wait for conversion to complete

    SerOut 0, T2400, ("P", #Chan, "W", #Chan, "cc", "W", #Chan, "be")   ' send temperature data

    SerOut 0, T2400, ("R", #Chan)   ' fetch data
    SerIn 0, T2400, #L
    Pause 100
    SerOut 0, T2400, ("R", #Chan)   ' fetch data
    SerIn 0, T2400, #H
    Pause 100

    ' now do the calculations
    X = H
    X = X * 256 + L

    SignBit = X / 256 / 128
    IF SignBit = 1 THEN ' its negative
       X = X ^ $ffff + 1 ' take the two's comp
    ENDIF
    ' multiply by 6.25 - This is 100 * Tc
    Y = X / 4   ' 0.25
    X = X * 6 + Y
    Whole = X / 100
    Fract = X // 100

    SerTxD (#Chan, " ")

    If SignBit = 1 Then
       SerTxD ("-")
    EndIf
    GoSub DisplayDec
    Return

DisplayDec:
    SerTxD (#Whole, ".")
    If Fract < 10 Then
       SerTxD ("0", #Fract)
    Else
       SerTxD (#Fract)
    EndIf
    SerTxD (10, 13)
    Return

DS2438_1.BAS

' DS2438_1.BAS  (PICAXE-18X)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with a DS2438 A/D and Temperature
' sensor ON Channel 2.
'
' Measures and displays Vdd, Vad and Tc.
'
' PICAXE-18X                      ONEWIRE PIC                  DS2438
'
' Out0 (term 6) ----------------> "RX" (term 5)          +5 VDC --- Vdd (term 5)
' In0 (term 15) <----------------- "TX" (term 6)          GRD ------ GRD (term 1)
'                                 "2" (term 3)  ---------***----- DQ (term 8)
'                      GRD ----- "BAUD" (term 11)     Vsensor --- Vad (term 4)
'
' 2400 Baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06


    Symbol H = B0
    Symbol L = B1
    Symbol N = B2
    Symbol SignBit = B3
    Symbol X = W2
    Symbol Y = W3
    Symbol Whole = B8
    Symbol Fract = B9
    Symbol Vsource = B10


    High 1		' Be sure Tx Pin is idle for some time
    Pause 5000		' wait for PICAXE LCD to boot


Top:

    VSource = 0    ' Vdd
    GOSUB MeasVoltage
    VSource = 1    ' Vad
    GOSUB MeasVoltage
    GOSUB MeasTemp

    PAUSE 500
    Goto Top:

MeasVoltage:

    SerOut 0, T2400, ("P2", "W2cc", "W24e", "W200")

    If VSource = 0 Then
        SerOut 0, T2400,  ("W208")
    Else
        SerOut 0, T2400, ("W200")
    EndIf

    SerOut 0, T2400, ("P2", "W2cc", "W2b4")  '  perform A/D

    Pause 1100    ' wait for A/D to complete

    SerOut 0, T2400, ("P2", "W2cc", "W2b8", "W200")  '  recall to scratchpad
    SerOut 0, T2400, ("P2", "W2cc", "W2be", "W200")  '  read scratchpad

    For N = 1 TO 3
        SerOut 0, T2400, ("R2")
        Pause 100
    Next


    SerOut 0, T2400, ("R2")
    SerIn 0, T2400, #L
    Pause 100
    SerOut 0, T2400, ("R2")
    SerIn 0, T2400, #H
    Pause 100

    X = H
    X = X * 256 + L
    Whole = X / 100
    Fract = X % 100

    If VSource = 0 Then
       SerTxD ("Vdd = ")
    Else
       SerTxD ("Vad = ")
    EndIf
    GoSub DisplayDec

    Return

MeasTemp:

    SerOut 0, T2400, ("P2", "W2cc", "W24e", "W200")  ' setup for temperature meas
    SerOut 0, T2400, ("P2", "W2cc", "W244")  '  perform temp measurement

    Pause 1000

    SerOut 0, T2400, ("P2", "W2cc", "W2b8", "W200")  '  recall to scratchpad
    SerOut 0, T2400, ("P2", "W2cc", "W2be", "W200")  '  read scratchpad

    SerOut 0, T2400, ("R2") '
    Pause 100
    SerOut 0, T2400, ("R2") '
    SerIn 0, T2400, #L ' byte 2
    Pause 100
    SerOut 0, T2400, ("R2") ' byte 3
    SerIn 0, T2400, #H
    Pause 100

    ' now do the calculations
    X = H
    X = X * 256 + L
    signbit = X / 256 / 128
    If SignBit = 1 Then ' its negative
       X = X ^ $ffff + 1 ' take the two's comp
    EndIf

    X = X / 8

    ' multiply by 3.125 - This is 100 * Tc
    Y = X / 8   ' 0.125
    X = X * 3 + Y
    Whole = X / 100
    Fract = X // 100

    SerTxD ("Tc = ")
    If SignBit = 1 Then
       SerTxD ("-")
    EndIf

    GoSub DisplayDec

    Return

DisplayDec:
    SerTxD (#Whole, ".")
    If Fract < 10 Then
       SerTxD ("0", #Fract)
    Else
       SerTxD (#Fract)
    EndIf
    SerTxD (10, 13)
    Return

DS2423_1.BAS

' DS18B20_1.BS2  (PICAXE-18X)
'
' Illustrates the use of the ONEWIRE PIC in interfacing with a DS2423 Dual 32-bit
' counter on Channel 1.
'
' BS2-IC                          ONEWIRE PIC                    DS2423
'
' Out0 (term 6) ----------------> "RX" (term 5)
' In0 (term 15) <---------------- "TX" (term 6)            GRD ---- GRD (term 1)
'                                 "1" -------------------***------- DQ (term 2)
'                      GRD ----- "BAUD"                 +5 VDC --- Vdd (term 3)
'
' 2400 Baud.
'
' Copyright, Peter H. Anderson, Baltimore, MD, Nov 14, '06

    Symbol H = B0
    Symbol L = B1
    Symbol N = B2
    Symbol CounterNum = B3
    Symbol X = W2
    Symbol Y = W3


    High 1		' Be sure Tx Pin is idle for some time
    Pause 5000	' wait for PICAXE LCD to boot


Top:

    CounterNum = 0
    GoSub ReadCounter
    CounterNum = 1
    GoSub ReadCounter
    Pause 3000
    Goto Top:


ReadCounter:

    SerOut 0, T2400, ("P1", "W1cc", "W1a5")
    If CounterNum = 0 Then
       SerOut 0, T2400, ("W1c0")
    Else
       SerOut 0, T2400, ("W1e0")
    EndIf

    SerOut 0, T2400, ("W101")

    For N = 1 to 32
       SerOut 0, T2400, ("R1")
       Pause 100
    Next

    SerOut 0, T2400, ("R1")   ' fetch data
    SerIn 0, T2400, #L
    Pause 100
    SerOut 0, T2400, ("R1")
    SerIn 0, T2400, #H
    Pause 100

    X = H
    X = X * 256 + L

    SerOut 0, T2400, ("R1")
    SerIn 0, T2400, #L
    Pause 100
    SerOut 0, T2400, ("R1")
    SerIn 0, T2400, #H
    Pause 100

    Y = H
    Y = Y * 256 + L

    SerTxD (#CounterNum, " ", #Y, "  ", #X, 10, 13)

    Return