Files
checker_slave/source/elec_det/elec_det.c
ranchuan cbbb2af298 解决自动更新bootloader死机的问题
软件版本2.00
解决检测任务中重试失败后不会填充返回值的bug
2023-10-16 18:53:12 +08:00

462 lines
10 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "board.h"
#include "bytearray.h"
#include "mystdlib.h"
#include "mystring.h"
#include "debug.h"
#include "stdlib.h"
#include "dev_flash.h"
#include "elec_det.h"
#include "base/delay.h"
#include "base/utility.h"
#include "hardware/adc_cfg.h"
#include "hardware/dac_cfg.h"
#include "hardware/gpio_cfg.h"
#include "hardware/jw3425iic.h"
#include "hardware/power.h"
#include "hardware/timer_cfg.h"
#include "driver/EWDriver.h"
#include "driver/JQDriver.h"
#include "driver/XTDriver.h"
#include "interface/BaseChecker.h"
#include "interface/JQChecker.h"
#include "interface/XTChecker.h"
#include "interface/EWChecker.h"
#define PLAN_MAX_TASK 64
typedef struct{
CheckerTask_Info_st* task_info_array[PLAN_MAX_TASK];//方案参数结构体指针
int task_num;
int scheme_inited;
array_def *data;
}self_def;
static self_def g_self;
int elec_check_scheme(void);
void elec_load_scheme(void);
int elec_parper_power(void);
// 初始化
int elec_init(void)
{
void Ye_BoardInit(void);
Ye_BoardInit();
elec_bootinfo();
DBG_LOG("local addr:%d.",elec_local_addr());
return elec_scheme_init();
}
// 初始化方案
int elec_scheme_init(void)
{
self_def *s=&g_self;
int ret=0;
if(elec_check_scheme()!=0){
// 方案校验失败
DBG_WARN("scheme check failed.");
s->scheme_inited=0;
return 1;
}
s->scheme_inited=1;
elec_load_scheme();
ret=elec_parper_power();
return ret;
}
// 调压
static int elec_parper_power(void)
{
self_def *s=&g_self;
CheckerTask_Info_st *task_par=0;
int ret=0;
task_par= s->task_info_array[0];
if(task_par->taskid!=0){
// 第一个任务不是调压任务,失败
DBG_WARN("parper power failed,first taskid is not 0.");
return 1;
}
// 装载参数
checker_runcfg.power_prapare_exe=0;
rt_memcpy(&checker_runcfg.task_info,task_par,sizeof(CheckerTask_Info_st));
checker_runcfg.param_count = checker_runcfg.task_info.param_rtv_count & 0x0F;
checker_runcfg.rtv_count = (checker_runcfg.task_info.param_rtv_count >> 4) & 0x0F;
rt_memcpy(checker_runcfg.params,checker_runcfg.task_info.params,checker_runcfg.param_count*2);
Checker_PowerPrapare();
ret=checker_runcfg.excue_rtv;
if(ret){
DBG_WARN("parper power failed,ret=%d.",ret);
}else{
checker_runcfg.power_prapare_exe=1;
}
JQBUS_OFF;
delay_ms(20);
PowerCalibration_set(POWER_DEF_V,POWER_DEF_V-10);
return ret;
}
// 获取本机地址
uint8_t elec_local_addr(void)
{
static uint8_t addr=0;
if(addr==0){
addr=Gpio_GetDeivceAddr();
}
return addr;
}
// 设置led1状态
void elec_led1_power(int power)
{
LED1_Out=power?0:1;
}
// 设置led2状态
void elec_led2_power(int power)
{
LED2_Out=power?0:1;
}
// 获取自检参数
array_def *elec_bootinfo(void)
{
void Ye_BoardCheck(void);
Ye_BoardCheck();
board_st.hard_v=sys_param()->hard_version;
board_st.resistor_diff=sys_param()->resistor_diff;
board_st.hard_v=19;
array_def *r=arr_creat();
arr_append(r,0);
arr_appends(r,&board_st,sizeof(BoartCheck_st));
return arr_temp(r);
}
// 获取检测结果
array_def *elec_check_result(void)
{
self_def *s=&g_self;
array_def *r=0;
if(s->data){
r=arr_duplicate(s->data);
}
return arr_temp(r);
}
// 写硬件版本号
array_def *elec_write_hardversion(int version)
{
sys_param_def *spar=0;
spar=calloc(1,sizeof(sys_param_def));
memcpy(spar,sys_param(),sizeof(sys_param_def));
spar->hard_version=version;
flash_save_param(spar);
free(spar);
board_st.hard_v=version;
array_def *r=arr_creat();
arr_append(r,0);
return arr_temp(r);
}
// 写电阻校准值
array_def *elec_write_resistor_cbv(int cbv)
{
sys_param_def *spar=0;
spar=calloc(1,sizeof(sys_param_def));
memcpy(spar,sys_param(),sizeof(sys_param_def));
spar->resistor_diff=cbv;
flash_save_param(spar);
free(spar);
board_st.resistor_diff=cbv;
array_def *r=arr_creat();
arr_append(r,0);
return arr_temp(r);
}
// 写缓存
array_def *elec_write_fat_buff(array_def *d)
{
int ret=0;
int num=arr_length(d);
if(num<CHECKER_FAC_BUF_LEN){
memcpy(Checker_FacBuf,arr_data(d),num);
DBG_LOG("facbuf:%s.",str_temp(arr_string(d)));
ret=0;
}else{
ret=1;
}
array_def *r=arr_creat();
arr_append(r,ret);
return arr_temp(r);
}
// 测量桥丝阻值
array_def *elec_check_resistor(void)
{
/*
1 通道1-4通过桥丝
2 通道2-3通过桥丝
3 通道1-3通测阻抗
4 通道2-4通测阻抗
*/
uint16_t aus_sample[5];
uint16_t us_resistor;
uint8_t uc_index = 0;
AD_SampleResistor(aus_sample);
for(uc_index = 0; uc_index < 5; uc_index++)
{
aus_sample[uc_index] -= board_st.resistor_diff;
}
// 读取方案中测量电阻的模式
switch(0)
{
case 0: us_resistor = aus_sample[0];break;
case 1: us_resistor = aus_sample[1];break;
case 2: us_resistor = aus_sample[2];break;
default : us_resistor = 0;break;
}
array_def *r=arr_creat();
arr_append(r,0);
arr_append(r,us_resistor&0xff);
arr_append(r,(us_resistor >> 8) & 0xff);
return arr_temp(r);
}
// 校验方案,返0成功
static int elec_check_scheme(void)
{
uint32_t ul_crc32;
ul_crc32 = Crc32Calu((uint32_t*)APP_TEST_PLAN_ADDR,(APP_TEST_PLANINFO_SIZE-4));
if(ul_crc32 != (*(uint32_t*)(APP_TEST_PLAN_ADDR+APP_TEST_PLANINFO_SIZE-4)))
{
board_st.plan_id = ~0;
LED1_Out_Off;
return 1;
}else{
board_st.plan_id = *((uint32_t*)APP_TEST_PLAN_ADDR);
}
return 0;
}
// 加载方案
static void elec_load_scheme(void)
{
self_def *s=&g_self;
uint8_t uc_index = 0;
uint32_t ul_len;
CheckerTask_Info_st* pinfo_st = (CheckerTask_Info_st*)(APP_TEST_PLAN_ADDR+256);
for(uc_index = 0; uc_index < PLAN_MAX_TASK; uc_index++)
{
s->task_info_array[uc_index] = 0;
}
uc_index = 0;
s->task_num=0;
while((pinfo_st->runindex != 0xFF) && (uc_index < PLAN_MAX_TASK))
{
s->task_info_array[uc_index++] = pinfo_st;
s->task_num++;
ul_len = pinfo_st->param_rtv_count & 0x0F;
ul_len = (ul_len<<1)+5;
pinfo_st = (CheckerTask_Info_st*)((uint8_t*)pinfo_st + ul_len);
}
}
// 注码 参数校验
static int elec_code_param_check(array_def *uid_psw)
{
if((uid_psw==0)||(arr_length(uid_psw)==0)){
return 1;
}
if(arr_length(uid_psw)!=(arr_get(uid_psw,0)+arr_get(uid_psw,1)+3)){
return 2;
}
if(arr_get(uid_psw,2)!=0){
return 3;
}
if((arr_get(uid_psw,0)>13)||(arr_get(uid_psw,1)>8)){
return 4;
}
return 0;
}
// 注码 准备参数
static int elec_code_load_param(array_def *uid_psw)
{
uint8_t pwd_len=0,uid_len=0;
uid_len = arr_get(uid_psw,0);
pwd_len = arr_get(uid_psw,1);
checker_runcfg.uid_len=uid_len;
checker_runcfg.pwd_len=pwd_len;
memcpy(checker_runcfg.writeuid,arr_data(uid_psw)+3,uid_len);
memcpy(checker_runcfg.writepwd,arr_data(uid_psw)+3+uid_len,pwd_len);
return 0;
}
// 检测 准备参数
static int elec_check_load_task_param(uint8_t taskid,
CheckerTask_Info_st *task_par,CheckerTask task_fun)
{
memset(&checker_runcfg.task_info,0,sizeof(CheckerTask_Info_st));
memset(checker_runcfg.params,0,20);
checker_runcfg.param_count = 0;//参数个数
checker_runcfg.rtv_count = 0;//返回值个数
checker_runcfg.excue_rtv = 0;
checker_runcfg.task_info.retry_time = 0;
if(taskid>=CHECKER_MAXID_COUNT){
DBG_WARN("taskid=%d out of bound.",taskid);
return 1;
}
if(task_par==0){
DBG_WARN("can not find task params.");
return 2;
}
if(task_fun==0){
DBG_WARN("can not find task fun.");
return 3;
}
// 装载参数
memcpy(&checker_runcfg.task_info,task_par,sizeof(CheckerTask_Info_st));
checker_runcfg.param_count = checker_runcfg.task_info.param_rtv_count & 0x0F;
checker_runcfg.rtv_count = (checker_runcfg.task_info.param_rtv_count >> 4) & 0x0F;
memcpy(checker_runcfg.params,checker_runcfg.task_info.params,checker_runcfg.param_count*2);
return 0;
}
// 进行检测
array_def *elec_check_with_scheme(array_def *uid_psw)
{
self_def *s=&g_self;
const uint8_t* taskid_table = (uint8_t*)(APP_TEST_PLAN_ADDR+4);
CheckerTask *tasks_fun_table[]={jqtaskArray,xttaskArray,ewtaskArray};
CheckerTask_Info_st *task_par=0;
uint8_t chip_type=0;
uint8_t taskid=0;
CheckerTask task_fun=0;
uint8_t res=0;
array_def *r=arr_creat();
CHECK_DO(s->data,arr_delete);
res=checker_runcfg.power_prapare_exe;
memset(&checker_runcfg,0,sizeof(Checker_RunCfg_st));
checker_runcfg.power_prapare_exe=res;
chip_type=(board_st.plan_id >> 12 ) & 0x0F;
if(elec_code_param_check(uid_psw)==0){
elec_code_load_param(uid_psw);
}
if(s->scheme_inited==0){
DBG_WARN("scheme not init.");
arr_append(r,1);
return arr_temp(r);
}
if(chip_type>=LENGTH(tasks_fun_table)){
DBG_WARN("unknown chip type.");
arr_append(r,2);
return arr_temp(r);
}
int task_index=0;
LED1_Out_Off;
while(task_index<s->task_num){
taskid=taskid_table[task_index];
task_fun=tasks_fun_table[chip_type][taskid];
task_par= s->task_info_array[task_index];
if(elec_check_load_task_param(taskid,task_par,task_fun)){
break;
}
// 执行任务
for(int i=0;i<1+task_par->retry_time;i++)
{
checker_runcfg.excue_rtv=1;
task_fun();
Checker_Excueindex(task_index);
if(checker_runcfg.excue_rtv==0)
break;
checker_runcfg.rtv_index-=checker_runcfg.rtv_count;
}
if(checker_runcfg.excue_rtv){
checker_runcfg.rtv_index+=checker_runcfg.rtv_count;
}
DBG_LOG("task_index:%d,taskid:%d,ret=%d,rtv_index=%d.",task_index,taskid,checker_runcfg.excue_rtv,
checker_runcfg.rtv_index);
// 找寻下一个任务
task_index++;
if(checker_runcfg.excue_rtv != 0){
uint8_t err_to=checker_runcfg.task_info.error_jumpto;
uint8_t temp;
if(err_to==0xff) continue;
if(err_to>s->task_num-1) err_to=s->task_num-1;
for(;task_index<err_to;task_index++){
Checker_MaskResult(1,task_index);
temp=(s->task_info_array[task_index]->param_rtv_count >> 4) & 0x0F;
checker_runcfg.rtv_index+=temp;
}
}
}
arr_append(r,0);
arr_appends(r,checker_runcfg.Task_Result,8);
arr_appends(r,checker_runcfg.Task_Excute,8);
arr_appends(r,checker_runcfg.Test_Rtv,checker_runcfg.rtv_index*2);
s->data=arr_duplicate(r);
return arr_temp(r);
}
// 单独注码
array_def *elec_code(array_def *uid_psw)
{
self_def *s=&g_self;
array_def *r=arr_creat();
uint8_t ret=0;
int check_ret=0;
CHECK_DO(s->data,arr_delete);
check_ret=elec_code_param_check(uid_psw);
if(check_ret){
arr_append(r,check_ret);
return arr_temp(r);
}
elec_code_load_param(uid_psw);
ret = XT_UID_PWD_Bind();
arr_append(r,ret);
s->data=arr_duplicate(r);
return arr_temp(r);
}