feat: implement iv_cycle mode
This commit is contained in:
@@ -49,6 +49,7 @@
|
||||
<PreprocessorDefinitions>DEBUG=1;USE_APP_CONFIG=1;LFS_THREADSAFE=1;%(ClCompile.PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalOptions />
|
||||
<CPPLanguageStandard />
|
||||
<Optimization>O0</Optimization>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalLinkerInputs>;%(Link.AdditionalLinkerInputs)</AdditionalLinkerInputs>
|
||||
@@ -57,6 +58,16 @@
|
||||
<LinkerScript>nRF52840_XXAA_S140_reserve.lds</LinkerScript>
|
||||
<AdditionalOptions />
|
||||
</Link>
|
||||
<ToolchainSettingsContainer>
|
||||
<InstructionSet>THUMB</InstructionSet>
|
||||
</ToolchainSettingsContainer>
|
||||
<ToolchainSettingsContainer>
|
||||
<FloatABI>hard</FloatABI>
|
||||
</ToolchainSettingsContainer>
|
||||
<ToolchainSettingsContainer>
|
||||
<ARMFPU>fpv4-sp-d16</ARMFPU>
|
||||
<ARMCPU>cortex-m4</ARMCPU>
|
||||
</ToolchainSettingsContainer>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|VisualGDB'">
|
||||
<ClCompile>
|
||||
@@ -188,6 +199,7 @@
|
||||
<ClCompile Include="elite_board.c" />
|
||||
<ClCompile Include="dac_drv.c" />
|
||||
<ClCompile Include="elite_dev.c" />
|
||||
<ClCompile Include="edc20_cycle_iv_mode.c" />
|
||||
<ClCompile Include="fs.c" />
|
||||
<ClCompile Include="gd25d10c.c" />
|
||||
<ClCompile Include="max5136.c" />
|
||||
|
||||
@@ -1431,6 +1431,18 @@
|
||||
<ClCompile Include="pel10_io.c">
|
||||
<Filter>Source files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="btn.c">
|
||||
<Filter>Source files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="elite_dev.c">
|
||||
<Filter>Source files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="pel.c">
|
||||
<Filter>Source files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="edc20_cycle_iv_mode.c">
|
||||
<Filter>Source files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="nRF52840_XXAA_S140_reserve.lds">
|
||||
@@ -1777,6 +1789,15 @@
|
||||
<ClInclude Include="pel10_io.h">
|
||||
<Filter>Header files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="btn.h">
|
||||
<Filter>Header files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="elite_dev.h">
|
||||
<Filter>Header files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="pel.h">
|
||||
<Filter>Header files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\bmd380_sdk\external\segger_rtt\license\license.txt">
|
||||
|
||||
+4
-4
@@ -5,10 +5,10 @@
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define DAC0 (0x01 << 0)
|
||||
#define DAC1 (0x01 << 1)
|
||||
#define DAC2 (0x01 << 2)
|
||||
#define DAC3 (0x01 << 3)
|
||||
#define DAC0 (0x01 << 0)
|
||||
#define DAC1 (0x01 << 1)
|
||||
#define DAC2 (0x01 << 2)
|
||||
#define DAC3 (0x01 << 3)
|
||||
|
||||
typedef struct
|
||||
{
|
||||
|
||||
@@ -109,6 +109,27 @@ typedef struct
|
||||
} instru;
|
||||
} edc20_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
float coeff;
|
||||
float offset;
|
||||
} edc20_cal_data_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
struct
|
||||
{
|
||||
float coeff;
|
||||
float offset;
|
||||
} dac_c;
|
||||
struct
|
||||
{
|
||||
float coeff;
|
||||
float offset;
|
||||
float Voffset;
|
||||
} dac_f[3];
|
||||
} edc20_dac_cal_data_t;
|
||||
|
||||
extern edc20_t edc;
|
||||
|
||||
#endif // !__EDC_H__
|
||||
|
||||
@@ -932,7 +932,13 @@ static void vis_shiny_dis(uint8_t *ins, uint16_t size)
|
||||
}
|
||||
|
||||
static void curve_iv(uint8_t *ins, uint16_t size) { NRF_LOG_INFO("%s", __FUNCTION__); }
|
||||
static void curve_iv_cy(uint8_t *ins, uint16_t size) { NRF_LOG_INFO("%s", __FUNCTION__); }
|
||||
static void curve_iv_cy(uint8_t *ins, uint16_t size)
|
||||
{
|
||||
NRF_LOG_INFO("%s", __FUNCTION__);
|
||||
extern void edc20_cycle_iv_mode_start(uint8_t * ins, uint16_t size);
|
||||
edc20_cycle_iv_mode_start(ins, size);
|
||||
}
|
||||
|
||||
static void curve_vo(uint8_t *ins, uint16_t size) { NRF_LOG_INFO("%s", __FUNCTION__); }
|
||||
static void curve_rt(uint8_t *ins, uint16_t size) { NRF_LOG_INFO("%s", __FUNCTION__); }
|
||||
static void curve_vt(uint8_t *ins, uint16_t size) { NRF_LOG_INFO("%s", __FUNCTION__); }
|
||||
|
||||
@@ -0,0 +1,483 @@
|
||||
#include "app_config.h"
|
||||
#include "edc.h"
|
||||
#include "elite_board.h"
|
||||
|
||||
#include "dac_drv.h"
|
||||
|
||||
#include "nrf.h"
|
||||
#include "nrf_log.h"
|
||||
|
||||
#include "FreeRTOS.h"
|
||||
#include "elite_board.h"
|
||||
#include "semphr.h"
|
||||
#include "task.h"
|
||||
|
||||
#include <math.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#if (DEF_ELITE_MODEL == DEF_ELITE_EDC_20)
|
||||
|
||||
#define OUT_0 DAC0
|
||||
#define OUT_1 DAC1
|
||||
|
||||
typedef struct __PACKED
|
||||
{
|
||||
uint32_t notify_time;
|
||||
int32_t ch1_data;
|
||||
int32_t ch2_data;
|
||||
int32_t ch3_data;
|
||||
uint16_t cycle;
|
||||
uint8_t finish_flag;
|
||||
uint32_t bat_volt;
|
||||
uint8_t packet_seq;
|
||||
int32_t ch4_data;
|
||||
int32_t ch5_data;
|
||||
int32_t ch6_data;
|
||||
} payload_t;
|
||||
|
||||
typedef struct __PACKED
|
||||
{
|
||||
uint8_t mem_board_id;
|
||||
payload_t payload;
|
||||
uint8_t : 8;
|
||||
uint8_t : 8;
|
||||
uint8_t : 8;
|
||||
} elite_notify_packet_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint32_t id;
|
||||
uint32_t mS_period;
|
||||
elite_dac_config_t config;
|
||||
} iv_cycle_mode_param_t;
|
||||
|
||||
const edc20_dac_cal_data_t edc20_dac_cal_data = {
|
||||
.dac_c = { 2.9701475, 121.9763670 },
|
||||
.dac_f = {
|
||||
[0] = { 65.7454092, -290.3872456, -36.65060000 },
|
||||
[1] = { 27.4300538, -100.6332479, -37.39872222 },
|
||||
[2] = { 7.61192880, -0.568019000, -40.99282222 } }
|
||||
};
|
||||
#define FS_1000mV 1000
|
||||
#define FS_2800mV 2800
|
||||
#define FS_8000mV 8000
|
||||
const float edc20_range_mV[] = {
|
||||
[0] = FS_1000mV,
|
||||
[1] = FS_2800mV,
|
||||
[2] = FS_8000mV,
|
||||
};
|
||||
|
||||
static SemaphoreHandle_t semphr_start = NULL;
|
||||
|
||||
static TaskHandle_t task_handle = NULL;
|
||||
|
||||
static bool running = false;
|
||||
|
||||
extern ret_code_t le_event_notify(uint8_t *p_value, uint16_t len);
|
||||
|
||||
static ret_code_t _send_start_packet(elite_notify_packet_t *p_buf, uint32_t loops)
|
||||
{
|
||||
memset(&p_buf->payload, 0x00, sizeof(p_buf->payload));
|
||||
for (uint32_t i = 0; i < loops; i++)
|
||||
{
|
||||
ret_code_t ret = le_event_notify((void *)p_buf, sizeof(*p_buf));
|
||||
if (ret != NRF_SUCCESS)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
return NRF_SUCCESS;
|
||||
}
|
||||
|
||||
static ret_code_t _send_data_packet(elite_notify_packet_t *p_notify_buf, bool is_last_notify)
|
||||
{
|
||||
static int32_t ch1 = 0;
|
||||
static int32_t ch2 = 0;
|
||||
static int32_t ch3 = 0;
|
||||
|
||||
ch1 += 100;
|
||||
ch2++;
|
||||
ch3 = ch2;
|
||||
|
||||
p_notify_buf->payload.notify_time = xTaskGetTickCount();
|
||||
p_notify_buf->payload.ch1_data = ch1;
|
||||
p_notify_buf->payload.ch2_data = ch2;
|
||||
p_notify_buf->payload.ch3_data = ch3;
|
||||
p_notify_buf->payload.bat_volt = 3600;
|
||||
p_notify_buf->payload.packet_seq++;
|
||||
p_notify_buf->payload.finish_flag = is_last_notify;
|
||||
|
||||
return le_event_notify((void *)p_notify_buf, sizeof(*p_notify_buf));
|
||||
}
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int32_t dir;
|
||||
float mV_output;
|
||||
float mV_max;
|
||||
float mV_min;
|
||||
float mV_start;
|
||||
float mV_stop;
|
||||
uint32_t step;
|
||||
uint32_t cycle_cnt;
|
||||
uint32_t cycle_max;
|
||||
uint32_t fullscale;
|
||||
struct
|
||||
{
|
||||
float eta_c;
|
||||
float eta_f;
|
||||
float Voffset;
|
||||
float Vc;
|
||||
float Nc;
|
||||
float Nc0;
|
||||
float Nf;
|
||||
};
|
||||
} cycle_iv_dac_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint32_t period;
|
||||
} cycle_iv_adc_t;
|
||||
|
||||
static uint32_t mV_out_0(cycle_iv_dac_t *p)
|
||||
{
|
||||
for (uint32_t i = 0; i < COUNTOF(edc20_range_mV); i++)
|
||||
{
|
||||
if ((p->mV_max - p->mV_min) <= edc20_range_mV[i])
|
||||
{
|
||||
p->fullscale = edc20_range_mV[i];
|
||||
p->eta_c = edc20_dac_cal_data.dac_c.coeff;
|
||||
p->eta_f = edc20_dac_cal_data.dac_f[i].coeff;
|
||||
p->Voffset = edc20_dac_cal_data.dac_f[i].Voffset;
|
||||
break;
|
||||
}
|
||||
}
|
||||
p->Vc = (p->mV_max + p->mV_min) / 2;
|
||||
p->Nc = round((p->Vc - p->Voffset) * p->eta_c) + 32768;
|
||||
p->Nc0 = round((0 - p->Voffset) * p->eta_c) + 32768;
|
||||
return p->Nc;
|
||||
}
|
||||
|
||||
static uint32_t mV_out_1(cycle_iv_dac_t *p)
|
||||
{
|
||||
p->Nf = round((p->mV_output - p->Vc - p->Voffset - (p->Nc0 - 32768) / p->eta_c) * p->eta_f) + 32768;
|
||||
return p->Nf;
|
||||
}
|
||||
|
||||
static uint32_t cal_dac_timer_interval(elite_dac_config_t *p_config, cycle_iv_dac_t *p_cycle_iv_dac)
|
||||
{
|
||||
const float STEP_TIME_FACTOR = 2.0f;
|
||||
uint32_t intvl;
|
||||
uint32_t step_time = p_config->uS_step * STEP_TIME_FACTOR;
|
||||
for (uint32_t intvl = 100; intvl < 1000000; intvl *= 10)
|
||||
{
|
||||
p_cycle_iv_dac->step = (p_config->mV_step * intvl) / step_time;
|
||||
if (p_cycle_iv_dac->step)
|
||||
{
|
||||
return intvl;
|
||||
}
|
||||
}
|
||||
return intvl;
|
||||
}
|
||||
|
||||
void _callback(void *p_arg)
|
||||
{
|
||||
cycle_iv_dac_t *p = p_arg;
|
||||
|
||||
if (p->mV_output <= p->mV_min)
|
||||
{
|
||||
p->mV_output = p->mV_min;
|
||||
p->dir = 1;
|
||||
}
|
||||
|
||||
if (p->mV_output >= p->mV_max)
|
||||
{
|
||||
p->mV_output = p->mV_max;
|
||||
p->dir = -1;
|
||||
}
|
||||
|
||||
dac_write_through(OUT_1, mV_out_1(p));
|
||||
|
||||
if (p->mV_output == p->mV_start)
|
||||
{
|
||||
p->cycle_cnt++;
|
||||
if (p->cycle_cnt > p->cycle_max)
|
||||
{
|
||||
running = false;
|
||||
}
|
||||
}
|
||||
p->mV_output += p->dir * p->step;
|
||||
}
|
||||
|
||||
static void edc20_cycle_iv_mode_task(void *p_arg)
|
||||
{
|
||||
elite_notify_packet_t packet_buf;
|
||||
cycle_iv_dac_t dac_param;
|
||||
cycle_iv_adc_t adc_param;
|
||||
iv_cycle_mode_param_t mode_param;
|
||||
|
||||
taskENTER_CRITICAL();
|
||||
|
||||
/* copy iv cycle parameter */
|
||||
memcpy(&mode_param, p_arg, sizeof(mode_param));
|
||||
|
||||
memset(&packet_buf, 0x00, sizeof(packet_buf));
|
||||
memset(&dac_param, 0x00, sizeof(dac_param));
|
||||
memset(&adc_param, 0x00, sizeof(adc_param));
|
||||
|
||||
taskEXIT_CRITICAL();
|
||||
|
||||
if (1)
|
||||
{
|
||||
char info[256];
|
||||
snprintf(info, 256, "%s() @ %p start", __FUNCTION__, xTaskGetCurrentTaskHandle());
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%8ld", "id", mode_param.id);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%7.0fmV", "V_start", mode_param.config.mV_start);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%7.0fmV", "V_stop", mode_param.config.mV_stop);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%7.0fmV", "uV_step", mode_param.config.mV_step);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%8ldus", "uS_step_time", mode_param.config.uS_step);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%8ld", "cycles", mode_param.config.cycles);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%8ldms", "mS_period", mode_param.mS_period);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
}
|
||||
|
||||
/* set memborad id */
|
||||
packet_buf.mem_board_id = mode_param.id;
|
||||
|
||||
/* send start packet 4 times */
|
||||
_send_start_packet(&packet_buf, 4);
|
||||
|
||||
dac_param.mV_output = mode_param.config.mV_start;
|
||||
dac_param.mV_max = MAX(mode_param.config.mV_start, mode_param.config.mV_stop);
|
||||
dac_param.mV_min = MIN(mode_param.config.mV_start, mode_param.config.mV_stop);
|
||||
dac_param.mV_start = mode_param.config.mV_start;
|
||||
dac_param.mV_stop = mode_param.config.mV_stop;
|
||||
dac_param.dir = dac_param.mV_output == dac_param.mV_min ? 1 : -1;
|
||||
dac_param.cycle_cnt = 0;
|
||||
dac_param.cycle_max = mode_param.config.cycles;
|
||||
dac_param.fullscale = 0;
|
||||
|
||||
if (1)
|
||||
{
|
||||
NRF_LOG_INFO("%s", "");
|
||||
mV_out_0(&dac_param);
|
||||
char info[256];
|
||||
snprintf(info, 256, "%16s:%10.3f", "eta_c", dac_param.eta_c);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%10.3f", "eta_f", dac_param.eta_f);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%10.3f", "Voffset", dac_param.Voffset);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%10.3f", "Vc", dac_param.Vc);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%10.3f", "Nc", dac_param.Nc);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
snprintf(info, 256, "%16s:%10.3f", "Nc0", dac_param.Nc0);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
|
||||
dac_param.mV_output = dac_param.mV_start;
|
||||
mV_out_1(&dac_param);
|
||||
snprintf(info, 256, "%16s:%10.3f", "V1 Nf", dac_param.Nf);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
|
||||
dac_param.mV_output = dac_param.mV_stop;
|
||||
mV_out_1(&dac_param);
|
||||
snprintf(info, 256, "%16s:%10.3f", "V2 Nf", dac_param.Nf);
|
||||
NRF_LOG_INFO("%s", info);
|
||||
}
|
||||
|
||||
// dac_write_through(OUT_0, mV_out_0(&dac_param));
|
||||
// dac_write_through(OUT_1, mV_out_1(&dac_param));
|
||||
|
||||
|
||||
|
||||
|
||||
//
|
||||
// /* start DAC timer */
|
||||
// edc20_dac_tim_start(cal_dac_timer_interval(&mode_param.config, &dac_param), _callback, &dac_param);
|
||||
//
|
||||
// /* start ADC timer */
|
||||
// edc20_adc_tim_start(&mode_param.config);
|
||||
//
|
||||
// /* get current tick */
|
||||
// TickType_t tick = xTaskGetTickCount();
|
||||
//
|
||||
// uint32_t notify_delay = pdMS_TO_TICKS(mode_param.mS_period);
|
||||
//
|
||||
// /* start data update process */
|
||||
// running = true;
|
||||
//
|
||||
// while (running)
|
||||
// {
|
||||
// ret_code_t ret = _send_data_packet(&packet_buf, false);
|
||||
// switch (ret)
|
||||
// {
|
||||
// case NRF_SUCCESS:
|
||||
// case NRF_ERROR_RESOURCES:
|
||||
// vTaskDelayUntil(&tick, notify_delay);
|
||||
// break;
|
||||
// default:
|
||||
// running = false;
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// edc20_dac_tim_stop();
|
||||
// edc20_adc_tim_stop();
|
||||
|
||||
if (1)
|
||||
{
|
||||
char info[256];
|
||||
snprintf(info, 256, "%s() @ %p stop", __FUNCTION__, xTaskGetCurrentTaskHandle());
|
||||
NRF_LOG_INFO("%s", info);
|
||||
}
|
||||
|
||||
vTaskDelete(NULL);
|
||||
}
|
||||
|
||||
void edc20_cycle_iv_mode_init(void)
|
||||
{
|
||||
}
|
||||
|
||||
#define VDIRECTION(v1, v2) ((v1 > v2) ? 0 : 1)
|
||||
// Step time macro
|
||||
#define STEPTIME_HALF_SEC 5000
|
||||
#define STEPTIME_ONE_SEC 10000
|
||||
#define STEPTIME_TWO_SEC 20000
|
||||
static uint32_t step2VsetRate(uint32_t step)
|
||||
{
|
||||
/*step = 100 mv, index = 0, n = 2
|
||||
10 mv, index = 1, n = 10
|
||||
1 mv, index = 2, n = 100
|
||||
0.1 mv, index = 3, n = 1000
|
||||
0.01mv, index = 4, n = 10000 */
|
||||
|
||||
if (step >= 10000)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else if (step >= 1000)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
else if (step >= 100)
|
||||
{
|
||||
return 2;
|
||||
}
|
||||
else if (step >= 10)
|
||||
{
|
||||
return 3;
|
||||
}
|
||||
else if (step >= 1)
|
||||
{
|
||||
return 4;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 5;
|
||||
}
|
||||
}
|
||||
|
||||
static uint32_t get_step_time(uint8_t StepTime)
|
||||
{
|
||||
switch (StepTime)
|
||||
{
|
||||
case 0: { // 0.5 sec
|
||||
return STEPTIME_HALF_SEC;
|
||||
}
|
||||
case 1: { // 1 sec
|
||||
return STEPTIME_ONE_SEC;
|
||||
}
|
||||
case 2: { // 2 sec
|
||||
return STEPTIME_TWO_SEC;
|
||||
}
|
||||
default: { // 1 sec
|
||||
return STEPTIME_ONE_SEC;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#define STEP_TO_VSETRATE(step) step2VsetRate(step)
|
||||
const uint32_t VsetRateTable[5] = { 2, 10, 100, 1000, 10000 };
|
||||
|
||||
static uint32_t convt_uS_step(uint32_t idx)
|
||||
{
|
||||
switch (idx)
|
||||
{
|
||||
case 0: { // 0.5 sec
|
||||
return 500000;
|
||||
}
|
||||
case 1: { // 1 sec
|
||||
return 1000000;
|
||||
}
|
||||
case 2: { // 2 sec
|
||||
return 2000000;
|
||||
}
|
||||
default: { // 1 sec
|
||||
return 1000000;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void edc20_cycle_iv_mode_start(uint8_t *ins, uint16_t size)
|
||||
{
|
||||
/*
|
||||
instru.eliteFxn = CURVE_IV_CY;
|
||||
instru.Ve1 = ((uint16_t)(ins[3]) << 8) | (uint16_t)(ins[4]);
|
||||
instru.Ve2 = ((uint16_t)(ins[5]) << 8) | (uint16_t)(ins[6]);
|
||||
instru.Vinit = (int32_t)instru.Ve1;
|
||||
instru.Vmax = (int32_t)VMAX(instru.Ve1,instru.Ve2);
|
||||
instru.Vmin = (int32_t)VMIN(instru.Ve1,instru.Ve2);
|
||||
instru.directionInit = VDIRECTION(instru.Ve1,instru.Ve2);
|
||||
instru.steptime = get_step_time(ins[9]); //5000;10000;20000;
|
||||
instru.step = ((uint32_t)(ins[7]) << 8) | (uint32_t)(ins[8]);//1~1000 = 0.1mv ~ 100mv
|
||||
instru.step = instru.step * 100000 / instru.steptime;
|
||||
STEP_TO_VSETRATE(instru.step);
|
||||
instru.VsetRate = VsetRateTable[instru.VsetRateIndex];//N
|
||||
instru.cycleNumber = ((uint16_t)(ins[10]) << 8) | (uint16_t)(ins[11]);
|
||||
instru.hign_z_en = ins[13] & 0x0F;
|
||||
instru.notifyRate = ((uint32_t)ins[14] << 8) | (uint32_t)ins[15];
|
||||
instru.notifyRate = 10000 / instru.notifyRate * 10;
|
||||
*/
|
||||
|
||||
struct __PACKED
|
||||
{
|
||||
uint8_t id : 4;
|
||||
uint8_t : 4;
|
||||
uint8_t : 8;
|
||||
uint8_t : 8;
|
||||
uint16_t volt_start; // unit: 100uV, -5V = 0, 0V = 25000, 5V = 50000
|
||||
uint16_t volt_stop; // unit: 100uV, -5V = 0, 0V = 25000, 5V = 50000
|
||||
uint16_t step; // unit: 100uV
|
||||
uint8_t step_time; // enum: 0 = 5000us, 1 = 10000us, 2 = 20000us
|
||||
uint16_t cycles; // 0 ~ 500000
|
||||
uint8_t : 8;
|
||||
uint8_t hi_z_en; // lower nibble
|
||||
uint16_t sample_rate; // unit: 0.1Hz
|
||||
} *p = (void *)ins;
|
||||
|
||||
iv_cycle_mode_param_t mode_param = {
|
||||
.id = p->id,
|
||||
.mS_period = 1000 * 10 / __REVSH(p->sample_rate),
|
||||
.config.mV_start = ((__REVSH(p->volt_start) & 0xFFFF) / 10 - 2500) * 2,
|
||||
.config.mV_stop = ((__REVSH(p->volt_stop) & 0xFFFF) / 10 - 2500) * 2,
|
||||
.config.mV_step = (uint32_t)__REVSH(p->step) / 10,
|
||||
.config.uS_step = convt_uS_step(p->step_time),
|
||||
.config.cycles = (__REVSH(p->cycles) & 0xFFFF)
|
||||
};
|
||||
|
||||
xTaskCreate(edc20_cycle_iv_mode_task, "iv_mode", 2048, (void *)&mode_param, 3, &task_handle);
|
||||
|
||||
portYIELD();
|
||||
}
|
||||
|
||||
#endif
|
||||
+63
-56
@@ -555,37 +555,68 @@ void spim_xfer(uint32_t cs_pin, nrf_spim_mode_t spi_mode, uint8_t *p_tx_buffer,
|
||||
|
||||
#define ELITE_DAC_TMR NRF_TIMER2
|
||||
|
||||
uint32_t dac_val = 0;
|
||||
uint32_t step = 0;
|
||||
int32_t dir = 1;
|
||||
uint32_t dac_max = 0xFF00;
|
||||
uint32_t dac_min = 0x0000;
|
||||
uint32_t dac_step = 0x100;
|
||||
extern int dac_write_through(uint32_t channel_mask, int32_t dac_val);
|
||||
|
||||
void dac_callback(void)
|
||||
{
|
||||
if (dac_val <= dac_min)
|
||||
{
|
||||
dir = 1;
|
||||
}
|
||||
else if (dac_val >= dac_max)
|
||||
{
|
||||
dir = -1;
|
||||
}
|
||||
dac_write_through(DAC0, dac_val);
|
||||
dac_val += dir * dac_step;
|
||||
}
|
||||
static void (*dac_tmr_cb)(void *p_arg) = NULL;
|
||||
static void *dac_tmr_p_arg = NULL;
|
||||
|
||||
void TIMER2_IRQHandler(void)
|
||||
{
|
||||
if (ELITE_DAC_TMR->EVENTS_COMPARE[0])
|
||||
{
|
||||
ELITE_DAC_TMR->EVENTS_COMPARE[0] = 0;
|
||||
dac_callback();
|
||||
if (dac_tmr_cb)
|
||||
{
|
||||
dac_tmr_cb(dac_tmr_p_arg);
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
void edc20_dac_tim_start(uint32_t period, void (*callback)(void *p_arg), void *p_arg)
|
||||
{
|
||||
NRF_LOG_INFO("%s()", __FUNCTION__);
|
||||
|
||||
__disable_irq();
|
||||
|
||||
sd_nvic_DisableIRQ(TIMER2_IRQn);
|
||||
sd_nvic_ClearPendingIRQ(TIMER2_IRQn);
|
||||
ELITE_DAC_TMR->SHORTS = 0;
|
||||
ELITE_DAC_TMR->TASKS_STOP = 1;
|
||||
|
||||
dac_tmr_p_arg = p_arg;
|
||||
dac_tmr_cb = callback;
|
||||
|
||||
ELITE_DAC_TMR->PRESCALER = NRF_TIMER_FREQ_1MHz;
|
||||
ELITE_DAC_TMR->MODE = NRF_TIMER_MODE_TIMER;
|
||||
ELITE_DAC_TMR->BITMODE = NRF_TIMER_BIT_WIDTH_32;
|
||||
ELITE_DAC_TMR->INTENSET = NRF_TIMER_INT_COMPARE0_MASK;
|
||||
ELITE_DAC_TMR->CC[0] = period;
|
||||
ELITE_DAC_TMR->SHORTS = NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK;
|
||||
sd_nvic_SetPriority(TIMER2_IRQn, _PRIO_APP_HIGH);
|
||||
sd_nvic_EnableIRQ(TIMER2_IRQn);
|
||||
|
||||
ELITE_DAC_TMR->TASKS_CLEAR = 1;
|
||||
ELITE_DAC_TMR->TASKS_START = 1;
|
||||
|
||||
__enable_irq();
|
||||
}
|
||||
|
||||
void edc20_dac_tim_stop(void)
|
||||
{
|
||||
NRF_LOG_INFO("%s()", __FUNCTION__);
|
||||
|
||||
__disable_irq();
|
||||
|
||||
dac_tmr_cb = NULL;
|
||||
dac_tmr_p_arg = NULL;
|
||||
|
||||
sd_nvic_DisableIRQ(TIMER2_IRQn);
|
||||
sd_nvic_ClearPendingIRQ(TIMER2_IRQn);
|
||||
ELITE_DAC_TMR->TASKS_STOP = 1;
|
||||
ELITE_DAC_TMR->SHORTS = 0;
|
||||
|
||||
__enable_irq();
|
||||
}
|
||||
|
||||
#endif /* ! DEF_DAC_DRV_ENABLED */
|
||||
|
||||
#if (DEF_ADC_DRV_ENABLED)
|
||||
@@ -599,11 +630,14 @@ void TIMER3_IRQHandler(void)
|
||||
ELITE_ADC_TMR->EVENTS_COMPARE[0] = 0;
|
||||
|
||||
float mv;
|
||||
extern int adc_read_milivolt(uint32_t channel, float *mv);
|
||||
adc_read_milivolt(2, &mv);
|
||||
|
||||
float v = mv / 1000.0 - 5;
|
||||
|
||||
#if (DEF_RTT_JSCOP_ENABLED)
|
||||
extern void j_scope_update(float f);
|
||||
j_scope_update(mv / 1000.0);
|
||||
j_scope_update(v * 5);
|
||||
#endif
|
||||
|
||||
return;
|
||||
@@ -625,57 +659,30 @@ void TIMER3_IRQHandler(void)
|
||||
return;
|
||||
}
|
||||
}
|
||||
#endif /* ! DEF_ADC_DRV_ENABLED */
|
||||
|
||||
#if (DEF_ADC_DRV_ENABLED == 1 && DEF_DAC_DRV_ENABLED)
|
||||
|
||||
void elite_peripheral_tim_init(void)
|
||||
void edc20_adc_tim_start(elite_dac_config_t *p_config)
|
||||
{
|
||||
// DAC Sample Rate 10KHz
|
||||
ELITE_DAC_TMR->PRESCALER = NRF_TIMER_FREQ_1MHz;
|
||||
ELITE_DAC_TMR->MODE = NRF_TIMER_MODE_TIMER;
|
||||
ELITE_DAC_TMR->BITMODE = NRF_TIMER_BIT_WIDTH_32;
|
||||
ELITE_DAC_TMR->INTENSET = NRF_TIMER_INT_COMPARE0_MASK;
|
||||
ELITE_DAC_TMR->CC[0] = 100;
|
||||
ELITE_DAC_TMR->SHORTS = NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK;
|
||||
sd_nvic_SetPriority(TIMER2_IRQn, _PRIO_APP_HIGH);
|
||||
sd_nvic_EnableIRQ(TIMER2_IRQn);
|
||||
NRF_LOG_INFO("%s()", __FUNCTION__);
|
||||
|
||||
/*
|
||||
ADC Sample rate 10KHz
|
||||
ADC Sample rate 10KHz
|
||||
*/
|
||||
ELITE_ADC_TMR->PRESCALER = NRF_TIMER_FREQ_1MHz;
|
||||
ELITE_ADC_TMR->MODE = NRF_TIMER_MODE_TIMER;
|
||||
ELITE_ADC_TMR->BITMODE = NRF_TIMER_BIT_WIDTH_32;
|
||||
ELITE_ADC_TMR->INTENSET = NRF_TIMER_INT_COMPARE0_MASK;
|
||||
ELITE_ADC_TMR->CC[0] = 100;
|
||||
ELITE_ADC_TMR->CC[0] = 1000;
|
||||
ELITE_ADC_TMR->SHORTS = NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK;
|
||||
sd_nvic_SetPriority(TIMER3_IRQn, _PRIO_APP_HIGH);
|
||||
sd_nvic_EnableIRQ(TIMER3_IRQn);
|
||||
}
|
||||
|
||||
void elite_peripheral_tim_period(uint32_t us)
|
||||
void edc20_adc_tim_stop(void)
|
||||
{
|
||||
ELITE_DAC_TMR->CC[0] = us;
|
||||
|
||||
ELITE_ADC_TMR->CC[0] = us;
|
||||
|
||||
ELITE_DAC_TMR->TASKS_CLEAR = ELITE_ADC_TMR->TASKS_CLEAR = 1;
|
||||
NRF_LOG_INFO("%s()", __FUNCTION__);
|
||||
}
|
||||
|
||||
void elite_peripheral_tim_enable(void)
|
||||
{
|
||||
ELITE_DAC_TMR->TASKS_CLEAR = ELITE_ADC_TMR->TASKS_CLEAR = 1;
|
||||
ELITE_DAC_TMR->TASKS_START = ELITE_ADC_TMR->TASKS_START = 1;
|
||||
}
|
||||
|
||||
void elite_peripheral_tim_disable(void)
|
||||
{
|
||||
ELITE_DAC_TMR->TASKS_STOP = 1;
|
||||
ELITE_ADC_TMR->TASKS_STOP = 1;
|
||||
}
|
||||
|
||||
#endif /* ! DEF_ADC_DRV_ENABLED && DEF_DAC_DRV_ENABLED*/
|
||||
#endif /* ! DEF_ADC_DRV_ENABLED */
|
||||
|
||||
void edc20_io_init(void)
|
||||
{
|
||||
|
||||
+16
-4
@@ -43,6 +43,16 @@
|
||||
#define SPIM_MOSI_PIN NRF_GPIO_PIN_MAP(0, 7)
|
||||
#define SPIM_MISO_PIN NRF_GPIO_PIN_MAP(1, 9)
|
||||
|
||||
typedef struct
|
||||
{
|
||||
float mV_start;
|
||||
float mV_stop;
|
||||
float mV_step;
|
||||
uint32_t uS_step;
|
||||
uint32_t cycles;
|
||||
bool hi_z_en;
|
||||
} elite_dac_config_t;
|
||||
|
||||
void gpio_init(void);
|
||||
void circuit_selection_vin_0(void);
|
||||
void circuit_selection_vin_1(void);
|
||||
@@ -72,9 +82,11 @@ void spi2_set_mode(nrf_drv_spi_mode_t mode);
|
||||
void edc20_io_init(void);
|
||||
void edc20_io_power_off(void);
|
||||
void edc20_io_power_on(void);
|
||||
void elite_peripheral_tim_init(void);
|
||||
void elite_peripheral_tim_period(uint32_t us);
|
||||
void elite_peripheral_tim_enable(void);
|
||||
void elite_peripheral_tim_disable(void);
|
||||
|
||||
void edc20_dac_tim_start(uint32_t period, void (*callback)(void *p_arg), void *p_arg);
|
||||
void edc20_dac_tim_stop(void);
|
||||
|
||||
void edc20_adc_tim_start(elite_dac_config_t *p_config);
|
||||
void edc20_adc_tim_stop(void);
|
||||
|
||||
#endif // !__EDC20_PIN_CTRL_H__
|
||||
|
||||
Reference in New Issue
Block a user