/************************************************************************** * * Copyright (c) 2009-2018 by SiFar Technology, Inc. * * This software is copyrighted by and is the property of SiFar * Technology, Inc.. All rights are reserved by SiFar Technology, Inc.. * This software may only be used in accordance with the corresponding * license agreement. Any unauthorized use, duplication, distribution, * or disclosure of this software is expressly forbidden. * * This Copyright notice MUST not be removed or modified without prior * written consent of SiFar Technology, Inc.. * * SiFar Technology, Inc. reserves the right to modify this software without notice. * * Author: Payton * Ver: 1.0.0 2023.02.14 * Description: mcu code * **************************************************************************/ #include #include #include #include #include #include #include #include #include #include #include #include #include #include "PrjInc.h" #include "IOCfg.h" #include "DxHunting.h" #include "sf_led.h" #include "flow_preview.h" /* #include "NvtUser/NvtUser.h" #include "AppControl/AppControl.h" #include "comm/hwclock.h" #include #include #include #include "UIInfo/UIInfo.h" #include "IOCfg.h" */ #if HUNTING_CAMERA_MCU == ENABLE UINT32 _DcVoltageVal = 0; UINT32 _LiPolymerVoltageVal = 0; /*4.0P no use*/ UINT32 _BatVoltageVal = 45; UINT8 IsNightLedOn = 0; UINT32 IsPowerDcIn = 1; UINT32 BatVoltageVal = 45; SF_BatteryLevel_e sf_LatestBattLevel = SF_BATT_LEVEL_0; UINT8 needCheckFirst = TRUE; UINT32 DcVoltageVal = 0; UINT32 LiPolymerVoltageVal = 0; /*4.0P no use*/ UINT32 batTempLevel = 0xff; #define SF_READ_BAT_MAX 10 ID FLG_ID_SF_BSTTERY = 0; #define SF_DC_IN_VOLATAGE 70 #define SF_LI_IN_VOLATAGE 99 #if SF_BATTERY_TEST == ENABLE UINT32 LiPolymerVoltageValTest = 0; UINT32 BatVoltageValTest = 0; #endif /************************************************* Function: sf_battery_voltage_convert Description: battery voltage convert Input: resistanceGnd:Grounding terminal resistance,resistanceVin:Input resistance,adcVal:adc val Output: N/A Return: Volt * 10 Others: N/A *************************************************/ UINT32 sf_battery_voltage_convert(UINT32 resistanceGnd, UINT32 resistanceVin, UINT32 adcVal) { UINT32 volt = 0; /*511 * (detected voltage) / (SARADC reference voltage) DC input voltage x resistanceGnd/(resistanceGnd + resistanceVin) = detected voltage, SARADC reference voltage:1.8V */ volt = 27 * adcVal * (resistanceGnd + resistanceVin) / resistanceGnd / 511; return volt; } UINT32 sf_battery_convert_to_adc(UINT32 resistanceGnd, UINT32 resistanceVin, UINT32 volt) { UINT32 adcVal = 0; adcVal = volt * resistanceGnd * 511 / 27 / (resistanceGnd + resistanceVin); return adcVal; } UINT32 sf_get_max_value(UINT32 *_ValueList) { UINT8 readBatCnt = 0; UINT32 MaxValue = 0; for(readBatCnt = 0; readBatCnt < 5; readBatCnt++) /*get max value of 5 times.*/ { MaxValue = (MaxValue > _ValueList[readBatCnt]? MaxValue : _ValueList[readBatCnt]); } return MaxValue; } void sf_adc_init(void) { if (adc_open(ADC_CH_VOLDET_BATTERY) != 0) { printf("sf_adc_init Can't open ADC channel for battery voltage detection\r\n"); return; } //650 Range is 250K Hz ~ 2M Hz adc_setConfig(ADC_CONFIG_ID_OCLK_FREQ, 250000); //250K Hz //battery voltage detection adc_setChConfig(ADC_CH_VOLDET_BATTERY, ADC_CH_CONFIG_ID_SAMPLE_FREQ, 10000); //10K Hz, sample once about 100 us for CONTINUOUS mode adc_setChConfig(ADC_CH_VOLDET_BATTERY, ADC_CH_CONFIG_ID_SAMPLE_MODE, (VOLDET_ADC_MODE) ? ADC_CH_SAMPLEMODE_CONTINUOUS : ADC_CH_SAMPLEMODE_ONESHOT); adc_setChConfig(ADC_CH_VOLDET_BATTERY, ADC_CH_CONFIG_ID_INTEN, FALSE); // Enable adc control logic adc_setEnable(TRUE); gpio_direction_output(P_GPIO_0,0); gpio_direction_output(P_GPIO_1,0); } /************************************************* Function: sf_adc_value_get Description: get battery adc Input: N/A Output: N/A Return: SUCCESS/FAIL Others: N/A *************************************************/ UINT32 sf_adc_value_get(UINT32 mux, UINT32 *pval) { static UINT8 getAdcFlg = 0; //static UINT8 outputflag = 1; *pval = 0; if(getAdcFlg) { return FAIL; } getAdcFlg = 1; if(SF_ADC_BATT == mux)//bat_det { //B:0 A:0 gpio_set_value(P_GPIO_0, 0);//adc_muxa gpio_set_value(P_GPIO_1, 0);//adc_muxb } else if(SF_ADC_LI == mux)//v-li_det { //B:0 A:1 gpio_set_value(P_GPIO_0, 1);//adc_muxa gpio_set_value(P_GPIO_1, 0);//adc_muxb } else if(SF_ADC_DC == mux)//dc12_det { //B:1 A:0 gpio_set_value(P_GPIO_0, 0);//adc_muxa gpio_set_value(P_GPIO_1, 1);//adc_muxb } else if(SF_ADC_TEMP == mux)//temp_det { //B:1 A:1 gpio_set_value(P_GPIO_0, 1);//adc_muxa gpio_set_value(P_GPIO_1, 1);//adc_muxb } //vos_util_delay_us(400); vos_util_delay_ms(1); *pval = adc_readData(0); //printf("[%s:%d] 1 *pval:%lu\n", __FUNCTION__, __LINE__,*pval); getAdcFlg = 0; return SUCCESS; } #if 0 /************************************************* Function: sf_battery_adc_value_get_once Description: get battery adc only once Input: N/A Output: N/A Return: SUCCESS/FAIL Others: N/A *************************************************/ UINT32 sf_battery_adc_value_get_once(void) { UINT32 batAdc = 0; static UINT8 getBatAdcFlg = 0; if(getBatAdcFlg) { return SUCCESS; } getBatAdcFlg = 1; if(sf_adc_value_get(SF_ADC_DC, &batAdc) == SUCCESS) { _DcVoltageVal = sf_battery_voltage_convert(10, 100, batAdc); if(sf_adc_value_get(SF_ADC_LI, &batAdc) == SUCCESS) { _LiPolymerVoltageVal = sf_battery_voltage_convert(15, 100, batAdc); if(_LiPolymerVoltageVal > SF_LI_IN_VOLATAGE) { getBatAdcFlg = 0; return SUCCESS; } else { _LiPolymerVoltageVal = 0; if(sf_adc_value_get(SF_ADC_BATT, &batAdc) == SUCCESS) { _BatVoltageVal = sf_battery_voltage_convert(15, 100, batAdc); //_BatVoltageVal += 1; getBatAdcFlg = 0; return SUCCESS; } else { getBatAdcFlg = 0; printf("%s:%d [ERR] failed !!!\n", __FUNCTION__, __LINE__); return FAIL; } } } else { getBatAdcFlg = 0; printf("%s:%d [ERR] failed !!!\n", __FUNCTION__, __LINE__); return FAIL; } } else { getBatAdcFlg = 0; printf("%s:%d [ERR] failed !!!\n", __FUNCTION__, __LINE__); return FAIL; } } #else /************************************************* Function: sf_battery_adc_value_get_once Description: get battery adc only once Input: N/A Output: N/A Return: SUCCESS/FAIL Others: N/A *************************************************/ UINT32 sf_battery_adc_value_get_once(void) { UINT32 batAdc = 0; UINT32 dcVoltageVal = 0; UINT32 liPolymerVoltageVal = 0; UINT32 batVoltageVal = 0; static UINT8 getBatAdcFlg = 0; if(getBatAdcFlg) return SUCCESS; getBatAdcFlg = 1; if(sf_adc_value_get(SF_ADC_DC, &batAdc) == SUCCESS) { dcVoltageVal = sf_battery_voltage_convert(10, 100, batAdc); dcVoltageVal += 4; } if(sf_adc_value_get(SF_ADC_LI, &batAdc) == SUCCESS) { liPolymerVoltageVal = sf_battery_voltage_convert(15, 100, batAdc); liPolymerVoltageVal += 4; } if(sf_adc_value_get(SF_ADC_BATT, &batAdc) == SUCCESS) { batVoltageVal = sf_battery_voltage_convert(15, 100, batAdc); batVoltageVal += 4; } _DcVoltageVal = dcVoltageVal; if ((liPolymerVoltageVal > batVoltageVal)) { _LiPolymerVoltageVal = liPolymerVoltageVal; _BatVoltageVal = 0; } else { _LiPolymerVoltageVal = 0; _BatVoltageVal = batVoltageVal; } getBatAdcFlg = 0; return SUCCESS; } #endif #if HW_S530 /************************************************* Function: sf_battery_level_update Description: Get battery Voltage with Level. Input: N/A Output: N/A Return: N/A Others: N/A *************************************************/ void sf_battery_level_update(void) { UINT8 batteryVal = 0; UINT8 batteryLevel = SF_BATT_LEVEL_0; batteryVal = sf_battery_value_get(sf_get_night_led_flag()); if(batteryVal >= 70) { batteryLevel = SF_BATT_LEVEL_4; } else if(batteryVal >= 40) { batteryLevel = SF_BATT_LEVEL_3; } else if(batteryVal >= 20) { batteryLevel = SF_BATT_LEVEL_2; } else if(batteryVal >= 1) { batteryLevel = SF_BATT_LEVEL_1; } else { batteryLevel = SF_BATT_LEVEL_0; } sf_LatestBattLevel = batteryLevel; } #else /************************************************* Function: sf_battery_level_update Description: Get battery Voltage with Level. Input: N/A Output: N/A Return: N/A Others: N/A *************************************************/ void sf_battery_level_update(void) { UINT8 batteryVal = 0; UINT8 batteryLevel = SF_BATT_LEVEL_0; if(sf_get_night_led_flag()) { return; } if(IsPowerDcIn == 0) { batteryVal = BatVoltageVal; if(SysGetFlag(BatteryType) == SF_BATT_ALKALINE) { if(batteryVal >= 106) { batteryLevel = SF_BATT_LEVEL_5; } else if(batteryVal >= 102) { batteryLevel = SF_BATT_LEVEL_4; } else if(batteryVal >= 97) { batteryLevel = SF_BATT_LEVEL_3; } else if(batteryVal >= 90) { batteryLevel = SF_BATT_LEVEL_2; } else if(batteryVal >= 75) { batteryLevel = SF_BATT_LEVEL_1; } else { batteryLevel = SF_BATT_LEVEL_0; } } else if(SysGetFlag(BatteryType) == SF_BATT_NI_MH) { if(batteryVal >= 103) { batteryLevel = SF_BATT_LEVEL_5; } else if(batteryVal >= 101) { batteryLevel = SF_BATT_LEVEL_4; } else if(batteryVal >= 100) { batteryLevel = SF_BATT_LEVEL_3; } else if(batteryVal >= 97) { batteryLevel = SF_BATT_LEVEL_2; } else if(batteryVal >= 75) { batteryLevel = SF_BATT_LEVEL_1; } else { batteryLevel = SF_BATT_LEVEL_0; } } else if(SysGetFlag(BatteryType) == SF_BATT_LI) //5.8CG Li Battery { if(batteryVal >= 122) { batteryLevel = SF_BATT_LEVEL_5; } else if(batteryVal >= 120) { batteryLevel = SF_BATT_LEVEL_4; } else if(batteryVal >= 117) { batteryLevel = SF_BATT_LEVEL_3; } else if(batteryVal >= 110) { batteryLevel = SF_BATT_LEVEL_2; } else if(batteryVal >= 80) { batteryLevel = SF_BATT_LEVEL_1; } else { batteryLevel = SF_BATT_LEVEL_0; } } } else { batteryLevel = SF_BATT_LEVEL_5; } sf_LatestBattLevel = batteryLevel; if(SysGetFlag(BatteryLogSwitch)) { printf("battery levle=%d\n", sf_LatestBattLevel); } } #endif /************************************************* Function: sf_check_low_battery Description: check is low battery in auto mode. Output: N/A Return: TRUE/FALSE Others: N/A *************************************************/ BOOL sf_check_low_battery(void) { UINT8 lowCompareVal = 0; BOOL ret = FALSE; UIMenuStoreInfo *puiPara = sf_ui_para_get(); if(sf_is_usb_flag()) { return FALSE; } sf_battery_level_update(); if(sf_get_night_led_flag()) { if(puiPara->BatteryType == SF_BATT_ALKALINE) { lowCompareVal = 69; } else if(puiPara->BatteryType == SF_BATT_NI_MH) { lowCompareVal = 71; } } else { if(puiPara->BatteryType == SF_BATT_ALKALINE) { lowCompareVal = 80; } else if(puiPara->BatteryType == SF_BATT_NI_MH) { lowCompareVal = 80; } else { lowCompareVal = 80; } } if((IsPowerDcIn == 0) && (BatVoltageVal < lowCompareVal)) { ret = TRUE; } else { ret = FALSE; } return ret; } /****************************************************** Function: sf_battery_value_fast_get Description: auto mode:take the maximum of 5 times; manual mode:take the average of 10 times; Input: N/A Output: N/A Return: SUCCESS/FAIL Others: N/A *******************************************************/ signed int sf_battery_value_fast_get(void) { UINT8 readBatCnt = 0; UINT32 dcValueList[12] = { 0 }; UINT32 batValueList[12] = { 0 }; UIMenuStoreInfo *puiPara = sf_ui_para_get(); SINT32 ret = FAIL; //if((sf_get_mode_flag() == 0) || (needCheckFirst == TRUE)) { //printf("[%s:%d]ConfigureModeFlag=%d,needCheckFirst=%d\n",__FUNCTION__,__LINE__,sf_get_mode_flag(),needCheckFirst); //needCheckFirst = FALSE; for(readBatCnt = 0; readBatCnt < 5;) //get max value of 5 times. { if(sf_battery_adc_value_get_once() == SUCCESS) { dcValueList[readBatCnt] = _DcVoltageVal; if(puiPara->BatteryLogSwitch) { printf("%s:%d [%d]DC ADC Value=%lu,After Convert:%lu(%lu.%luV)\n", __FUNCTION__, __LINE__, readBatCnt + 1, sf_battery_convert_to_adc(10, 100, dcValueList[readBatCnt]), dcValueList[readBatCnt], dcValueList[readBatCnt] / 10, dcValueList[readBatCnt] % 10); } if(_LiPolymerVoltageVal) { batValueList[readBatCnt] = _LiPolymerVoltageVal; if(puiPara->BatteryLogSwitch) { printf("%s:%d [%d]Li Battery ADC Value=%lu,After Convert:%lu(%lu.%luV)\n", __FUNCTION__, __LINE__, readBatCnt + 1, sf_battery_convert_to_adc(15, 100, batValueList[readBatCnt]), batValueList[readBatCnt], batValueList[readBatCnt] / 10, batValueList[readBatCnt] % 10); } } else { batValueList[readBatCnt] = _BatVoltageVal; if(puiPara->BatteryLogSwitch) { printf("%s:%d [%d]Other Battery ADC Value=%lu,After Convert:%lu(%lu.%luV)\n", __FUNCTION__, __LINE__, readBatCnt + 1, sf_battery_convert_to_adc(15, 100, batValueList[readBatCnt]), batValueList[readBatCnt], batValueList[readBatCnt] / 10, batValueList[readBatCnt] % 10); } } //appTimeDelayMs(50); readBatCnt++; } } DcVoltageVal = sf_get_max_value(dcValueList); if(_LiPolymerVoltageVal) { LiPolymerVoltageVal = sf_get_max_value(batValueList); BatVoltageVal = 0; } else { BatVoltageVal = sf_get_max_value(batValueList); LiPolymerVoltageVal = 0; } if((DcVoltageVal > LiPolymerVoltageVal) && (DcVoltageVal >= BatVoltageVal) && (DcVoltageVal >= SF_DC_IN_VOLATAGE)) { IsPowerDcIn = 1; } else { IsPowerDcIn = 0; } if(puiPara->BatteryLogSwitch) { printf("\n[max]DC,After Convert:(%lu.%luV),Is Dc In=%s\n", DcVoltageVal / 10, DcVoltageVal % 10, IsPowerDcIn == 1? "Yes" : "No"); if(LiPolymerVoltageVal) { printf("[max]Li Battery,After Convert:(%lu.%luV)\n\n", LiPolymerVoltageVal / 10, LiPolymerVoltageVal % 10); } else { printf("[max]Other Battery,After Convert:(%lu.%luV)\n\n", BatVoltageVal / 10, BatVoltageVal % 10); } } ret = SUCCESS; } #if SF_BATTERY_TEST == ENABLE LiPolymerVoltageValTest = LiPolymerVoltageVal; BatVoltageValTest = BatVoltageVal; #endif return ret; } /************************************************* Function: sf_battery_level_polling Description: polling battery level Input: N/A Output: N/A Return: N/A Others: N/A *************************************************/ void sf_battery_level_polling(void) { UINT16 readBatCnt = 0; UINT32 dcTemp = 0; UINT32 batTemp = 0; UINT32 LibatTemp = 0; UINT8 LibatCnt = 0; UINT8 batCnt = 0; UIMenuStoreInfo *puiPara = sf_ui_para_get(); static UINT32 prePowerDcStatus = 0; //signed int ret = FALSE; static UINT32 battEmpty = 0; for(readBatCnt = 0; readBatCnt < 100;) //get average value of 100 times. { if(sf_battery_adc_value_get_once() == SUCCESS) { vos_util_delay_ms(100); dcTemp += _DcVoltageVal; if(_LiPolymerVoltageVal) { LibatTemp += _LiPolymerVoltageVal; batCnt++; } else { batTemp += _BatVoltageVal; LibatCnt++; } readBatCnt++; if(readBatCnt >= 100) { _DcVoltageVal = dcTemp / 100; if(LibatCnt) _LiPolymerVoltageVal = LibatTemp / LibatCnt; if(batCnt) _BatVoltageVal = batTemp / batCnt; if((_DcVoltageVal > _LiPolymerVoltageVal) && (_DcVoltageVal >= _BatVoltageVal) && (_DcVoltageVal >= SF_DC_IN_VOLATAGE)) { IsPowerDcIn = 1; } else { IsPowerDcIn = 0; } if ((_LiPolymerVoltageVal > _BatVoltageVal)) { _BatVoltageVal = 0; } else { _LiPolymerVoltageVal = 0; } DcVoltageVal = _DcVoltageVal; LiPolymerVoltageVal = _LiPolymerVoltageVal; BatVoltageVal = _BatVoltageVal; if(puiPara->BatteryLogSwitch) { printf("\n[average]DC,After Convert:(%lu.%luV),Is Dc In=%s\n", DcVoltageVal / 10, DcVoltageVal % 10, IsPowerDcIn == 1? "Yes" : "No"); if(LiPolymerVoltageVal) { printf("[average]Li Battery,After Convert:(%lu.%luV)\n\n", LiPolymerVoltageVal / 10, LiPolymerVoltageVal % 10); } else { printf("[average]Other Battery,After Convert:(%lu.%luV)\n\n", BatVoltageVal / 10, BatVoltageVal % 10); } } } } } sf_battery_level_update(); //ret = sf_check_low_battery(); if(puiPara->BatteryLogSwitch) { printf("[%s:%d]batTempLevel=%lu,sf_LatestBattLevel=%d\n", __FUNCTION__, __LINE__, batTempLevel, sf_LatestBattLevel); } if((batTempLevel != sf_LatestBattLevel) || IsPowerDcIn != prePowerDcStatus) { prePowerDcStatus = IsPowerDcIn; batTempLevel = sf_LatestBattLevel; #if HW_S530 sf_view_osd_battery_draw(TRUE); #endif } if(sf_LatestBattLevel == SF_BATT_LEVEL_0) { if(sf_get_night_led_flag()) { sf_ir_led_set(0, 0, 0, 0); //pwm_pwm_disable(IRLED_PWMID); //printf("%s:%d \n", __FUNCTION__, __LINE__); } //the Module not need sleep. //gModuleSleep = 0; sf_set_module_sleep_flag(0); if(battEmpty == 0) { battEmpty = 1; printf("[%s:%d]power off because low battery\n", __FUNCTION__, __LINE__); //Ux_PostEvent(NVTEVT_SYSTEM_SHUTDOWN, 1, APP_POWER_OFF_BATT_EMPTY); //shutdown start #if SF_IQ_TEST != ENABLE sf_set_power_off_flag(1); flow_preview_set_stop_flag(TRUE); #endif } } else if(sf_LatestBattLevel == SF_BATT_LEVEL_1) { if((sf_battery_value_get(sf_get_night_led_flag()) < 10)/* && (sf_led_get(SF_LED_BAT1) != SF_LED_STATE_SLOW_FLASHING)*/) { printf("[%s:%d] SF_LED_BAT1 SF_LED_STATE_SLOW_FLASHING\n", __FUNCTION__, __LINE__); //sf_led_set(SF_LED_BAT1, SF_LED_STATE_SLOW_FLASHING); sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_0_SLOW); } else if((sf_battery_value_get(sf_get_night_led_flag()) == 10) /*&& (sf_led_get(SF_LED_BAT1) != SF_LED_STATE_ON)*/) { printf("[%s:%d] SF_LED_BAT1 SF_LED_STATE_SLOW_FLASHING\n", __FUNCTION__, __LINE__); //sf_led_set(SF_LED_BAT1, SF_LED_STATE_ON); sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_1); } } else { } } THREAD_RETTYPE sf_battery_check_thread(void *arg) { THREAD_ENTRY(); printf("[%s:%d] s\n", __FUNCTION__, __LINE__); if(sf_is_battery_low(1, 0) == TRUE) { printf("[%s:%d]power off because low battery\n", __FUNCTION__, __LINE__); //Ux_PostEvent(NVTEVT_SYSTEM_SHUTDOWN, 1, APP_POWER_OFF_BATT_EMPTY); //shutdown start #if SF_IQ_TEST != ENABLE sf_set_power_off_flag(1); flow_preview_set_stop_flag(TRUE); #endif } else { while(sf_while_flag()) { sf_battery_level_polling(); } } printf("[%s:%d] e \n", __FUNCTION__, __LINE__); THREAD_RETURN(0); } void sf_battery_thread_init(void) { static UINT8 dofirst = 1; printf("[%s:%d] s\n", __FUNCTION__, __LINE__); if(!dofirst) return; dofirst = 0; VK_TASK_HANDLE s_handle_batt = 0; vos_flag_create(&FLG_ID_SF_BSTTERY, NULL, "FLG_ID_SF_BSTTERY"); /*thread creat*/ s_handle_batt = vos_task_create(sf_battery_check_thread, NULL, "sf_battery_check_thread", 25, 2048); vos_task_resume(s_handle_batt); printf("[%s:%d] e\n", __FUNCTION__, __LINE__); } UINT8 sf_get_night_led_flag(void) { return IsNightLedOn; } void sf_set_night_led_flag(UINT8 flag) { IsNightLedOn = flag; } /************************************************* Function: sf_battery_level_get Description: get battery level Input: N/A Output: N/A Return: SUCCESS/FAIL Others: N/A *************************************************/ UINT32 sf_battery_level_get(void) { return (UINT32)sf_LatestBattLevel; } void sf_view_osd_battery_draw(UINT8 bShow) { printf("[%s:%d] s\n", __FUNCTION__, __LINE__); #if HW_S530 if(!sf_get_mode_flag()) { return; } if(bShow) { switch(sf_battery_level_get()) { case SF_BATT_LEVEL_0: sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_0); break; case SF_BATT_LEVEL_1: sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_1); break; case SF_BATT_LEVEL_2: sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_2); break; case SF_BATT_LEVEL_3: sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_3); break; case SF_BATT_LEVEL_4: sf_sys_status_led_set(SF_LED_SYS_STATE_BAT_4); break; default: break; } } #endif printf("[%s:%d] e\n", __FUNCTION__, __LINE__); } /************************************************* Function: sf_battery_value_get Description: get battery value x% Input: nightMode or no Output: N/A Return: battery value x% Others: N/A *************************************************/ UINT8 sf_battery_value_get(UINT8 nightMode) { UINT8 value = 0; UINT8 batteryVal = 0; UIMenuStoreInfo *puiPara = sf_ui_para_get(); if(IsPowerDcIn == 0) { //printf("BatMedian:%d\n", BatMedian); if(LiPolymerVoltageVal) { batteryVal = LiPolymerVoltageVal; if(batteryVal < 65) { if(nightMode && (batteryVal >= 43)) value = 1; else value = 0; } else if(batteryVal < 71) { value = 1; } else if(batteryVal < 72) { value = 10; } else if(batteryVal < 73) { value = 20; } else if(batteryVal < 74) { value = 30; } else if(batteryVal < 75) { value = 40; } else if(batteryVal < 76) { value = 50; } else if(batteryVal < 77) { value = 60; } else if(batteryVal < 78) { value = 70; } else if(batteryVal < 79) { value = 80; } else if(batteryVal < 81) { value = 90; } else { value = 100; } } else { batteryVal = BatVoltageVal; if(puiPara->BatteryType == SF_BATT_ALKALINE) //ALK { if(batteryVal < 62) { if(nightMode && (batteryVal >= 43)) value = 1; else value = 0; } else if(batteryVal < 65) { value = 1; } else if(batteryVal < 69) { value = 10; } else if(batteryVal < 71) { value = 20; } else if(batteryVal < 72) { value = 30; } else if(batteryVal < 73) { value = 40; } else if(batteryVal < 75) { value = 50; } else if(batteryVal < 76) { value = 60; } else if(batteryVal < 78) { value = 70; } else if(batteryVal < 80) { value = 80; } else if(batteryVal < 83) { value = 90; } else { value = 100; } } else if(puiPara->BatteryType == SF_BATT_NI_MH) //NIH { if(batteryVal < 60) { if(nightMode && (batteryVal >= 43)) value = 1; else value = 0; } else if(batteryVal < 61) { value = 1; } else if(batteryVal < 62) { value = 10; } else if(batteryVal < 64) { value = 20; } else if(batteryVal < 65) { value = 30; } else if(batteryVal < 67) { value = 40; } else if(batteryVal < 68) { value = 50; } else if(batteryVal < 70) { value = 60; } else if(batteryVal < 71) { value = 70; } else if(batteryVal < 73) { value = 80; } else if(batteryVal < 75) { value = 90; } else { value = 100; } } else { if(batteryVal < 62) { if(nightMode && (batteryVal >= 43)) value = 1; else value = 0; } else if(batteryVal < 75) { value = 1; } else if(batteryVal < 80) { value = 10; } else if(batteryVal < 82) { value = 20; } else if(batteryVal < 83) { value = 30; } else if(batteryVal < 84) { value = 40; } else if(batteryVal < 86) { value = 50; } else if(batteryVal < 91) { value = 60; } else if(batteryVal < 92) { value = 70; } else if(batteryVal < 93) { value = 80; } else if(batteryVal < 94) { value = 90; } else { value = 100; } } } } else { value = 100; } return value; } /************************************************* Function: sf_battery_type_get Description: Get battery type. Input: N/A Output: N/A Return: value: battery type, 0:normal 1:LiPolymer Others: N/A *************************************************/ UINT8 sf_battery_type_get(void) { if(IsPowerDcIn) return SF_POWER_TYPE_DC; else if(LiPolymerVoltageVal) return SF_POWER_TYPE_LI_POLYER; else return SF_POWER_TYPE_AA; } /************************************************* Function: sf_is_battery_low Description: Judge whether the power is low Input: refresh:refresh ADC acquisition or no, nightMode:day or night Output: N/A Return: TRUE/FALSE Others: N/A *************************************************/ BOOL sf_is_battery_low(UINT8 refresh, UINT8 nightMode) { UINT8 batteryVal = 0; UINT8 batteryLevel = 0; if(refresh) { sf_battery_value_fast_get(); //printf("DC=%d Custom=%d bat=%d\n", dcValue, CustomValue, batli8v); } batteryVal = sf_battery_value_get(nightMode); if(!sf_get_mode_flag()) { if(batteryVal >= 70) { batteryLevel = SF_BATT_LEVEL_4; } else if(batteryVal >= 40) { batteryLevel = SF_BATT_LEVEL_3; } else if(batteryVal >= 20) { batteryLevel = SF_BATT_LEVEL_2; } else if(batteryVal >= 1) { batteryLevel = SF_BATT_LEVEL_1; } else { batteryLevel = SF_BATT_LEVEL_0; } sf_LatestBattLevel = batteryLevel; } if(batteryVal == 0) return TRUE; return FALSE; } /************************************************* Function: sf_battery_check_init Description: Perform a battery test in manual mode. Input: N/A Output: N/A Return: value: TRUE ,FALSE Others: N/A *************************************************/ BOOL sf_battery_check_init(void) { sf_adc_init(); if(sf_is_battery_low(1, 0) == TRUE) { printf("[%s:%d]power off because low battery\n", __FUNCTION__, __LINE__); //Ux_PostEvent(NVTEVT_SYSTEM_SHUTDOWN, 1, APP_POWER_OFF_BATT_EMPTY); //shutdown start #if SF_IQ_TEST != ENABLE sf_set_power_off_flag(1); flow_preview_set_stop_flag(TRUE); #endif } return TRUE; } void sf_set_need_check_first(void) { needCheckFirst = TRUE; } /************************************************* Function: sf_is_enough_power_to_update Description: whether or not enough power to update Input: N/A Output: N/A Return: TRUE/FALSE Others: N/A *************************************************/ BOOL sf_is_enough_power_to_update(void) { //sf_set_need_check_first(); sf_battery_value_fast_get(); printf("update DC=%lu Li=%lu Bat=%lu\n", DcVoltageVal, LiPolymerVoltageVal, BatVoltageVal); if(sf_battery_value_get(0) < 40) { printf("low battery, no update\n"); return FALSE; } return TRUE; } #if SF_BATTERY_TEST == ENABLE void sf_BatteryInfoSave(char *name) { char *tmpBuf = NULL; UINT32 LibatAdc = 0; UINT32 batAdc = 0; //char fileName[64] = {0}; int fd = 0; struct stat st; tmpBuf = malloc(512); if (tmpBuf == NULL) { printf("%s:%d tmpBuf malloc err\n", __FUNCTION__, __LINE__); return; } //snprintf(fileName, sizeof(fileName), "%s", SF_BATTERY_TEST_FILE); if(access(SF_BATTERY_TEST_FILE, F_OK) == 0) { printf("fileName:%s\n",SF_BATTERY_TEST_FILE); fd = open(SF_BATTERY_TEST_FILE, O_APPEND | O_WRONLY); } else { fd = open(SF_BATTERY_TEST_FILE, O_APPEND | O_WRONLY | O_CREAT); } LibatAdc = sf_battery_convert_to_adc(15, 100, LiPolymerVoltageValTest); batAdc = sf_battery_convert_to_adc(15, 100, BatVoltageValTest); sprintf(tmpBuf, "%s BatAdc=%lu BatVal=%lu LiBatAdc=%lu LiBatVal=%lu\r\n", name, batAdc, BatVoltageValTest, LibatAdc, LiPolymerVoltageValTest); printf("%s\r", tmpBuf); if(fd) { fstat(fd, &st); lseek(fd, 0, SEEK_END); write(fd, tmpBuf, strlen(tmpBuf)); close(fd); printf("Add Success st_size:%ld\n", st.st_size); } free(tmpBuf); } #endif #endif