⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 18b20_multicultural_temperature.txt

📁 用单片机AVR得到多点温度
💻 TXT
字号:
#include <mega64.h>
#include <stdlib.h> 
#include <delay.h>



#define   DQ_pin    0
#define		DQ_H() 		PORTF|=(1<<DQ_pin)	
#define		DQ_L() 		PORTF&=~(1<<DQ_pin)
#define 	DQ_O() 		DDRF|=(1<<DQ_pin)
#define 	DQ_I() 		DDRF&=~(1<<DQ_pin)
#define Read_DQ() 	PINF&(1<<DQ_pin)     





#define RXB8 1
#define TXB8 0
#define UPE 2
#define OVR 3
#define FE 4
#define UDRE 5
#define RXC 7
                               //FE是一个固有变量,在AVR的头文件里面有定义,它是特定的寄存器的位。这里FE的值是4。
#define FRAMING_ERROR (1<<FE) //USART I/O数据寄存器-UDR,Bit 4 – FE: 帧错误
#define PARITY_ERROR (1<<UPE) //Bit 2 – UPE: USART奇偶校验错误
#define DATA_OVERRUN (1<<OVR) //*Bit 3 – DOR:数据溢出
#define DATA_REGISTER_EMPTY (1<<UDRE)  //5 – UDRE: USART数据寄存器空
#define RX_COMPLETE (1<<RXC)  //*Bit 7 – RXC: USART接收结束

// USART0 Receiver buffer
#define RX_BUFFER_SIZE0 8
char rx_buffer0[RX_BUFFER_SIZE0];

#if RX_BUFFER_SIZE0<256
unsigned char rx_wr_index0,rx_rd_index0,rx_counter0;
#else
unsigned int rx_wr_index0,rx_rd_index0,rx_counter0;
#endif

// This flag is set on USART0 Receiver buffer overflow
bit rx_buffer_overflow0;

// USART0 Receiver interrupt service routine     USARTO 接收中断服务程序
interrupt [USART0_RXC] void usart0_rx_isr(void)
{
char status,data;
status=UCSR0A;
data=UDR0;     /* read the received data */
if ((status & (FRAMING_ERROR | PARITY_ERROR | DATA_OVERRUN))==0)
   {
   rx_buffer0[rx_wr_index0]=data;
   if (++rx_wr_index0 == RX_BUFFER_SIZE0) rx_wr_index0=0;
   if (++rx_counter0 == RX_BUFFER_SIZE0)
      {
      rx_counter0=0;
      rx_buffer_overflow0=1;
      };
   };
} 
////
unsigned int rxBufferCount0(void)    //返回rx_counter缓存接收的计数
{
    return rx_counter0;
}

void clearRxBuffer0(void)
{
    #asm("cli");
    rx_rd_index0 = 0;
    rx_wr_index0 = 0;
    rx_counter0 = 0;
    #asm("sei");
}
////
#ifndef _DEBUG_TERMINAL_IO_
// Get a character from the USART0 Receiver buffer
#define _ALTERNATE_GETCHAR_
#pragma used+
char getchar(void)      //得到数据data

{
char data;
while (rx_counter0==0);
data=rx_buffer0[rx_rd_index0];  //
if (++rx_rd_index0 == RX_BUFFER_SIZE0) rx_rd_index0=0;
#asm("cli")   //开中断
--rx_counter0;
#asm("sei") //禁止所有中断

return data;
}
#pragma used-
#endif

// USART0 Transmitter buffer
#define TX_BUFFER_SIZE0 64
char tx_buffer0[TX_BUFFER_SIZE0];

#if TX_BUFFER_SIZE0<256
unsigned char tx_wr_index0,tx_rd_index0,tx_counter0;
#else
unsigned int tx_wr_index0,tx_rd_index0,tx_counter0;
#endif

// USART0 Transmitter interrupt service routine
interrupt [USART0_TXC] void usart0_tx_isr(void)
{
if (tx_counter0)
   {
   --tx_counter0;
   UDR0=tx_buffer0[tx_rd_index0];
   if (++tx_rd_index0 == TX_BUFFER_SIZE0) tx_rd_index0=0;
   };
}

#ifndef _DEBUG_TERMINAL_IO_
// Write a character to the USART0 Transmitter buffer
#define _ALTERNATE_PUTCHAR_
#pragma used+
void putchar(char c)
{
while (tx_counter0 == TX_BUFFER_SIZE0);
#asm("cli")
if (tx_counter0 || ((UCSR0A & DATA_REGISTER_EMPTY)==0))
   {
   tx_buffer0[tx_wr_index0]=c;
   if (++tx_wr_index0 == TX_BUFFER_SIZE0) tx_wr_index0=0;
   ++tx_counter0;
   }
else
   UDR0=c;
#asm("sei")
}
#pragma used-
#endif

// USART1 Receiver buffer
#define RX_BUFFER_SIZE1 8
char rx_buffer1[RX_BUFFER_SIZE1];

#if RX_BUFFER_SIZE1<256
unsigned char rx_wr_index1,rx_rd_index1,rx_counter1;
#else
unsigned int rx_wr_index1,rx_rd_index1,rx_counter1;
#endif

// This flag is set on USART1 Receiver buffer overflow
bit rx_buffer_overflow1;

// USART1 Receiver interrupt service routine
interrupt [USART1_RXC] void usart1_rx_isr(void)
{
char status,data;
status=UCSR1A;
data=UDR1;
if ((status & (FRAMING_ERROR | PARITY_ERROR | DATA_OVERRUN))==0)
   {
   rx_buffer1[rx_wr_index1]=data;
   if (++rx_wr_index1 == RX_BUFFER_SIZE1) rx_wr_index1=0;
   if (++rx_counter1 == RX_BUFFER_SIZE1)
      {
      rx_counter1=0;
      rx_buffer_overflow1=1;
      };
   };
}

// Get a character from the USART1 Receiver buffer
#pragma used+
char getchar1(void)
{
char data;
while (rx_counter1==0);
data=rx_buffer1[rx_rd_index1];
if (++rx_rd_index1 == RX_BUFFER_SIZE1) rx_rd_index1=0;
#asm("cli")
--rx_counter1;
#asm("sei")
return data;
}
#pragma used-
// USART1 Transmitter buffer
#define TX_BUFFER_SIZE1 64
char tx_buffer1[TX_BUFFER_SIZE1];

#if TX_BUFFER_SIZE1<256
unsigned char tx_wr_index1,tx_rd_index1,tx_counter1;
#else
unsigned int tx_wr_index1,tx_rd_index1,tx_counter1;
#endif

// USART1 Transmitter interrupt service routine
interrupt [USART1_TXC] void usart1_tx_isr(void)
{
if (tx_counter1)
   {
   --tx_counter1;
   UDR1=tx_buffer1[tx_rd_index1];
   if (++tx_rd_index1 == TX_BUFFER_SIZE1) tx_rd_index1=0;
   };
}

// Write a character to the USART1 Transmitter buffer
#pragma used+       //使用#pragma used+/#pragma used-之间的代码,生成putchar()函数,代替原系统的putchar()函数.
void putchar1(char c)
{
while (tx_counter1 == TX_BUFFER_SIZE1);
#asm("cli")
if (tx_counter1 || ((UCSR1A & DATA_REGISTER_EMPTY)==0))
   {
   tx_buffer1[tx_wr_index1]=c;
   if (++tx_wr_index1 == TX_BUFFER_SIZE1) tx_wr_index1=0;
   ++tx_counter1;
   }
else
   UDR1=c;
#asm("sei")
}
#pragma used-


void uartPutchars(unsigned char *c, unsigned int length) // 输出单位的数据
{
    unsigned int n;                                                              
    
    for (n = 0; n < length; n++)
    	putchar(*(c++));
}

void PrintString(char *Str)   //输出数组
{
        unsigned char i;
        
        i=0;
        while(Str[i]!=0)
        {
        putchar(Str[i]);
        i++;
        } 

}
void uartPutchars1(unsigned char *c, unsigned int length)
{
    unsigned int n;
    
    for (n = 0; n < length; n++)
    	putchar1(*(c++));
}

void PrintString1(char *Str)
{
        unsigned char i;
        
        i=0;
        while(Str[i]!=0)
        {
        putchar1(Str[i]);
        i++;
        } 

}





static unsigned int ToBeSend[8]={0},tflag[8];  
static unsigned char ROM1[8][8]={
	0x28,0x7B,0xFC,0x33,0x01,0x00,0x00,0x92,
        0x28,0x56,0xD6,0x20,0x01,0x00,0x00,0x9B,
        0x28,0x1B,0x51,0x21,0x01,0x00,0x00,0xB1,
        0x28,0x41,0xC9,0x20,0x01,0x00,0x00,0x56,
        0x28,0x66,0xFD,0x20,0x01,0x00,0x00,0xFE,
        0x28,0x9A,0xE8,0x20,0x01,0x00,0x00,0x5F,
        0x28,0xDB,0x37,0x34,0x01,0x00,0x00,0x1A,
        0x28,0x81,0xC5,0x20,0x01,0x00,0x00,0xE8};//16
void init_1820(void)
{
DQ_H();     					//DQ为高
DQ_O(); 							//输出模式 
DQ_L(); 							//DQ低    
delay_us(190);
 delay_us(190);
 delay_us(110);   		//480us以上,复位延时
DQ_H(); 							//DQ为高
DQ_I(); 							//输入模式  
delay_us(60);   		//15~60us,DS1820的等待时间
delay_us(120);
 delay_us(120); 
 delay_us(120);
 delay_us(60);   		
 DQ_H(); 							//DQ为高
 DQ_O(); 							//输出模式 
}

/******向DS1820写一个字节****************/
void write_1820(unsigned char x) 
{   
 unsigned char m; 
 for(m=0;m<8;m++) 		//从低位开始连续把X的第m位发送出去
	{ 
   DQ_L(); 	 					//DQ为低,开始发送
   if(x&(1<<m))  			//如果第m位是1
		{
		 delay_us(1);
		 DQ_H(); 	 				//DQ为高
		}
	 else 
    DQ_L(); 	 				//否则DQ为低
   delay_us(60);   	//信号保持60~120us 
   DQ_H(); 		 				//发送完后DQ为高
	 delay_us(1);			//两次发送间隙要大于1us
	} 
} 

/***********从DS1820读一个字节**************************/
unsigned char read_1820(void) 
{   
 unsigned char tmp=0,k,n; 
 for(n=0;n<8;n++) 
  { 
   DQ_L(); 						//DQ为低
   delay_us(2);     	//间隙要大于1us
	 DQ_H(); 						//DQ为高
   DQ_I(); 						//输入模式
   k=Read_DQ();  	 		//读数据,从低位开始 
   if(k) 							//如果k=1(即PIND6为1)
    tmp|=(1<<n); 			//temp的第n位与1求或
   else 
    tmp&=~(1<<n); 		//temp的第n位与0求与
   delay_us(60); 		//60~120us   
	 DQ_O(); 						//输出模式 
	 delay_us(1);			//两次接收间隙要大于1us
  } 
 return (tmp); 
}
/**********1820转换温度************************/
void DS1820Convert(void)
{ 
 init_1820();        		//复位18b20 
 write_1820(0xCC);   		// Skip ROM(不发出地址码)
 write_1820(0x44); 	 		//发出开始转换命令
} 

 /**********获取1820的rom序列**********************/     
/*unsigned char read_ROM(void)
{
	unsigned char j;
	init_1820();
 	delay_us(1);
 	write_1820(0x33);
 
 	for(j=0;j<8;j++){ROM1[j]=read_1820();}
 
 	 
 	return 1;  
} */ 
 
/**********获取1820的温度********************/   
void get_T(void)
{ 



unsigned char teml1,temh1,i;
unsigned char j=0;
unsigned int count2=0;
//unsigned char flag;
// flag=read_ROM();
// while(!flag);
  DS1820Convert();  
  
 for(j=0;j<8;j++)
 {  init_1820();    //复位18b20 
 write_1820(0x55);
 
 for (i=0;i<8;i++)			//发送所要查询的温感的ROMcode
	{
   write_1820(ROM1[j][i]);
	}
  delay_ms(2);
 write_1820(0xBE);	 		//发出读寄存器命令
 teml1=read_1820();	 		//读数据,第一次是收到第一个字节 
 temh1=read_1820(); 	     	//第二次收到第二个字节(共会传输9个,但这里只需前2个)	
 /*count2=temh1;
 count2<<=8;
 count2=count2|teml1;
 if(count2<0x0fff)
 {
 	tflag=0;
 }
 
 else  
 {      
	count2=~count2+1;
 	tflag=1;
 }
 count2=count2*(0.625);   */
  
 count2=(temh1*256+teml1)*6.25/100;  //计算具体温度,输出结果为实际值的100倍 
 ToBeSend[j]=count2;
  if(count2<4095)
 {
 	tflag[j]=0;
 }
 
 else  
 {      
	count2=(~count2+1);
 	tflag[j]=1;
 }


 
 }

}    




// Declare your global variables here

void main(void)
{
// Declare your local variables here

// Input/Output Ports initialization
// Port A initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T 
PORTA=0x00;
DDRA=0x00;

// Port B initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T 
PORTB=0x00;
DDRB=0x00;

// Port C initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T 
PORTC=0x00;
DDRC=0x00;

// Port D initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T 
PORTD=0x00;
DDRD=0x00;

// Port E initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T 
PORTE=0x00;
DDRE=0x00;

// Port F initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=Out 
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=1 
PORTF=0x01;
DDRF=0x01;

// Port G initialization
// Func4=In Func3=In Func2=In Func1=In Func0=In 
// State4=T State3=T State2=T State1=T State0=T 
PORTG=0x00;
DDRG=0x00;

// Timer/Counter 0 initialization
// Clock source: System Clock
// Clock value: Timer 0 Stopped
// Mode: Normal top=FFh
// OC0 output: Disconnected
ASSR=0x00;
TCCR0=0x00;
TCNT0=0x00;
OCR0=0x00;

// Timer/Counter 1 initialization
// Clock source: System Clock
// Clock value: Timer 1 Stopped
// Mode: Normal top=FFFFh
// OC1A output: Discon.
// OC1B output: Discon.
// OC1C output: Discon.
// Noise Canceler: Off
// Input Capture on Falling Edge
TCCR1A=0x00;
TCCR1B=0x00;
TCNT1H=0x00;
TCNT1L=0x00;
ICR1H=0x00;
ICR1L=0x00;
OCR1AH=0x00;
OCR1AL=0x00;
OCR1BH=0x00;
OCR1BL=0x00;
OCR1CH=0x00;
OCR1CL=0x00;

// Timer/Counter 2 initialization
// Clock source: System Clock
// Clock value: Timer 2 Stopped
// Mode: Normal top=FFh
// OC2 output: Disconnected
TCCR2=0x00;
TCNT2=0x00;
OCR2=0x00;

// Timer/Counter 3 initialization
// Clock source: System Clock
// Clock value: Timer 3 Stopped
// Mode: Normal top=FFFFh
// Noise Canceler: Off
// Input Capture on Falling Edge
// OC3A output: Discon.
// OC3B output: Discon.
// OC3C output: Discon.
TCCR3A=0x00;
TCCR3B=0x00;
TCNT3H=0x00;
TCNT3L=0x00;
ICR3H=0x00;
ICR3L=0x00;
OCR3AH=0x00;
OCR3AL=0x00;
OCR3BH=0x00;
OCR3BL=0x00;
OCR3CH=0x00;
OCR3CL=0x00;  

// USART0 initialization
// Communication Parameters: 8 Data, 1 Stop, No Parity
// USART0 Receiver: On
// USART0 Transmitter: On
// USART0 Mode: Asynchronous
// USART0 Baud rate: 115200
UCSR0A=0x00;
UCSR0B=0xD8;
UCSR0C=0x06;
UBRR0H=0x00;
UBRR0L=0x03;

// USART1 initialization
// Communication Parameters: 8 Data, 1 Stop, No Parity
// USART1 Receiver: On
// USART1 Transmitter: On
// USART1 Mode: Asynchronous
// USART1 Baud rate: 115200
UCSR1A=0x00;
UCSR1B=0xD8;
UCSR1C=0x06;
UBRR1H=0x00;
UBRR1L=0x03;

// External Interrupt(s) initialization
// INT0: Off
// INT1: Off
// INT2: Off
// INT3: Off
// INT4: Off
// INT5: Off
// INT6: Off
// INT7: Off
EICRA=0x00;
EICRB=0x00;
EIMSK=0x00;

// Timer(s)/Counter(s) Interrupt(s) initialization
TIMSK=0x00;
ETIMSK=0x00;

// Analog Comparator initialization
// Analog Comparator: Off
// Analog Comparator Input Capture by Timer/Counter 1: Off
ACSR=0x80;
SFIOR=0x00;   




while (1)
      {
      // Place your code here
               char j;
               char n_dat,flagdata;
               static char i;
               	char t_value[10];
               //	float t_f; 
               	get_T(); 
               	 
                 
               
               //	 t_f=ToBeSend; 
                for(i=0;i<8;i++) 
                { 
                  if(tflag[i]==0)
                 flagdata='+';
                 else
                 flagdata='-'; 
               	 n_dat=(i+0x31);
               	 ftoa(ToBeSend[i],1,t_value); 
               	 putchar(n_dat);  
               	 putchar(' ');
               	 putchar(' ');
               	 putchar(flagdata); 
               	 PrintString(t_value);
                 putchar('`'); 
                 putchar('C');
                 delay_us(1000);
                 putchar(' ');
               	 putchar(' ');
                 putchar('\n'); 
  
               	/*//putchar(i+0x31);  
                 putchar('R'); 
               	 for(j=0;j<8;j++)
               	 {
               	  putchar(ROM1[i][j]);    
               	 
               	 }
               	 
                 putchar('\n'); 
                 delay_us(1000);*/
 	 
               	 delay_ms(1000);
                }
                
               	
      };

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -