📄 lcc_handle_message.c
字号:
/******************************************************************************
* Power Task (pwr)
* Design and coding by Svend Kristian Lindholm, skl@ti.com
*
* PWR Message Processing
*
* $Id: lcc_handle_message.c,v 1.1.1.1 2004/06/19 06:00:29 root Exp $
*
******************************************************************************/
#include <string.h>
#include "lcc.h"
#include "lcc_api.h"
#include "lcc_trace.h"
#include "lcc_task.h"
#include "lcc_tm_i.h"
#include "lcc_cfg_i.h"
#include "lcc_modulate.h"
#include "ffs.h"
#include "etm_env.h"
#include "abb.h"
// TISH031218: Added by Jason
#include "rvf_api.h"
#include "rvm_use_id_list.h"
/******************************************************************************
* Function prototypes
******************************************************************************/
void ttr(unsigned trmask, char *format, ...);
void str(unsigned mask, char *string);
void *pwr_malloc(int size);
T_RVM_RETURN pwr_task_init(void);
UINT32 pwr_timer_elapsed(UINT32 time_begin, UINT32 current_timer);
void build_name(const char *ch_pre, char *cfg_id , UINT8 index, const char * ch_post, char * name);
void pwr_modulate_init(void);
void pwr_modulate_on(void);
int pwr_capacity(uint16 Vbat);
void pwr_check_timers();
void pwr_stop_timers();
T_RVM_RETURN pwr_start_timer(UINT32 *timer_begin);
T_RVM_RETURN pwr_stop_timer(UINT32 *timer_begin);
T_RVM_RETURN pwr_check_files(void);
T_RVM_RETURN pwr_read_files(void);
T_RVM_RETURN pwr_read_chg_files(void);
T_RVM_RETURN pwr_read_cal_files(void);
void pwr_send_msg(uint32 msg_id ,T_RVF_ADDR_ID src_addr_id, T_RVF_ADDR_ID dest_addr_id);
void mmi_send_msg(struct mmi_info_ind_s *event);
void start_q401_charge(void);
void start_q402_charge(void);
void start_pre_charge(void);
void stop_q401_charge(void);
void stop_q402_charge(void);
void stop_pre_charge(void);
void charger_unplug_house_keeping(void);
void cv_charging_house_keeping(void);
void end_charging_house_keeping(void);
int check_chg_unplug(void);
#if (TEST_PWR_MMI_INTERFACE == 1)
#include "lcc_mmi_api.c"
#endif
extern T_PWR_CTRL_BLOCK *pwr_ctrl;
extern T_PWR_CFG_BLOCK *pwr_cfg;
/* Robert.Chen add, 2004-05-28 */
UINT8 cv_stage = 0;
UINT8 cv_overflow = 0;
/* zhq, 2004/06/16, add this for in CAL & INI state, we can not read temp<n>.cfg,
so we just use this to get a rough value of bat capacity. */
uint16 cap_CAL_INI[9+1] = {
/* Voltage VS Capacity vector */
4200, // 100%,
4050, // 90%,
3950, // 80%,
3850, // 70%,
3750, // 60%,
3650, // 50%,
3550, // 40%,
3500, // 30%,
3400, // 20%,
3350 // 10%
}; /* 20 */ // Capacity as a function of voltage measured at t=20 degrees - C(t=20)
// Capacity vector : 100%, 90%, 80%, 70% ,60% ,50%, 40%, 30%, 20%, 10%
/* zhq, 2004/06/16, add this for send event to MMI at least 6 times we enter PRE, to prevent that
send start charging event to MMI too frequently. */
static UINT8 eventsend = 0;
/******************************************************************************
* Functions
******************************************************************************/
void build_name(const char *ch_pre, char *cfg_id, UINT8 index, const char * ch_post, char * name)
{
// TISH031218: Modified by Jason
//char tmp[1];
char tmp[2];
strcpy(name, ch_pre);
tmp[0] = *cfg_id;
tmp[1] = 0; // null-termination of strings!
strcpy(&(name[index]), tmp);
strcat(name, ch_post);
ttw(ttr(TTrInit, "build_name: '%s'" NL, name));
}
T_RVM_RETURN pwr_task_init()
{
// Perform battery initialization of the pwr task by
// reading battery id and FFS configuration files
T_FFS_SIZE error;
ttw(ttr(TTrInit, "pwr_task_init(%d)" NL, 0));
#if 0 //TISH040218
// Check configuration and calibration files
if ((error = pwr_check_files()) < 0)
return error;
// Read configuration files
if ((error = pwr_read_files()) < 0)
return error;
#endif
pwr_read_files(); //TISH040218
ttw(ttr(TTrInit, "pwr_task_init(%d)" NL, 0xFF));
return RV_OK;
}
int pwr_chg_start(int Tbat) {
int capacity;
// Tbat is the temperature measured in Celsius
// Check start conditions for charging - it is assumed that a charger is plugged
// This check is used in state SUP
// Charging start will _not_ be performed if ...
// 1) Battery temperature is outside limits (measurement)
// 2) Charger identity is unknown
ttw(ttr(TTrCharge, "pwr_chg_start(%d)" NL, 0));
// 1)
// Battery temperature is outside limits (measurement)
// FIXME: Check also low temperatures
// if ((Tbat < pwr_cfg->temp.tbat_min) || (Tbat > pwr_cfg->temp.tbat_max)) {
/* zhq, 2004/06/16, add this macro to prevent using thermal resistor to detect
temperature for we do not have its support on hardware. */
#if (LCC_TEMP_DETECT_EN == 1)
if ((Tbat > pwr_cfg->temp.tbat_max))
{
ttw(ttr(TTrCharge, "pwr_chg_start(%d) Tbat=(%d)" NL, 0xFF, Tbat));
return FALSE;
}
#endif
// 2)
// Charger identity unknown
/* zhq, 2004/06/16, add this macro to prevent using ID resistor to detect battery ID
for we do not have its support on hardware. */
#if (LCC_BATID_DETECT_EN == 1)
if ((pwr_ctrl->flag_chg_unknown == 1) && (pwr_ctrl->flag_mmi_registered == 1))
{
ttw(ttr(TTrCharge, "pwr_chg_start(%d) Chg unknown=(%d)" NL, 0xFF, Tbat));
pwr_ctrl->mmi_ptr->header.msg_id = MMI_CHG_UNKNOWN_IND;
mmi_send_msg(pwr_ctrl->mmi_ptr);
// Send only once
pwr_ctrl->flag_bat_unknown = 0;
return FALSE;
}
#endif
ttw(ttr(TTrCharge, "pwr_chg_start(%d)" NL, 0xFF));
return TRUE;
}
int pwr_chg_stop(int Tbat, int Vbat) {
// Check stop conditions for charging
// I.e.
// - temperature (RF+Battery) thresholds
// - battery voltage thresholds
// - regulation loop gain (duty cycle)
//
// This check is used regularly in state CCI, LCI, CCV and LCV
// Charging will be stopped if ...
// 1) Battery temperature is outside limits
// 2) Battery voltage is equal to - or above - charging stop battery voltage
// Nickel checks:
// 3) The RF temperature versus battery temperature rise is above threshold (Possible?)
//
// Lithium checks:
// 4) The regulation parameter k is below configured threshold limit
// Returns TRUE if the charging algorithm should be stopped
// Returns FALSE if the charging algorithm should be continued
ttw(ttr(/*TTrCharge*/0xff000000, "pwr_chg_stop(%d)" NL, 0));
// 1)
// Battery temperature is outside limits
// FIXME: Check also low temperatures
/* zhq, 2004/06/16, add this macro to prevent using thermal resistor to detect
temperature for we do not have its support on hardware. */
#if (LCC_TEMP_DETECT_EN == 1)
if (Tbat > pwr_cfg->temp.tbat_max)
{
ttw(ttr(0xff000000, "pwr_chg_stop(%d) Tbat=(%d)" NL, 0xFF, Tbat));
if (pwr_ctrl->flag_mmi_registered == 1)
{
pwr_ctrl->mmi_ptr->header.msg_id = MMI_CHG_FAILED_IND;
pwr_ctrl->mmi_ptr->cause = BATTERY_TEMPERATURE_HIGH;
mmi_send_msg(pwr_ctrl->mmi_ptr);
}
return TRUE;
}
#endif
// 2)
// Battery voltage is equal to - or above - charging stop battery voltage
if(pwr_cfg->bat.type != LITHIUM) /* Robert.Chen added this condition, 2004-05-29 */
{
if ((Vbat > pwr_cfg->bat.chg_stop_thr))
{
ttw(ttr(0xff000000, "pwr_chg_stop(%d) Vbat=(%d)" NL, 0xFF, Vbat));
ttw(ttr(TTrCharge, "pwr_cfg->bat.chg_stop_thr=%d" NL, 0xFF, pwr_cfg->bat.chg_stop_thr));
return TRUE;
}
}
#if 0
#ifndef PWR_FFS_CFG
pwr_cfg->common.rise_thr = PWR_RISE_THR ;
#endif
// 3)
// The RF temperature versus battery temperature rise is above threshold (Possible?)
// Did the battery temperature rise more than the RF temperature rise - stop for Nickel charging!
// Only for Nickel batteries
// FIXME: How big time difference should there be between the deltas? Configurable?
if ((pwr_cfg->data.dTbat - pwr_cfg->data.dT_rf > pwr_cfg->common.rise_thr) == TRUE)
{
ttw(ttr(TTrCharge, "pwr_chg_stop(%d) d(Tbat-Trf)=(%d)" NL, 0xFF, pwr_cfg->data.dTbat - pwr_cfg->data.dT_rf));
return TRUE;
}
#endif
// 4) FIXME: Remove states in this part of the function
// Regulation parameter k is below the configured limit
#if 0 /* Robert.Chen modified, 2004-05-29 */
if ((pwr_cfg->bat.type == LITHIUM) &&
((pwr_ctrl->state == LCV) || (pwr_ctrl->state == CCV)) &&
(pwr_cfg->data.k < pwr_cfg->bat.chg_ctrl_thr))
#else
if ((pwr_cfg->bat.type == LITHIUM) &&
(Vbat > pwr_cfg->bat.chg_stop_thr) && (pwr_ctrl->state == CCV) &&
(pwr_cfg->data.k <= pwr_cfg->bat.chg_ctrl_thr))
#endif
{
ttw(ttr(0xff000000, "k=%d < %d" NL, pwr_cfg->data.k, pwr_cfg->bat.chg_ctrl_thr));
return TRUE;
}
ttw(ttr(TTrCharge, "pwr_chg_stop(%d)" NL, 0xFF));
return FALSE;
}
int pwr_chg_ci_cv_transition(int Vbat) {
// Check CI -> CV condition for charging
// Only for Lithium batteries
// Returns TRUE if CI-> CV transition should be made
// Returns FALSE if CI-> CV transition should NOT be made
ttw(ttr(TTrCharge, "pwr_chg_ci_cv_transition(%d)" NL, 0));
// 1) Check CV charging start threshold
/* Robert.Chen modified, 2004-06-03, to speed up charging */
if ((Vbat > pwr_cfg->bat.chg_start_thr))
//if ((Vbat > pwr_cfg->bat.chg_stop_thr))
/*end*/
{
ttw(ttr(TTrCharge, "pwr_chg_ci_cv_transition(%d) Vbat=(%d)" NL, 0xFF, Vbat));
return TRUE;
}
ttw(ttr(TTrCharge, "pwr_chg_ci_cv_transition(%d)" NL, 0xFF));
return FALSE;
}
int pwr_capacity(uint16 Vbat) {
// Calculate the capacity, C(T,V), of the battery based on
// - Battery Voltage Measurement
// - Battery Temperature Measurement
// - Configuration Parameters
// Returns a value in the interval 0..100 [%]
uint8 i;
uint8 cap;
ttw(ttr(TTrEventLow,"pwr_capacity (Vbat=%d)" NL, Vbat));
cap = 100; // 100%
for (i=0;i<=9;i++)
{
if (Vbat < pwr_cfg->temp.cap[i])
{
cap -= 10; // Count down 10% for each index
ttw(ttr(TTrEventLow,"Trying cap=%d" NL, cap));
}
else
{
// FIXME: Interpolate ... instead of truncate
ttw(ttr(TTrEventLow,"capacity=%d" NL, cap));
return cap;
}
}
ttw(ttr(TTrEventLow,"pwr_capacity (%d)" NL, 0xFF));
return 0; // Couldn't lookup capacity
}
int pwr_capacity_CAL_INI(uint16 Vbat) {
// Calculate the capacity, C(T,V), of the battery based on
// - Battery Voltage Measurement
// - Battery Temperature Measurement
// - Configuration Parameters
// Returns a value in the interval 0..100 [%]
uint8 i;
uint8 cap;
ttw(ttr(TTrEventLow,"pwr_capacity (Vbat=%d)" NL, Vbat));
cap = 100; // 100%
for (i=0;i<=9;i++)
{
if (Vbat < cap_CAL_INI[i])
{
cap -= 10; // Count down 10% for each index
ttw(ttr(TTrEventLow,"Trying cap=%d" NL, cap));
}
else
{
// FIXME: Interpolate ... instead of truncate
ttw(ttr(TTrEventLow,"capacity=%d" NL, cap));
return cap;
}
}
ttw(ttr(TTrEventLow,"pwr_capacity (%d)" NL, 0xFF));
return 0; // Couldn't lookup capacity
}
int8 pwr_temp_lookup(uint16 ADC, uint8 i_meas)
{
// temperature = f(ADC, I_meas)
// f(x) is table-lized using ETM command 'pww 4 ...'
int i;
int temp;
#define MAX_TEMP_SIZE 9
i = 0;
temp = -20;
// FIXME: Always using the second current - should also use the first...
while (ADC < pwr_cfg->temp.v2t_2[i] && i < MAX_TEMP_SIZE)
{
ttw(ttr(TTrEventLow,"ADC=%d < pwr_cfg->temp.v2t_2[%d]=0x%x" NL, ADC,i, pwr_cfg->temp.v2t_2[i]));
ttw(ttr(TTrEventLow,"temp=%d" NL, temp));
i++;
temp += 10;
}
if (i == MAX_TEMP_SIZE)
{
// No temperature found - return NULL value (0xFF)
ttr(TTrWarning, "Temperature lookup failed %d" NL, ADC);
return 0xFF;
}
if (i != 0)
{
// Interpolate
if (pwr_cfg->temp.v2t_2[i-1] == 0xFFFF)
temp += 10*(ADC - pwr_cfg->temp.v2t_2[i])/(pwr_cfg->temp.v2t_2[i] - 1024);
else
temp += 10*(ADC - pwr_cfg->temp.v2t_2[i])/(pwr_cfg->temp.v2t_2[i] - pwr_cfg->temp.v2t_2[i-1]);
ttw(ttr(TTrEventLow,"Interpolated temp=%d" NL, temp));
}
return((int8)temp);
}
enum
{
Vbat = 0,
Vchg = 1,
Ichg = 2,
Vbt2 = 3,
Type = 4,
Tbat = 5,
T_rf = 6,
Tc_x = 7,
Tc_y = 8,
State= 9
} adc_index_e;
// The driving element of the LCC task - the ADC measurements
T_RV_RET process_spi_adc_indication (T_PWR_REQ *request)
{
struct pwr_adc_ind_s *ind;
int error, i, index;
int8 temp;
UINT32 timer;
UINT16 status; // Result of charger plug - unplug - polled
UINT32 tmp_vbat_mV;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -