/*****************************************************************************
**
** 1_wire.h
** functions of 1wire sensors
**
*****************************************************************************/
#define TRUE 1
#define FALSE 0
#define OUT 1
#define IN 0
#ifndef PORTS_DQ
#define PORTS_DQ 1
#define DQ_RX PTAD_PTAD0
#define DQ_TX PTAD_PTAD1
#define DIR_DQRX 0
#define DIR_DQTX 1
#endif
/*****************************************************************************
** void delay 2 us
*****************************************************************************/
void delay_2us(unsigned int n);
/*****************************************************************************
** principal functions
*****************************************************************************/
/* ow_reset function return if there any sensor*/
unsigned char ow_reset(void);
/* read bit functions*/
unsigned char read_bit(void);
/* write bit*/
void write_bit(unsigned char);
/*read byte*/
unsigned char read_byte(void);
/* first */
unsigned char First(void);
/*next*/
unsigned char Next(void);
void ow_scan(void);
void ow_select(char);
/*ow search*/
char ow_search(void);
/*ow verify*/
char ow_verify(void);
/*ow_crc algorithm*/
unsigned char docrc8(unsigned char);
/*****************************************************************************
** principal functions
** DS18S20
**
*****************************************************************************/
int ds1820_temperatureX2(char);/******************************************************************************
**
** 1_wire.c
** DEFINITIONS FUNCTIONS
** braulio elias chi salavarria
******************************************************************************/
#include "derivative.h"
#include "1_wire.h"
static unsigned char dscrc_table[] = {
0, 94,188,226, 97, 63,221,131,194,156,126, 32,163,253, 31, 65,
157,195, 33,127,252,162, 64, 30, 95, 1,227,189, 62, 96,130,220,
35,125,159,193, 66, 28,254,160,225,191, 93, 3,128,222, 60, 98,
190,224, 2, 92,223,129, 99, 61,124, 34,192,158, 29, 67,161,255,
70, 24,250,164, 39,121,155,197,132,218, 56,102,229,187, 89, 7,
219,133,103, 57,186,228, 6, 88, 25, 71,165,251,120, 38,196,154,
101, 59,217,135, 4, 90,184,230,167,249, 27, 69,198,152,122, 36,
248,166, 68, 26,153,199, 37,123, 58,100,134,216, 91, 5,231,185,
140,210, 48,110,237,179, 81, 15, 78, 16,242,172, 47,113,147,205,
17, 79,173,243,112, 46,204,146,211,141,111, 49,178,236, 14, 80,
175,241, 19, 77,206,144,114, 44,109, 51,209,143, 12, 82,176,238,
50,108,142,208, 83, 13,239,177,240,174, 76, 18,145,207, 45,115,
202,148,118, 40,171,245, 23, 73, 8, 86,180,234,105, 55,213,139,
87, 9,235,181, 54,104,138,212,149,203, 41,119,244,170, 72, 22,
233,183, 85, 11,136,214, 52,106, 43,117,151,201, 74, 20,246,168,
116, 42,200,150, 21, 75,169,247,182,232, 10, 84,215,137,107, 53};
unsigned char components[5][8]; // table that contain all code ROM of components available
// just 5 components
// 0 1 2 3 4 5 6 7
// composant[0] : XX XX XX XX XX XX XX XX ROM code of component index 0
// composant[1] : XX XX XX XX XX XX XX XX ROM code of component index 1
// composant[2] : XX XX XX XX XX XX XX XX ROM code of component index 2
// composant[3] : XX XX XX XX XX XX XX XX ROM code of component index 3
// composant[4] : XX XX XX XX XX XX XX XX ROM code of component index 4
/******************************************************************************
**
** VARIABLES EXTERNS
**
******************************************************************************/
// global search state
unsigned char nb_components;
unsigned char ROM_NO[8];
unsigned char LastDiscrepancy;
unsigned char LastFamilyDiscrepancy;
unsigned char LastDeviceFlag;
unsigned char crc8;
/******************************************************************************
**
** definitions delay_us functions
******************************************************************************/
void delay_2us(unsigned int n)
{
asm {
LDHX (n)
LOOP1: AIX #-1 ;[2]
NOP
NOP
CPHX #0 ;[3]
BNE LOOP1 ;[3]
}
}
/*****************************************************************************
**
** unsigned char ow_reset(void) fundamentals for communications sensor
*****************************************************************************/
unsigned char ow_reset(void)
{
unsigned char presence;
DQ_TX=0; //reset sensor
delay_2us(235); //delay 470 us
DQ_TX=1; //high again
delay_2us(30);//delay 60 us
presence= DQ_RX;
delay_2us(230); //delay ~_ 470 us
return presence;
}
/*****************************************************************************
**
** unsigned char read_bit(void)
** reads a bit from the one-wire bus. The delay
** required for a read is 15us
*****************************************************************************/
unsigned char read_bit(void){
unsigned char i;
DQ_TX=0; //
delay_2us(1);
DQ_TX=1;
delay_2us(7);//delay for 16 us
i=DQ_RX;
delay_2us(22);//delay for 44 us
return i;
}
/*****************************************************************************
**
** unsigned char write_bit(void)
** writes a bit to the one-wire bus, passed in bitval.
*****************************************************************************/
void write_bit(unsigned char bit){
if(bit){
DQ_TX=0;
delay_2us(1); //delay for 2 us
DQ_TX=1;
delay_2us(15);
}else{
DQ_TX=0;
delay_2us(15);//delay for 30us
DQ_TX=1;
delay_2us(1);
}
}
/*****************************************************************************
**
** unsigned char read_byte(void)
**
*****************************************************************************/
unsigned char read_byte(void){
unsigned char i;
unsigned char value=0;
for (i=0;i<8;i++){
if(read_bit()){value|=0x01<<i;}
}
return value;
}
/*****************************************************************************
**
** void write_byte(unsigned char);
**
*****************************************************************************/
void write_byte(unsigned char value){
unsigned char i, temp;
for(i=0;i<8;i++){
temp=value>>i;
temp&=0x01;
write_bit(temp);
}
}
/*****************************************************************************
**
** ONE WIRE CRC
**
*****************************************************************************/
unsigned char docrc8(unsigned char value){
crc8=dscrc_table[crc8^value];
return crc8;
}
/*****************************************************************************
**
** FIRST
**
*****************************************************************************/
unsigned char First(void){
// reset the search state
LastDiscrepancy = 0;
LastDeviceFlag = FALSE;
LastFamilyDiscrepancy = 0;
return ow_search();
}
/*****************************************************************************
**
** ow_scan
**
*****************************************************************************/
void ow_scan(void){
char a;
a=First(); //in search for the fist component on the bus
nb_components=a;
while(a){
a=Next(); // new search
nb_components += a;
}
}
/*****************************************************************************
**
** Next
**
*****************************************************************************/
unsigned char Next(void){
return ow_search();
}
/*****************************************************************************
**
** ow search
**
*****************************************************************************/
char ow_search(){
unsigned char id_bit_number;
unsigned char last_zero, rom_byte_number;
unsigned char search_result;
unsigned char id_bit, cmp_id_bit;
unsigned char rom_byte_mask, search_direction;
// initialize for search
id_bit_number = 1;
last_zero = 0;
rom_byte_number = 0;
rom_byte_mask = 1;
search_result = 0;
crc8 = 0;
// if the last call was not the last one
if (!LastDeviceFlag)
{
// 1-Wire reset
if (!ow_reset())
{
// reset the search
LastDiscrepancy = 0;
LastDeviceFlag = FALSE;
LastFamilyDiscrepancy = 0;
return FALSE;
}
// issue the search command
write_byte(0xF0);
// loop to do the search
do
{
// read a bit and its complement
id_bit = read_bit();
cmp_id_bit = read_bit();
// check for no devices on 1-wire
if ((id_bit == 1) && (cmp_id_bit == 1))
break;
else
{
// all devices coupled have 0 or 1
if (id_bit != cmp_id_bit)
search_direction = id_bit; // bit write value for search
else
{
// if this discrepancy if before the Last Discrepancy
// on a previous next then pick the same as last time
if (id_bit_number < LastDiscrepancy)
search_direction = ((ROM_NO[rom_byte_number] & rom_byte_mask) > 0);
else
// if equal to last pick 1, if not then pick 0
search_direction = (id_bit_number == LastDiscrepancy);
// if 0 was picked then record its position in LastZero
if (search_direction == 0)
{
last_zero = id_bit_number;
// check for Last discrepancy in family
if (last_zero < 9)
LastFamilyDiscrepancy = last_zero;
}
}
// set or clear the bit in the ROM byte rom_byte_number
// with mask rom_byte_mask
if (search_direction == 1)
ROM_NO[rom_byte_number] |= rom_byte_mask;
else
ROM_NO[rom_byte_number] &= ~rom_byte_mask;
// serial number search direction write bit
write_bit(search_direction);
// increment the byte counter id_bit_number
// and shift the mask rom_byte_mask
id_bit_number++;
rom_byte_mask <<= 1;
// if the mask is 0 then go to new SerialNum byte rom_byte_number and reset mask
if (rom_byte_mask == 0)
{
docrc8(ROM_NO[rom_byte_number]); // accumulate the CRC
rom_byte_number++;
rom_byte_mask = 1;
}
}
}
while(rom_byte_number < 8); // loop until through all ROM bytes 0-7
// if the search was successful then
if (!((id_bit_number < 65) || (crc8 != 0)))
{
// search successful so set LastDiscrepancy,LastDeviceFlag,search_result
LastDiscrepancy = last_zero; // check for last device
if (LastDiscrepancy == 0)
LastDeviceFlag = TRUE;
search_result = TRUE;
}
}
// if no device found then reset counters so next 'search' will be like a first
if (!search_result || !ROM_NO[0])
{
LastDiscrepancy = 0;
LastDeviceFlag = FALSE;
LastFamilyDiscrepancy = 0;
search_result = FALSE;
}
return search_result;
}
/*****************************************************************************
**
** ow_verify
**
*****************************************************************************/
char ow_verify()
{
unsigned char rom_backup[8];
unsigned char i,rslt,ld_backup,ldf_backup,lfd_backup;
// keep a backup copy of the current state
for (i = 0; i < 8; i++)
rom_backup[i] = ROM_NO[i];
ld_backup = LastDiscrepancy;
ldf_backup = LastDeviceFlag;
lfd_backup = LastFamilyDiscrepancy;
// set search to find the same device
LastDiscrepancy = 64;
LastDeviceFlag = FALSE;
if (ow_search())
{
// check if same device found
rslt = TRUE;
for (i = 0; i < 8; i++)
{
if (rom_backup[i] != ROM_NO[i])
{
rslt = FALSE;
break;
}
}
}
else
rslt = FALSE;
// restore the search state
for (i = 0; i < 8; i++)
ROM_NO[i] = rom_backup[i];
LastDiscrepancy = ld_backup;
LastDeviceFlag = ldf_backup;
LastFamilyDiscrepancy = lfd_backup;
// return the result of the verify
return rslt;
}
/*****************************************************************************
**
** ow_select
**
*****************************************************************************/
void ow_select(char index_components){
char i;
if(!ow_reset()){ // enable all components
write_byte(0x55); //command MATCH ROM
for(i=0;i<8;i++) write_byte(components[index_components][i]); // about the send of the 64 bits of the component
}
}
/*****************************************************************************
**
** Read_Temperature(); from ds18s20
**
*****************************************************************************/
int ds1820_temperatureX2(char index_component){
char k;
unsigned char get[9];
int temp2=0;
if(components[index_component][0]!=0x10){
temp2=0xFFFF;
return temp2;
}
write_byte(0x44); //demand of conversion
delay_2us(1);
ow_select(index_component);
write_byte(0xBE); //demand the lecture of memory ds1820
for (k=0;k<9;k++){get[k]=read_byte();} //lecture scratchpad
temp2=get[1]<<8; //if get[1]=FF > temperature negative
//if get[1]=00 > temperature positive
if(get[1]){get[0]=(~get[0])+1;} //if negative
temp2|=get[0];
return temp2;
}