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

📄 gas_mon.c

📁 DS2438 one wire (ow) battery monitor code for renesas M16c... (-:cool:-)
💻 C
📖 第 1 页 / 共 3 页
字号:
//_____________________________________________________________________________
// IAD turns the current A/D on and off and must be off for performing some functions
// such as writing the threshold register.
//_____________________________________________________________________________
void gas_mon_clearIAD(void)
{
    byte_union status_config_reg;
   
    status_config_reg.asbyte = gas_mon_readRegister(0, 0); 
    status_config_reg.asBits.b0 = 0;
    gas_mon_writeRegister(0, 0, status_config_reg.asbyte);
}



//_____________________________________________________________________________
//  gas_mon_getIAD
//_____________________________________________________________________________
// gets the state of the IAD bit.
//_____________________________________________________________________________
byte gas_mon_getIAD(void)
{
    byte_union status_config_reg;

    status_config_reg.asbyte = gas_mon_readRegister(0, 0); 
    return (byte)status_config_reg.asBits.b0;
}



//=============================================================================
//  private
//=============================================================================


//_____________________________________________________________________________
//  gas_mon_changeToVad
//_____________________________________________________________________________
// change to Vad rather than Vdd
// Note:  Vad means Vad pin on gascell monitor pin, not necessarily Vad pin on MCU
//_____________________________________________________________________________
static void gas_mon_changeToVad(void)
{
    asm("fclr I");  // disable interrupts 
    
    //write to scratchpad 0
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(WRITE_SP); // write to scratch pad
    writebyte(0x00); // scratch pad 0
    writebyte(0x07); // to do:  *******  read modify write instead of just writing

// don't bother writing the rest 

    //copy scratchpad 0 to memory
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(COPY_SP); // copy entire scratch pad:  to do read and re-write threshold register
    writebyte(0x00); // page number to read
    while (!readBit()); // the monitor outputs all zeros on the DQ line
                            // until the NV writing is complete, at which
                  // time it outputs all ones.

    asm("fset I");  // enable interrupts    

}


//_____________________________________________________________________________
//  gas_mon_changeToVdd
//_____________________________________________________________________________
// change to Vdd rather than Vad
// Note:  Vdd means Vdd pin on gascell monitor pin, not necessarily Vdd pin in
//        the application.
//_____________________________________________________________________________
static void gas_mon_changeToVdd(void)
{
    asm("fclr I");  // disable interrupts 
    
    //write to scratchpad 0
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(WRITE_SP); // write to scratch pad
    writebyte(0x00); // scratch pad 0
    writebyte(0x0F); // to do:  *******  read modify write instead of just writing

    // don't bother writing the rest 

    //copy scratchpad 0 to memory
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(COPY_SP); // copy entire scratch pad:  to do read and re-write threshold register
    writebyte(0x00); // page number to read
    while (!readBit()); // the monitor outputs all zeros on the DQ line
                            // until the NV writing is complete, at which
                            // time it outputs all ones.
     

    asm("fset I");  // enable interrupts    

}


//_____________________________________________________________________________
//  gas_mon_readVoltage
//_____________________________________________________________________________
// Read the voltage from the selected source: Vdd or Vad pin on gas monitor IC.
// The Vdd pin might not be actually connected to "Vdd" in the application.
// The Vad pin might not be actually connected to "Vad" in the application.
// Units: Volts
//_____________________________________________________________________________
static float gas_mon_readVoltage(void)
{
    word_union voltage;

    asm("fclr I");  // disable interrupts 
    
    // start voltage conversion
    resetDQ(); // modify to check for presence pulse was received OK
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(CONVERT_V); // start conversion
    while (!readBit()); // the monitor outputs all zeros on the DQ line
                            // until the conversion is complete, at which
                            // time it outputs all ones.
    //recall page 0 to scratchpad
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(RECALL_MEMORY); // recall SP command
    writebyte(0x00); // page number to read

    //read scratchpad
    resetDQ(); 
    writebyte(SKIP_ROM); // Skip ROM
    writebyte(READ_SP); // read SP command
    writebyte(0x00); // page number to read
    readbyte(); // throw away these
    readbyte(); // throw away these
    readbyte(); // throw away these
    voltage.asbytes.lowbyte = readbyte(); // read LSB 
    voltage.asbytes.highbyte = readbyte(); // read LSB 

       

    asm("fset I");  // enable interrupts    

    // convert data
    // See page 4 of the DS2438 data sheet
    return (float)voltage.asword/100;
}


//_____________________________________________________________________________
//  gas_mon_set_threshold
//_____________________________________________________________________________
// Sets the value of the current register value below which no accumulation 
// of current measurements is made.
// I.e., small apparent currents are assumed to be offset errors and are prevented
// from accumulating in the ICA.
//  See the data sheet for the full meaning of th1 and th2
//
//   th2   th1   Threshold (+/- least sig bit)
//  -----+-----+----------------------------------
//    0     0    no threshold (default)
//    0     1    +/- 2LSB
//    1     0    +/- 4LSB
//    1     1    +/- 8LSB
//_____________________________________________________________________________
static void gas_mon_set_threshold(byte th2, byte th1)
{
    byte_union threshold_reg;
    
    threshold_reg.asbyte = 0x00;
    threshold_reg.asBits.b7 = th2;
    threshold_reg.asBits.b6 = th1;

    // When writing to the threshold register, current measurement MUST be disabled 
    gas_mon_clearIAD();
    gas_mon_writeRegister(0, 7, threshold_reg.asbyte); // threshold register is byte 7 on page 0
    gas_mon_setIAD();
}


//_____________________________________________________________________________
//  resetDQ
//_____________________________________________________________________________
// Generate a 1-Wire reset, return 1 if no
// presence detect was found, return 0 otherwise.
//_____________________________________________________________________________
static int resetDQ(void)
{
    int result = 1; // 1 means no gas monitor connected

    //asm("fclr I");  // disable interrupts 

    DQ=LOW; 
    DQ_DIRECTION = OUTPUT; // Drives DQ low to excite presence pulse
    delay_100ns((word) 4900);        // keep line low for at 480us
    //DQ=HIGH;            // If required,
                          // drive line high quickly, then release the bus
                          // DQ is set to output a 1 briefly to improve the rise time
                          // (helps the weak internal pull-up resistor)
    DQ_DIRECTION = INPUT; 
    delay_100ns((word) 650);        // wait till the middle of the expected presence pulse
    
    result = DQ;        //Sample and return the presence pulse value: 0 = presence
    
    delay_100ns((word) 3600);

    //asm("fset I");  // enable interrupts

    return result;


}


//_____________________________________________________________________________
//  write1
//_____________________________________________________________________________
// generate a write1
//_____________________________________________________________________________
static void write1(void)
{
    //asm("fclr I");  // disable interrupts 

    DQ=0; DQ_DIRECTION = OUTPUT; // Drives DQ low
    delay_100ns((word) 85); // bring it high within 15us to indicate a 1
    DQ=1; DQ_DIRECTION = INPUT; //Releases the bus
    delay_100ns((word) 600); // all write slots must be a minimum of 60us
                        // they must end with a minimum if 1us high

    //asm("fset I");  // enable interrupts

}


//_____________________________________________________________________________
//  write0
//_____________________________________________________________________________
// Generate a Write0. There is a 5us recovery
// time in case the rise time of DQ line in the system is
// slower than 1us.
//_____________________________________________________________________________
static void write0(void)
{
    //asm("fclr I");  // disable interrupts 

    DQ=LOW; 
    DQ_DIRECTION = OUTPUT; // Drives DQ low
    delay_100ns((word) 700); // keep it low for at least 60us to indicate a 0
    DQ=1; DQ_DIRECTION = INPUT; //Releases the bus
    delay_100ns((word) 100);  // all write slots must be a minimum of 60us
                        // they must end with a minimum if 1us high

    //asm("fset I");  // enable interrupts

}


//_____________________________________________________________________________
//  readBit
//_____________________________________________________________________________
// read 1 bit from the bus and return it
//_____________________________________________________________________________
static BOOL readBit(void)
{
    BOOL result;

    //asm("fclr I");  // disable interrupts 

    DQ=LOW; 
    DQ_DIRECTION = OUTPUT; // Drives DQ low
    delay_2_us();
    DQ_DIRECTION = INPUT; //Releases the bus to allow the device to drive the line

    delay_2_us();  // slightly more delay here because if the gas monitor is not pulling low
    delay_2_us();  // then it takes about 3us for the line to be pulled weakly high
    delay_2_us();  // by the internal pull-up
    result = DQ; //sample DQ for data
    
    //LED_Green = ON; // spike to show where DQ is being sampled by MCU

    delay_100ns((word) 600); // all read slots must be a minimum of 60us
                        // they must end with a minimum if 1us high

    //LED_Green = OFF;

    //asm("fset I");  // enable interrupts


    return result;
}



//_____________________________________________________________________________
//  writebyte
//_____________________________________________________________________________
// write data byte
//_____________________________________________________________________________
static void writebyte(byte data)
{
    byte loop;

    //Do 1 complete byte
    for(loop=0; loop<8; loop++)
    {
        //0x01,0x02,0x04,0x08,0x10,etc.
        if(data & ((byte) 0x01<<loop))
            write1();
        else
            write0();
    }

}


//_____________________________________________________________________________
//  readbyte
//_____________________________________________________________________________
// read data byte and return it
//_____________________________________________________________________________
static byte readbyte(void)
{
    byte loop;
    byte result=0;
    for(loop=0; loop<8; loop++)
    {
        result = result + (readBit() << loop);
    }
    return result;
}


// End of file: gas_mon.c
//_____________________________________________________________________________

⌨️ 快捷键说明

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