?? battest.c
字號:
/***************************************************************************
* This code and information is provided "as is" without warranty of any *
* kind, either expressed or implied, including but not limited to the *
* implied warranties of merchantability and/or fitness for a particular *
* purpose. *
* *
* Copyright (C) 2005 Teridian Semiconductor Corp. All Rights Reserved. *
***************************************************************************/
//**************************************************************************
// DESCRIPTION: 71M652x POWER METER - battery test code.
// If BME, bit 6 of 0x2020, is set, then a load is applied and on the
// next alternate conversion cycle, the battery voltage is measured.
// Since this loads the battery, it should be as short as possible,
// and done only rarely, e.g. once per day.
// Therefore, the real-time logic is in the CE interrupts in ce.c
// In xfer_busy, which starts the almux cycle to mesure temperature,
// there's code to start a battery test. In ce-busy, which runs
// after every mux cycle, there's code to collect the battery test
// data.
// The code here commands the battery test, and then interprets it.
//
// AUTHOR: RGV
//
// HISTORY: See end of file.
//**************************************************************************
// File: BATTEST.C
//
#include "options.h"
#if BATTERY_TEST
#include "meter.h" // access to day of month
#include "ce.h" // memget_ce()
#include "lcd.h" // liquid crystal display
#include "battest.h" // test the fn prototypes
/*** External variables referenced by this module ***/
// See "math.h"
// Refer to "ce652x.h" include file.
// VBat is in Totals, in meter.h (so it can be displayed, saved, etc.)
// VBatMin is in Totals.Parms, in meter.h (so it can be calibrated)
/*** Public variables declared within this module ***/
uint8_t data bat_sample_cnt = 0; // counts samples not yet collected
int32_t xdata bat_samples; // sum of samples
/*** Private functions declared within this module ***/
static int32_t mVBat (int32_t v); // calculate the battery voltage, in mV
/*** Private variables declared within this module ***/
#if REAL_TIME_DATE
static uint8_t last_day = 0; // the last day that a battery test was done
#elif OPERATING_TIME
static uint32_t last_day = 0; // the last day that a battery test was done
#else
#error battery test needs a way to find the next day
#endif
// This routine may be called from the command line to start a battery
// test. The xfer_busy_interrupt, in ce.c, reads bat_sample_cnt to start
// a measurement.
void battest_start (void)
{
if (bat_sample_cnt) // if a measurement is in progress, don't mess it up
return;
#if REAL_TIME_DATE
last_day = Rtc_Date;
#elif OPERATING_TIME
last_day = OperatingSeconds + 86400L;
#else
#error needs a day sensor
#endif
LCDX |= BME; // start reading the battery
bat_sample_cnt = 3;
}
// This routine is called from the part of meter_run() that only
// operates when the CE is active. This is because the battery test
// can only run when the CE is active. It can't run in brownout mode,
// for example.
void battest_run (void)
{
// Schedule a battery test every day at midnight, and ASAP when the meter
// is turned on. With a 3.6V battery at the worst case battery load
// resistor, 27 kiloOhms, this nominally draws 133 microamps for
// 2 seconds each day.
// If mains power never fails, this depletes a 1Amp/Hour battery
// (typical small 3.6V lithium) in ten years.
#if REAL_TIME_DATE
if (last_day != Rtc_Date)
#elif OPERATING_TIME
if (last_day < OperatingSeconds)
#else
#error needs a day sensor
#endif
{
battest_start ();
}
else if (bat_sample_cnt > 0)
{
--bat_sample_cnt;
if (bat_sample_cnt == 0)
{
VBat = ((uint32_t) memget_ce (&vbat) ) >> 9;
LCDX &= ~BME; // stop measuring
}
}
// if mesurement is done, and the battery exists
else if (bat_sample_cnt == BATTERY_MODE_ENABLE)
{
// report the results
// VBatMin can be calibrated. It's in the parameter table
// in meter\meter.h with other calibrations.
// NOT AN ERROR!! The ADC count is bigger for smaller VBat voltage
if (VBat > VBatMin) // e.g. 0V = 7FFFFF adc counts, 5V = 0x600000
{
// report an error
Status |= BATTERY_BAD;
}
else
{
// report a success
Status &= ~BATTERY_BAD;
}
}
}
// display the most recent battery voltage on the LCD
void battest_lcd (void) // there's only one battery! Don't pass the value.
{
LCD_Number (mVBat(VBat), 6, 3);
LCD_3DP (); // Three decimal places.
battest_start (); // start another measurement, so display adjusts
}
// calculate the battery voltage in millivolts
int32_t mVBat (int32_t v)
{
// The ADC sample has to be shifted right 9 bits.
// So the float constant (-2.298e-6, from official testing) is divided by 2.
// The most accurate place in the ADC is 3.3V, roughly 0x69d800
// For a perfectly accurate scheme, the chip-to-chip variations in
// offset and LSB have to be calibrated, and they have 5% variations.
// This is not done, because the display is a gross mesurement.
// The code is designed so the failure voltage can be calibrated.
return (3300L + (int32_t)((-2.298e-3) * (float)((v - 0x69D800L))));
}
/***************************************************************************
* History
* $Log: battest.c,v $
* Revision 1.9 2006/09/27 01:34:19 tvander
* Battery mode moved to DIO-8
*
* Revision 1.8 2006/09/12 02:44:49 gmikef
* *** empty log message ***
*
* Revision 1.7 2006/08/09 00:57:33 tvander
* *** empty log message ***
*
* Revision 1.6 2006/07/07 01:04:19 tvander
* Only reports a battery error when there's supposed to be a battery.
*
* Revision 1.5 2006/06/14 02:41:26 tvander
* New, derated battery test runs at 1/8 MPU speed, but uses 150x more battery
* current.
*
* Revision 1.4 2006/06/06 03:57:33 tvander
* Modified to run with hardware timers as well as software timers.
*
* Revision 1.3 2006/05/30 17:18:49 tvander
* Made it possible to compile this on non-6520s
*
* Revision 1.2 2006/05/18 23:18:50 tvander
* 16K and 32K
* First cut at new requirements.
* 32K 6521 is grossly tested.
* All others have a clean compile with C51 8.02
*
* Revision 1.1 2006/05/17 19:07:59 tvander
* Battery test works.
* Power factor works for instantaneous value. Periodic value compiles, but is
* untested.
*
*
* Copyright (C) 2005 Teridian Semiconductor Corp. All Rights Reserved. *
* this program is fully protected by the United States copyright *
* laws and is the property of Teridian Semiconductor Corporation. *
***************************************************************************/
/* battest.c */
#endif // BATTERY_TEST
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -