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

📄 1624_1.c

📁 Low End Microchip PICs C函数
💻 C
字号:
// 1624_1.C
//
//    PIC16F877                   DS1624
//
//    SCL (term 18) ----------- SCL (term 2) ----- To Other
//    SDA (term 23) ----------- SDA (term 1) ----- I2C Devices
//
//
// Performs 10 temperature measurements and displays each result on the
// LCD and also save the data to the DS1624's EEPROM.  The data is then
// read from EEPROM and displayed on the LCD.
//
// copyright, Peter H. Anderson, Baltimore, MD, Mar, '01

#case

#device PIC16F877 *=16 ICD=TRUE

#include <defs_877.h>
#include <lcd_out.h>
#include <i2c_mstr.h>

#define TRUE !0
#define FALSE 0

// functions in this program
void ds1624_config(byte dev_adr, byte mode);
void ds1624_start_conv(byte dev_adr);
void ds1624_meas_temp(byte dev_adr, byte *p_whole, byte *p_fract);
byte ds1624_compute_fraction(byte t_fract);

void ds1624_ee_write(byte dev_adr, byte ee_adr,  byte dat);
byte ds1624_ee_read(byte dev_adr, byte ee_adr);

#define NUM_SAMPS 10

void main(void)
{
   byte m, n, line, ee_adr, dat_h, dat_l, temp_h, temp_l, t_whole, t_fract;

   lcd_init();
   i2c_master_setup();

   ds1624_config(0x02, 0x01);  // dev adr is 0x02, mode is 0x01 - 1 shot

   for(n = 0, ee_adr=0; n<NUM_SAMPS; n++)
   {
     ds1624_start_conv(0x02);
     delay_ms(1000);
     ds1624_meas_temp(0x02, &dat_h, &dat_l);
     		// note that pointers are passed
     if(dat_h & 0x80)		// result is negative
     {
	    temp_l = (~dat_l & 0xf8) + 0x08;
        temp_h = ~dat_h;
        if (temp_l == 0)
        {
          ++temp_h;
        }
	    lcd_char('-');
     }

  	 else
	 {
		 temp_h = dat_h;
		 temp_l = dat_l;
	 }
	 t_whole = temp_h;
     t_fract = ds1624_compute_fraction(temp_l);
	                          // convert to decimal format
     lcd_clr_line(0);
     lcd_dec_byte(t_whole, 2);
     lcd_char('.');	// decimal point
     lcd_dec_byte(t_fract, 2);

     ds1624_ee_write(0x02, ee_adr, dat_h);
     ds1624_ee_write(0x02, ee_adr+1, dat_l);
     ee_adr += 2;
     delay_ms(1000);
   }

   lcd_init();

   for (ee_adr = 0, n = 0, m = 0, line = 0; n<NUM_SAMPS; n++)
            // now fetch each from EEPROM and display
   {

      if (m==2)
      {
	     m=0;
	     ++line;
	     if (line == 4)
	     {
	        line = 0;
            lcd_init();
	     }
	     lcd_clr_line(line);
      }
      ++m;

      dat_h = ds1624_ee_read(0x02, ee_adr);
      dat_l = ds1624_ee_read(0x02, ee_adr+1);
      ee_adr += 2;

      if(dat_h & 0x80)		// result is negative
      {
	    temp_l = (~dat_l & 0xf8) + 0x08;
        temp_h = ~dat_h;
        if (temp_l == 0)
        {
          ++temp_h;
        }
	    lcd_char('-');
      }

	  else
	  {
	 	 temp_h = dat_h;
         temp_l = dat_l;
	  }

	  t_whole = temp_h;
      t_fract = ds1624_compute_fraction(temp_l);
	                          // convert to decimal format
      lcd_dec_byte(t_whole, 2);
      lcd_char('.');	// decimal point
      lcd_dec_byte(t_fract, 2);

      lcd_char(' ');
      delay_ms(500);
   }

   while(1)	/* loop */		;
}

void ds1624_config(byte dev_adr, byte mode)
// configures DS1624 in 1SHOT temperature conversion mode
{
   i2c_master_start();
   i2c_master_out_byte(0x90 | (dev_adr << 1));
   i2c_master_out_byte(0xac);	// access configuration
   i2c_master_out_byte(mode);
   i2c_master_stop();
   delay_ms(25);  	// wait for EEPROM to program
}

void ds1624_start_conv(byte dev_adr)
{
   i2c_master_start();
   i2c_master_out_byte(0x90 | (dev_adr << 1));
   i2c_master_out_byte(0xee);	// start conversion
   i2c_master_stop();
}

void ds1624_meas_temp(byte dev_adr, byte *p_whole, byte *p_fract)
// fetches temperature result.  Values t_whole and t_fract returned using
// pointers
{
   i2c_master_start();
   i2c_master_out_byte(0x90 | (dev_adr << 1));
   i2c_master_out_byte(0xaa);	// fetch temperature

   i2c_master_repeated_start();   	// no intermediate stop
   i2c_master_out_byte(0x90 | (dev_adr << 1) | 0x01);
   *p_whole=i2c_master_in_byte(TRUE);	// value pointed to by p_whole
   *p_fract=i2c_master_in_byte(FALSE);
   i2c_master_stop();
}

byte ds1624_compute_fraction(byte t_fract)
// converts high five bits in t_fract to a number in the range of
// 0 - 100.
{
    byte sum = 0;
    byte y, n;
	const byte dec_vals[5] = {3, 6, 12, 25, 50};
				// 3 / 100, 6/100, 12/100, etc
	y = t_fract >> 3;		// fractional part is now in lowest five bits
	for (n=0; n<5; n++)
	{
	   if (y&0x01)
	   {
		   sum = sum + dec_vals[n];
	   }
	   y = y >> 1;
	}
	return(sum);
}

byte ds1624_ee_read(byte dev_adr, byte ee_adr)
// returns content location of location ee_adr in DS1624 EEPROM
{
   byte y;

   i2c_master_start();
   i2c_master_out_byte(0x90 | (dev_adr << 1));
   i2c_master_out_byte(0x17);		// access memory

   i2c_master_out_byte(ee_adr);	// the eeprom address

   i2c_master_repeated_start();			// no intermediate stop
   i2c_master_out_byte(0x90 | (dev_adr << 1) | 0x01);

   y = i2c_master_in_byte(FALSE);
   i2c_master_stop();

   return(y);
}

void ds1624_ee_write(byte dev_adr, byte ee_adr, byte dat)
// writes content of dat to specified address ee_adr
{
   i2c_master_start();
   i2c_master_out_byte(0x90 | (dev_adr << 1));
   i2c_master_out_byte(0x17);		// access memory

   i2c_master_out_byte(ee_adr);	// the eeprom address
   i2c_master_out_byte(dat);		// the eeprom data
   i2c_master_stop();
   delay_ms(25);  		// wait for eeprom to program
}

#include <lcd_out.c>
#include <i2c_mstr.c>

⌨️ 快捷键说明

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