2 датчика ds18b20 на отдельные порты. Atmega32
Добавлено: Сб янв 13, 2018 13:33:04
Доброго времени суток! Есть проект на Atmega32 к холодильным системам. Нужно подключить несколько датчиков ds18b20 к контроллеру. Но!!!! Чтобы у каждого датчика был свой отдельный порт. Казалось бы, что проще в родной библиотеке переподключить , переназначить входные порты от ds18b20. А нет. Оказывается так не работает.
Этот кусок программы наверное часто встречали.
Код:
//определяем порт и бит к которому подключён датчик
#define OWI_PORT PORTD
#define OWI_DDR DDRD
#define OWI_PIN PIND
#define OWI_BIT 4
Вот код, с одним датчиком работает прекрасно.
Код:
#include <avr/io.h>
#define F_CPU 8000000UL
#include <stdlib.h>
#include <util/delay.h> //èñïîëüçóåì ñòàíäàðòíóþ ïðîöåäóðó çàäåðæêè
#include <stdint.h>
#include <avr/interrupt.h>
unsigned char a,b,c,d,e,r,f,delta,buf_up,buf_down,d2,start,blok,blok1,r1,d1,d2,d3,temp_min,temper_d;
unsigned int time,buf_del,temperature;
unsigned int bufy,t_min,t_buf,minus,ds18_temp,ttd;
unsigned char blok1,blok2,blok,mode,blok_tem;
unsigned char c1,ee;
unsigned char pit,buf,blok_del,buff;
unsigned int temp,Temp,temper,Temp_L,Temp_H,bu,bd;
unsigned char x,blok1,blok2,blok3,blok4,blok5,blok6;
unsigned char v1,v2,v3,v4,a1,a2,a3,a1,a2,a3,t1,t2,t3,t4;
char blok_zum,blok_zum1,blok_zum2;
unsigned char g,acp,d,np,p,p1,p2,p3,p4,skor_l,perehod;
unsigned char s,cikl,razn_l,st;
unsigned char e,term;
unsigned int bt,bt1,bt2,buf_t,stop_a,aad,ad,v,vob,vv3,vv4,vvd,vd,baad;
unsigned int temperatura,temper,zer,zer1,zer2;
unsigned char v11,v12,v13,v21,v22,v23,v31,v32,v33,v41,v42,v43;
unsigned char kol_pusk,dlit_pusk,dlit_pauz,alarm,n,min,sec;
unsigned int msec,bsec,knop;
#define SKIP_ROM 0xCC
#define CONVERT_T 0x44
#define READ_SCRATCHPAD 0xBE
#define WRITE_SCRATCHPAD 0x4E
#define COPY SCRATCHPAD 0x48
#define OWI_PORT PORTD
#define OWI_DDR DDRD
#define OWI_PIN PIND
Can1()
{
#define OWI_BIT 5
PORTA &=~_BV(PA1);
PORTA |= _BV(PA2);
}
Can2()
{
#define OWI_BIT 4
PORTA &=~_BV(PA2);
PORTA |= _BV(PA1);
}
#define OWI_LOW OWI_DDR |= 1<<OWI_BIT
#define OWI_HIGH OWI_DDR &= ~(1<<OWI_BIT)
char OWI_find(void)
{
char SR0=SREG;
cli();
char device;
OWI_LOW;
_delay_us(480);
OWI_HIGH;
_delay_us(65);
if((OWI_PIN & (1<<OWI_BIT)) ==0x00)
device = 1;
else
device = 0;
SREG=SR0;
_delay_us(480);
return device;
}
void OWI_write_bit (char bit)
{
char SR1=SREG;
cli();
OWI_LOW;
_delay_us(2);
if(bit) OWI_HIGH;
_delay_us(65);
OWI_HIGH;
SREG=SR1;
}
void OWI_write_byte(unsigned char c)
{
char i;
for(i = 0; i < 8; i++)
{
if((c & (1<<i)) == 1<<i)
OWI_write_bit(1);
else
OWI_write_bit(0);
}
}
char OWI_read_bit (void)
{
char SR2=SREG;
cli();
char OWI_rbit;
OWI_LOW;
_delay_us(2);
OWI_HIGH;
_delay_us(13);
OWI_rbit=(OWI_PIN & (1<<OWI_BIT))>>OWI_BIT;
_delay_us(45);
SREG=SR2;
return OWI_rbit;
}
unsigned char OWI_read_byte()
{
char data=0,i;
for(i = 0; i < 8; i++)
data|= OWI_read_bit()<<i;
return data;
}
int temp_18b20()
{
unsigned char B;
unsigned int ds18_temp=0;
if(OWI_find()==1)
{
OWI_write_byte(SKIP_ROM);
OWI_write_byte(CONVERT_T);
_delay_ms(5);
OWI_find();
OWI_write_byte(SKIP_ROM);
if(ee==0)
{
OWI_write_byte(WRITE_SCRATCHPAD);
OWI_write_byte(READ_SCRATCHPAD);
}
ee=1;
OWI_write_byte(READ_SCRATCHPAD);
Temp_L=OWI_read_byte();
Temp_H=OWI_read_byte();
ds18_temp = (Temp_H<<8)|Temp_L;
temperature=ds18_temp;
t_buf=temperature;
t_buf=t_buf>>11;
t_min=t_buf&1;
minus=t_min;
if(minus==1)
{
temperature=~temperature;
}
temp=temperature>>4;
Temp=temperature&15;
temp_min=((Temp * 10) / 16);
ds18_temp=temp;
}
return ds18_temp;
}
char convert (unsigned int td)
{
char dat=td>>0;
return dat;
}
//********************************
int main (void)
{
DDRC=255;
DDRD=0b11000000;
DDRB=0;
DDRA=0b11111110;
while(1)
{
buf++;
if(buf==1)
{
Can1();
_delay_ms(10);
}
else if(buf==125)
{
Can2();
_delay_ms(10);
}
v=convert(temp_18b20());
}
}
Так вот что происходит. По условию, переменная buf изменяется и переключаются между собой функции Can1(), Can2(). А вот входные порты "4" и "5" для работы с датчиком, не переназначаются. И не понятно почему в данном коде именно BIT 4 работает? Или я подозреваю следующее, что компилятору без разницы где находится строчка #define. поэтому последним он увидел строчку #define OWI_BIT 4 которая относится именно к портам подключения. Поэтому его и подключил. Как правильно переподключить порты между собой? Заранее спасибо.
Этот кусок программы наверное часто встречали.
Код:
//определяем порт и бит к которому подключён датчик
#define OWI_PORT PORTD
#define OWI_DDR DDRD
#define OWI_PIN PIND
#define OWI_BIT 4
Вот код, с одним датчиком работает прекрасно.
Код:
#include <avr/io.h>
#define F_CPU 8000000UL
#include <stdlib.h>
#include <util/delay.h> //èñïîëüçóåì ñòàíäàðòíóþ ïðîöåäóðó çàäåðæêè
#include <stdint.h>
#include <avr/interrupt.h>
unsigned char a,b,c,d,e,r,f,delta,buf_up,buf_down,d2,start,blok,blok1,r1,d1,d2,d3,temp_min,temper_d;
unsigned int time,buf_del,temperature;
unsigned int bufy,t_min,t_buf,minus,ds18_temp,ttd;
unsigned char blok1,blok2,blok,mode,blok_tem;
unsigned char c1,ee;
unsigned char pit,buf,blok_del,buff;
unsigned int temp,Temp,temper,Temp_L,Temp_H,bu,bd;
unsigned char x,blok1,blok2,blok3,blok4,blok5,blok6;
unsigned char v1,v2,v3,v4,a1,a2,a3,a1,a2,a3,t1,t2,t3,t4;
char blok_zum,blok_zum1,blok_zum2;
unsigned char g,acp,d,np,p,p1,p2,p3,p4,skor_l,perehod;
unsigned char s,cikl,razn_l,st;
unsigned char e,term;
unsigned int bt,bt1,bt2,buf_t,stop_a,aad,ad,v,vob,vv3,vv4,vvd,vd,baad;
unsigned int temperatura,temper,zer,zer1,zer2;
unsigned char v11,v12,v13,v21,v22,v23,v31,v32,v33,v41,v42,v43;
unsigned char kol_pusk,dlit_pusk,dlit_pauz,alarm,n,min,sec;
unsigned int msec,bsec,knop;
#define SKIP_ROM 0xCC
#define CONVERT_T 0x44
#define READ_SCRATCHPAD 0xBE
#define WRITE_SCRATCHPAD 0x4E
#define COPY SCRATCHPAD 0x48
#define OWI_PORT PORTD
#define OWI_DDR DDRD
#define OWI_PIN PIND
Can1()
{
#define OWI_BIT 5
PORTA &=~_BV(PA1);
PORTA |= _BV(PA2);
}
Can2()
{
#define OWI_BIT 4
PORTA &=~_BV(PA2);
PORTA |= _BV(PA1);
}
#define OWI_LOW OWI_DDR |= 1<<OWI_BIT
#define OWI_HIGH OWI_DDR &= ~(1<<OWI_BIT)
char OWI_find(void)
{
char SR0=SREG;
cli();
char device;
OWI_LOW;
_delay_us(480);
OWI_HIGH;
_delay_us(65);
if((OWI_PIN & (1<<OWI_BIT)) ==0x00)
device = 1;
else
device = 0;
SREG=SR0;
_delay_us(480);
return device;
}
void OWI_write_bit (char bit)
{
char SR1=SREG;
cli();
OWI_LOW;
_delay_us(2);
if(bit) OWI_HIGH;
_delay_us(65);
OWI_HIGH;
SREG=SR1;
}
void OWI_write_byte(unsigned char c)
{
char i;
for(i = 0; i < 8; i++)
{
if((c & (1<<i)) == 1<<i)
OWI_write_bit(1);
else
OWI_write_bit(0);
}
}
char OWI_read_bit (void)
{
char SR2=SREG;
cli();
char OWI_rbit;
OWI_LOW;
_delay_us(2);
OWI_HIGH;
_delay_us(13);
OWI_rbit=(OWI_PIN & (1<<OWI_BIT))>>OWI_BIT;
_delay_us(45);
SREG=SR2;
return OWI_rbit;
}
unsigned char OWI_read_byte()
{
char data=0,i;
for(i = 0; i < 8; i++)
data|= OWI_read_bit()<<i;
return data;
}
int temp_18b20()
{
unsigned char B;
unsigned int ds18_temp=0;
if(OWI_find()==1)
{
OWI_write_byte(SKIP_ROM);
OWI_write_byte(CONVERT_T);
_delay_ms(5);
OWI_find();
OWI_write_byte(SKIP_ROM);
if(ee==0)
{
OWI_write_byte(WRITE_SCRATCHPAD);
OWI_write_byte(READ_SCRATCHPAD);
}
ee=1;
OWI_write_byte(READ_SCRATCHPAD);
Temp_L=OWI_read_byte();
Temp_H=OWI_read_byte();
ds18_temp = (Temp_H<<8)|Temp_L;
temperature=ds18_temp;
t_buf=temperature;
t_buf=t_buf>>11;
t_min=t_buf&1;
minus=t_min;
if(minus==1)
{
temperature=~temperature;
}
temp=temperature>>4;
Temp=temperature&15;
temp_min=((Temp * 10) / 16);
ds18_temp=temp;
}
return ds18_temp;
}
char convert (unsigned int td)
{
char dat=td>>0;
return dat;
}
//********************************
int main (void)
{
DDRC=255;
DDRD=0b11000000;
DDRB=0;
DDRA=0b11111110;
while(1)
{
buf++;
if(buf==1)
{
Can1();
_delay_ms(10);
}
else if(buf==125)
{
Can2();
_delay_ms(10);
}
v=convert(temp_18b20());
}
}
Так вот что происходит. По условию, переменная buf изменяется и переключаются между собой функции Can1(), Can2(). А вот входные порты "4" и "5" для работы с датчиком, не переназначаются. И не понятно почему в данном коде именно BIT 4 работает? Или я подозреваю следующее, что компилятору без разницы где находится строчка #define. поэтому последним он увидел строчку #define OWI_BIT 4 которая относится именно к портам подключения. Поэтому его и подключил. Как правильно переподключить порты между собой? Заранее спасибо.