zhaohe 1 year ago
parent
commit
348c906519
  1. 3
      .vscode/settings.json
  2. 3
      README.md
  3. 2
      app/config/sdk_config.h
  4. 103
      app/src/app_ble_service.c
  5. 2
      app/src/basic/version.h
  6. 1
      app/src/board/board.h
  7. 138
      app/src/device_ctrl_service.c
  8. 11
      app/src/device_ctrl_service.h
  9. 2
      dynamic_electrocardiograph_ble_server
  10. 2
      ify_hrs_protocol
  11. 3
      scripter/build_app.bat

3
.vscode/settings.json

@ -167,7 +167,8 @@
"streambuf": "cpp",
"thread": "cpp",
"cinttypes": "cpp",
"device_exception_manager.h": "c"
"device_exception_manager.h": "c",
"xiosbase": "c"
},
"files.encoding": "gbk"
}

3
README.md

@ -1,6 +1,9 @@
# three_lead_ecg_v2
```
V25:
1.针对协议V1.8进行修改
V24:
1.修复V23版本的BUG

2
app/config/sdk_config.h

@ -7812,7 +7812,7 @@
// <e> NRF_LOG_ENABLED - nrf_log - Logger
//==========================================================
#ifndef NRF_LOG_ENABLED
#define NRF_LOG_ENABLED 0
#define NRF_LOG_ENABLED 1
#endif
// <h> Log message pool - Configuration of log message pool

103
app/src/app_ble_service.c

@ -16,8 +16,7 @@
#include "znordic.h"
static uint8_t rxbufcache[256];
static bool is_rxbufcache_used = false; //
static bool m_realtime_report_state = false; //
static bool is_rxbufcache_used = false; //
static uint8_t m_txbuf[256];
static uint8_t m_reportbuf[256];
@ -54,14 +53,6 @@ static void zdatachannel_data_handler(zdatachannel_evt_t* p_evt) {
/*******************************************************************************
* UTILS *
*******************************************************************************/
int ble_start_realtime_report() {
m_realtime_report_state = true;
return 0;
}
int ble_stop_realtime_report() {
m_realtime_report_state = false;
return 0;
}
static void send_error_receipt(ify_hrs_packet_t* rxpacket, int32_t errorcode) {
ify_hrs_packet_t* txheader = (ify_hrs_packet_t*)m_txbuf;
@ -111,7 +102,7 @@ static void prvf_try_report_sample_end_event() {
}
void prvf_report_sample_data(uint32_t frameIndex, one_frame_data_t* data, int32_t ndata) {
if (!m_realtime_report_state) {
if (!DeviceCtrl_IsRealtimeReport()) {
return;
}
@ -335,13 +326,16 @@ static void prvf_process_ble_rx_data(void* p_event_data, uint16_t len) {
receipt->drop_state1 = 0x00;
receipt->device_state0.sampling_state = (DeviceCtrl_now_state() == kdevice_state_sampling);
receipt->device_state0.report_state = m_realtime_report_state;
receipt->device_state0.report_state = DeviceCtrl_IsRealtimeReport();
receipt->device_state0.low_battery = (BoardBattery_get_battery_level() < APP_LOW_BATTERY_WARNING_LIMIT);
receipt->device_state0.full_storge = (SampleDataMgr_storageIsFull());
// receipt->device_state0.is_storaging = DeviceCtrl_isStoraging();
receipt->device_state1 = 0;
receipt->powerlevel = BoardBattery_get_battery_level();
receipt->storage_item_num = SampleDataMgr_getFileNum();
// receipt->storage_setting_time_s = DeviceCtrl_getSettingStorageTime();
// receipt->storage_has_storaged_time_s = DeviceCtrl_getHasStoragedTime();
zdatachannel_data_send2(m_txbuf, sendlen);
}
@ -368,82 +362,50 @@ static void prvf_process_ble_rx_data(void* p_event_data, uint16_t len) {
znordic_rtc_settime(cmd->year + 2000, cmd->month, cmd->day, cmd->hour, cmd->minute, cmd->second);
zdatachannel_data_send2(m_txbuf, sendlen);
}
#if 1
else if (cmd == ify_hrs_cmd_start_capture) {
// hwss_start_capture();
if (DeviceExceptionMgr_has_error()) {
send_error_receipt(rxheader, kifyhrs_ecode_device_exception);
return;
}
if (RecordUpload_is_uploading()) {
ZLOGI("uploading,can not start capture");
send_error_receipt(rxheader, kifyhrs_ecode_device_busy);
return;
else if (cmd == ify_hrs_cmd_start_realtime_preview) {
uint8_t ecode = DeviceCtrl_StartPreview();
if (ecode == 0) {
send_success_receipt(rxheader, 0);
} else {
send_error_receipt(rxheader, ecode);
}
}
if (!hwss_line_detect_get_state()) {
send_error_receipt(rxheader, kifyhrs_ecode_electrode_is_not_inserted);
return;
else if (cmd == ify_hrs_cmd_stop_realtime_preview) {
uint8_t ecode = DeviceCtrl_StopPreview();
if (ecode == 0) {
send_success_receipt(rxheader, 0);
} else {
send_error_receipt(rxheader, ecode);
}
DeviceCtrl_startSample(0);
send_success_receipt(rxheader, 0);
}
else if (cmd == ify_hrs_cmd_start_capture_time_v2) {
// kifyhrs_ecode_parameter_error
// hwss_start_capture();
//
else if (cmd == ify_hrs_cmd_start_storage) {
if (paramLen < 4) {
send_error_receipt(rxheader, kifyhrs_ecode_parameter_error);
return;
}
uint32_t time = *(uint32_t*)rxheader->data;
int32_t capture_time_s = *(int32_t*)(&rxheader->data[0]);
if (RecordUpload_is_uploading()) {
ZLOGI("uploading,can not start capture");
send_error_receipt(rxheader, kifyhrs_ecode_device_busy);
return;
}
if (!hwss_line_detect_get_state()) {
send_error_receipt(rxheader, kifyhrs_ecode_electrode_is_not_inserted);
return;
}
DeviceCtrl_startSample(capture_time_s);
send_success_receipt(rxheader, 0);
}
//
// ify_hrs_cmd_start_upload_record_v2
else if (cmd == ify_hrs_cmd_stop_capture) {
// hwss_stop_capture();
DeviceCtrl_stopSample();
send_success_receipt(rxheader, 0);
}
else if (cmd == ify_hrs_cmd_start_realtime_report) {
int ecode = ble_start_realtime_report();
uint8_t ecode = DeviceCtrl_startStorage(time);
if (ecode == 0) {
send_success_receipt(rxheader, 8); // 8使便
send_success_receipt(rxheader, 0);
} else {
send_error_receipt(rxheader, ecode);
}
}
else if (cmd == ify_hrs_cmd_stop_realtime_report) {
int ecode = ble_stop_realtime_report();
//
else if (cmd == ify_hrs_cmd_stop_storage) {
uint8_t ecode = DeviceCtrl_stopStorage();
if (ecode == 0) {
send_success_receipt(rxheader, 0);
} else {
send_error_receipt(rxheader, ecode);
}
}
#endif
else if (cmd == ify_hrs_cmd_read_records_info) {
// 10-
@ -605,11 +567,8 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
prvf_try_report_sample_end_event();
} else if (event->eventType == kevent_capture_little_data_block_event) {
//
if (m_realtime_report_state) {
//
prvf_report_sample_data(event->val.little_data_block.frameIndex, //
event->val.little_data_block.data, LITTLE_DATA_BLOCK_FRAME_NUM);
}
prvf_report_sample_data(event->val.little_data_block.frameIndex, //
event->val.little_data_block.data, LITTLE_DATA_BLOCK_FRAME_NUM);
}
}

2
app/src/basic/version.h

@ -2,7 +2,7 @@
#define CATEGORY "M1002" // Èýµ¼Áª
#define MANUFACTURER_NAME "iflytop"
#define FIRMWARE_VERSION (24)
#define FIRMWARE_VERSION (25)
#define BLESTACK_VERSION 1
#define BOOTLOADER_VERSION 1
#define HARDWARE_VERSION (1)

1
app/src/board/board.h

@ -60,6 +60,7 @@
#define HEART_WAVE_SAMPLE_SERVICE_CACHE_SIZE (180)
#define FILE_MAX_COUNT 1
#define SDCARD_MAX_FILE_SIZE (uint32_t)(3.5 * 1024 * 1024 * 1024)
#define APP_MAX_STORAGE_TIME_S (uint32_t)(72 * 60 * 60)
//
#define SAMPLE_RATE 400
#define LITTLE_DATA_BLOCK_FRAME_NUM 4 // 每两帧回调一次,对应100HZ

138
app/src/device_ctrl_service.c

@ -1,22 +1,31 @@
#include "device_ctrl_service.h"
#include "../../ify_hrs_protocol/heart_rate_sensor_protocol.h"
#include "app_event_distribute.h"
#include "board/board_battery_state.h"
#include "board/board_beep_ctrl.h"
#include "board/board_button.h"
#include "board/board_light_ctrl.h"
#include "board/board_sdcard_driver.h"
#include "board/device_exception_manager.h"
#include "heart_wave_sample_service.h"
#include "sample_data_manager_service.h"
#include "zble_module.h"
#include "zdatachannel_service.h"
#include "znordic.h"
//
APP_TIMER_DEF(m_state_machine_driver_tmr); //
static device_state_t m_device_state = kdevice_state_standby; //
static uint32_t m_change_to_cur_state_tp = 0; //
static int m_sample_data_fd = -1; //
static int m_sample_duration_ms;
APP_TIMER_DEF(m_state_machine_driver_tmr); //
static device_state_t m_device_state = kdevice_state_standby; //
static uint32_t m_change_to_cur_state_tp = 0; //
static int m_sample_data_fd = -1; //
static bool m_has_triggered_connected = false; //
static uint32_t m_settingStorageTimeS;
static uint32_t m_startStorageTimeTicket;
static uint32_t m_hasStoragedTimeS;
static bool m_isStoraging;
static bool m_IsRealtimeReport;
/*******************************************************************************
* *
@ -170,6 +179,7 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
* *
*******************************************************************************/
if (event->eventType == kevent_ble_connect_event) {
m_has_triggered_connected = true;
BoardLight_setGreenLightEffect(kLightEffect_slowFlash);
} else if (event->eventType == kevent_ble_disconnect_event) {
BoardLight_setGreenLightEffect(kLightEffect_quickFlash);
@ -197,12 +207,11 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
} else if (BoardBattery_get_battery_level() < APP_LOW_BATTERY_LIMIT) {
ZLOGI("auto sleep because low battery");
prvf_change_to_standby_state();
} else if (m_has_triggered_connected && !zble_module_is_connected()) {
prvf_change_to_standby_state();
}
}
//
if (event->eventType == kevent_ble_disconnect_event) {
prvf_change_to_standby_state();
}
if (event->eventType == kevent_start_sample_cmd_event) {
ZLOGI("start sample");
@ -229,7 +238,11 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
else if (m_device_state == kdevice_state_sampling) {
//
if (event->eventType == kevent_capture_data_block_event) {
if (m_isStoraging) {
m_hasStoragedTimeS = znordic_getpower_on_s() - m_startStorageTimeTicket;
}
if (m_isStoraging && event->eventType == kevent_capture_data_block_event) {
ZLOGI("capture data block %d", event->val.block_sensor_data.len);
SampleDataMgr_write(m_sample_data_fd, (uint8_t*)event->val.block_sensor_data.data, event->val.block_sensor_data.len);
}
@ -252,8 +265,14 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
} else if (event->eventType == kevent_stop_sample_cmd_event) {
ZLOGI("stop sample because stop sample event");
stopcapture = true;
} else if (m_sample_duration_ms != 0 && DeviceCtrl_cur_state_haspassed_ms() > m_sample_duration_ms) {
ZLOGI("stop sample because sample timeout");
} else if (m_isStoraging && m_hasStoragedTimeS >= m_settingStorageTimeS) {
ZLOGI("stop sample because storage time is enough");
stopcapture = true;
} else if (!m_isStoraging && !zble_module_is_connected()) {
ZLOGI("stop sample because ble disconnected");
stopcapture = true;
} else if (!m_isStoraging && zble_module_is_connected() && zdatachannel_last_rx_data_haspassed_s() >= BLE_UNCONNECTED_OVERTIME_S) {
ZLOGI("stop sample because ble unconnected");
stopcapture = true;
} else if (BoardBattery_get_battery_level() < APP_LOW_BATTERY_LIMIT) {
ZLOGI("stop sample because low battery");
@ -282,22 +301,93 @@ static void app_event_listener(void* p_event_data, uint16_t event_size) { //
}
}
void DeviceCtrl_startSample(int duration_s) {
ZLOGI("start sample %d", duration_s);
m_sample_duration_ms = duration_s * 1000;
if (duration_s == 0) {
m_sample_duration_ms = 2 * 60 * 1000; //
uint8_t DeviceCtrl_startStorage(uint32_t storageTimeS) {
if (DeviceExceptionMgr_has_error()) {
return kifyhrs_ecode_device_exception;
}
static app_event_t event;
event.eventType = kevent_start_sample_cmd_event;
AppEvent_pushEvent(&event);
if (DeviceCtrl_now_state() != kdevice_state_sampling) {
return kifyhrs_ecode_invalid_state;
}
if (storageTimeS == 0) {
return kifyhrs_ecode_illegal_parameter;
}
if (storageTimeS >= APP_MAX_STORAGE_TIME_S) {
return kifyhrs_ecode_illegal_parameter;
}
m_settingStorageTimeS = storageTimeS;
m_hasStoragedTimeS = 0;
m_startStorageTimeTicket = znordic_getpower_on_s();
m_isStoraging = true;
ZLOGI("start storage %d", storageTimeS);
return 0;
}
void DeviceCtrl_stopSample() {
ZLOGI("stop sample");
static app_event_t event;
event.eventType = kevent_stop_sample_cmd_event;
AppEvent_pushEvent(&event);
uint8_t DeviceCtrl_stopStorage() {
m_isStoraging = false;
m_hasStoragedTimeS = 0;
m_settingStorageTimeS = 0;
m_startStorageTimeTicket = 0;
if (DeviceCtrl_now_state() == kdevice_state_sampling) {
static app_event_t event;
event.eventType = kevent_stop_sample_cmd_event;
AppEvent_pushEvent(&event);
}
return 0;
}
bool DeviceCtrl_isStoraging() { return m_isStoraging; }
uint32_t DeviceCtrl_getSettingStorageTime() { return m_settingStorageTimeS; }
uint32_t DeviceCtrl_getHasStoragedTime() { return m_hasStoragedTimeS; }
uint8_t DeviceCtrl_StartPreview() {
if (DeviceExceptionMgr_has_error()) {
return kifyhrs_ecode_device_exception;
}
/**
* @brief
* 1.
* 2.
*/
if (m_device_state != kdevice_state_ready && m_device_state != kdevice_state_sampling) {
return kifyhrs_ecode_invalid_state;
}
if (m_device_state == kdevice_state_ready) {
static app_event_t event;
event.eventType = kevent_start_sample_cmd_event;
AppEvent_pushEvent(&event);
m_IsRealtimeReport = true;
m_isStoraging = false;
m_hasStoragedTimeS = 0;
m_settingStorageTimeS = 0;
m_startStorageTimeTicket = 0;
} else if (m_device_state == kdevice_state_sampling) {
m_IsRealtimeReport = true;
}
return 0;
}
uint8_t DeviceCtrl_StopPreview() {
m_IsRealtimeReport = false;
if (m_device_state == kdevice_state_sampling && !m_isStoraging) {
static app_event_t event;
event.eventType = kevent_stop_sample_cmd_event;
AppEvent_pushEvent(&event);
}
return 0;
}
bool DeviceCtrl_IsRealtimeReport() { return m_IsRealtimeReport; }
/*******************************************************************************
* EXTERN *

11
app/src/device_ctrl_service.h

@ -37,9 +37,16 @@ void DeviceCtrl_change_to_state(device_state_t state);
uint32_t DeviceCtrl_cur_state_haspassed_ms();
device_state_t DeviceCtrl_now_state();
void DeviceCtrl_startSample(int duration_ms);
uint8_t DeviceCtrl_startStorage(uint32_t storageTimeS);
uint8_t DeviceCtrl_stopStorage();
bool DeviceCtrl_isStoraging();
uint32_t DeviceCtrl_getSettingStorageTime();
uint32_t DeviceCtrl_getHasStoragedTime();
uint8_t DeviceCtrl_StartPreview();
uint8_t DeviceCtrl_StopPreview();
bool DeviceCtrl_IsRealtimeReport();
void DeviceCtrl_stopSample();
void DeviceCtrl_schdeule();
void DeviceCtrl_init();

2
dynamic_electrocardiograph_ble_server

@ -1 +1 @@
Subproject commit a1cff30cf7bc44f0f12fd0a9623603a6a0060ae5
Subproject commit 34a1c922a7336ef7602e1aa54fb04334a3d7274a

2
ify_hrs_protocol

@ -1 +1 @@
Subproject commit 192db524c562d22760899ba950f8c2bd493b3660
Subproject commit 82fc06a24d3eb73b6bb76f2ff5baaae6db0c8b20

3
scripter/build_app.bat

@ -3,7 +3,6 @@
@REM 编译app
call scripter\keil_build.bat app\app.uvprojx app\_build\app.hex
del output\*
@REM 检查是否编译成功
if not exist app\_build\app.hex (
@ -11,7 +10,9 @@ if not exist app\_build\app.hex (
exit /b 1
)
@REM 拷贝app.hex 到 output\
del /q output\*
copy /y app\_build\app.hex output\app.hex

Loading…
Cancel
Save