Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: max32630fthr Adafruit_FeatherOLED USBDevice
MAX30001_Helper.cpp
00001 #include "MaximSensor.h" 00002 #include "MAX30001_Helper.h" 00003 #include "Peripherals.h" 00004 #include "EcgComm_Defines.h" 00005 00006 00007 00008 00009 /// define stream out fifo 00010 #define MAX_ECG_REPORT_COUNT 256 00011 /// allocate a large fifo buffer for streaming out 00012 static uint8_t streamOutBuffer[sizeof(ecg_sensor_report ) * MAX_ECG_REPORT_COUNT]; 00013 00014 00015 MAX30001_Helper::MAX30001_Helper(MAX30001 *m, InterruptIn *ir_B, InterruptIn *ir_2B) 00016 :m_max30001(m), m_max30001_InterruptB(ir_B), m_max30001_Interrupt2B(ir_2B){ 00017 queue_init(&mmax30001_queue, streamOutBuffer, sizeof(ecg_sensor_report ), sizeof(streamOutBuffer)); 00018 printf("Constructor is called\n"); 00019 m_max30001->m_max30001_int_happened_ = false; 00020 } 00021 00022 00023 int MAX30001_Helper::readRegister(uint8_t reg, uint8_t *data, int len){ 00024 printf("Empty Function is Called %s", __func__); 00025 return -1; 00026 } 00027 00028 int MAX30001_Helper::writeRegister(uint8_t reg, const uint8_t data){ 00029 printf("Empty Function is Called %s", __func__); 00030 return -1; 00031 } 00032 00033 int MAX30001_Helper::MS_max30001readRegister(uint8_t addr, uint32_t *return_data){ 00034 return m_max30001->max30001_reg_read(static_cast<MAX30001::MAX30001_REG_map_t> (addr), return_data); 00035 } 00036 00037 int MAX30001_Helper::MS_max30001writeRegister(uint8_t addr, uint32_t data){ 00038 return m_max30001->max30001_reg_write(static_cast<MAX30001::MAX30001_REG_map_t> (addr), data); 00039 } 00040 00041 int MAX30001_Helper::get_part_info(uint8_t *part_id, uint8_t *rev_id){ 00042 return -1; 00043 } 00044 00045 void MAX30001_Helper::Max30001_Helper_SetInterrupts(char en){ 00046 if(en){ 00047 m_max30001_InterruptB->disable_irq(); 00048 m_max30001_Interrupt2B->disable_irq(); 00049 m_max30001_InterruptB->mode(PullUp); 00050 m_max30001_InterruptB->fall(&MAX30001Mid_IntB_Handler); 00051 m_max30001_Interrupt2B->mode(PullUp); 00052 m_max30001_Interrupt2B->fall(&MAX30001Mid_Int2B_Handler); 00053 m_max30001_InterruptB->enable_irq(); 00054 m_max30001_Interrupt2B->enable_irq(); 00055 MAX30001_AllowInterrupts(1); 00056 //ret |= m_max30001->max30001_sw_rst(); // Do a software reset of the MAX30001 00057 m_max30001->onDataAvailable(&StreamPacketUint32); 00058 m_max30001->m_max30001_int_happened_ = (false); 00059 }else{ 00060 m_max30001_InterruptB->disable_irq(); 00061 m_max30001_Interrupt2B->disable_irq(); 00062 MAX30001_AllowInterrupts(0); 00063 //ret |= m_max30001->max30001_sw_rst(); // Do a software reset of the MAX30001 00064 m_max30001->m_max30001_int_happened_ = (false); 00065 } 00066 } 00067 00068 int MAX30001_Helper::Max30001Helper_InitializeECGandRtoR(){ 00069 int ret = 0; 00070 /**** ENABLE CHANNELS for ECG ****/ 00071 // CNFG_GEN 00072 if (m_max30001->max30001_reg_read(MAX30001::CNFG_GEN, &m_max30001->max30001_cnfg_gen.all) == -1) { 00073 return -1; 00074 } 00075 m_max30001->max30001_cnfg_gen.bit.en_ecg = 0x1; // 0b1 00076 // fmstr is default 00077 if (m_max30001->max30001_reg_write(MAX30001::CNFG_GEN, m_max30001->max30001_cnfg_gen.all) == -1) { 00078 return -1; 00079 } 00080 ret = m_max30001->max30001_PLL_lock(); 00081 // MNGR_INT 00082 if (m_max30001->max30001_reg_read(MAX30001::MNGR_INT, &m_max30001->max30001_mngr_int.all) == -1) { 00083 return -1; 00084 } 00085 m_max30001->max30001_mngr_int.bit.e_fit = E_FIT; // 31 00086 // if (m_max30001->max30001_reg_write(MAX30001::MNGR_INT, m_max30001->max30001_mngr_int.all) == -1) { 00087 // return -1; 00088 // } 00089 // end of MNGR_INT 00090 00091 // Configure RtoR Parameters 00092 // MNGR_INT 00093 // if (m_max30001->max30001_reg_read(MAX30001::MNGR_INT, &m_max30001->max30001_mngr_int.all) == -1) { 00094 // return -1; 00095 // } 00096 m_max30001->max30001_mngr_int.bit.clr_rrint = 0x01; // 0b01 & 0b00 are for interrupt mode... 00097 // 0b10 is for monitoring mode... it just overwrites the data... 00098 if (m_max30001->max30001_reg_write(MAX30001::MNGR_INT, m_max30001->max30001_mngr_int.all) == -1) { 00099 return -1; 00100 } 00101 // RTOR1 00102 if (m_max30001->max30001_reg_read(MAX30001::CNFG_RTOR1, &m_max30001->max30001_cnfg_rtor1.all) == -1) { 00103 return -1; 00104 } 00105 m_max30001->max30001_cnfg_rtor1.bit.en_rtor = 0x1; 00106 if (m_max30001->max30001_reg_write(MAX30001::CNFG_RTOR1, m_max30001->max30001_cnfg_rtor1.all) == -1) { 00107 return -1; 00108 } 00109 return ret; 00110 } 00111 00112 int MAX30001_Helper::Max30001Helper_SetECGSampleRate(Max30001_Helper_ECG_Sample_Rate ecg_rate){ 00113 // ECG Rate 00114 if (m_max30001->max30001_reg_read(MAX30001::CNFG_ECG, &m_max30001->max30001_cnfg_ecg.all) == -1) { 00115 return -1; 00116 } 00117 m_max30001->max30001_cnfg_ecg.bit.rate = ecg_rate; 00118 if (m_max30001->max30001_reg_write(MAX30001::CNFG_ECG, m_max30001->max30001_cnfg_ecg.all) == -1) { 00119 return -1; 00120 } 00121 pr_debug("Setting reg 0x%02X to value 0x%02X\r\n", MAX30001::CNFG_ECG, ecg_rate); 00122 return 0; 00123 } 00124 00125 00126 int MAX30001_Helper::sensor_enable(int enable){ 00127 int ret = 0; 00128 queue_reset(&mmax30001_queue); 00129 memset(&m_ecg_packet_, 0, sizeof(m_ecg_packet_)); 00130 m_rtor_last_bpm_ = 0; 00131 Max30001_Helper_SetInterrupts(enable); 00132 if(enable){ 00133 ret = Max30001Helper_InitializeECGandRtoR(); 00134 ret |= MS_Max30001_RtoR_InitStart(EN_RTOR_OP,WNDW_OP,GAIN_RTOR_OP,PAVG_OP,PTSF_OP,HOFF_OP,RAVG_OP,RHSF_OP,CLR_RRINT_OP); 00135 ret |= MS_max30001_INT_assignment(EN_ENINT_LOC, EN_EOVF_LOC, EN_FSTINT_LOC, 00136 EN_DCLOFFINT_LOC, EN_BINT_LOC,EN_BOVF_LOC, 00137 EN_BOVER_LOC,EN_BUNDR_LOC,EN_BCGMON_LOC, 00138 EN_PINT_LOC,EN_POVF_LOC,EN_PEDGE_LOC, 00139 EN_LONINT_LOC,EN_RRINT_LOC, EN_SAMP_LOC, 00140 INTB_TYPE,INT2B_TYPE); 00141 ret |= MS_max30001sync(); 00142 }else{ 00143 ret = m_max30001->max30001_Stop_ECG(); 00144 ret |= m_max30001->max30001_Stop_RtoR(); 00145 ret |= MS_max30001sync(); 00146 } 00147 return ret; 00148 } 00149 00150 int MAX30001_Helper::agc_enable(int agc_enable){ 00151 return -1; 00152 } 00153 00154 const char *MAX30001_Helper::get_sensor_part_name(){ 00155 return "max30001"; 00156 } 00157 00158 const char *MAX30001_Helper::get_sensor_name(){ 00159 return "max30001"; 00160 } 00161 00162 int MAX30001_Helper::get_sensor_report(ecg_sensor_report &sensor_report) 00163 { 00164 return dequeue(&mmax30001_queue, &sensor_report); 00165 } 00166 00167 int MAX30001_Helper::dump_registers(addr_val_pair *reg_vals){ 00168 int i, j = 0; 00169 int ret = 0; 00170 //43 registers total 00171 for (i = 0x00; i <= 0x05; i++, j++) { 00172 reg_vals[j].addr = i; 00173 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00174 } 00175 for (i = 0x08; i <= 0x0A; i++, j++) { 00176 reg_vals[j].addr = i; 00177 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00178 } 00179 for (i = 0x0F; i <= 0x10; i++, j++) { 00180 reg_vals[j].addr = i; 00181 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00182 } 00183 for (i = 0x12; i <= 0x12; i++, j++) { 00184 reg_vals[j].addr = i; 00185 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00186 } 00187 for (i = 0x14; i <= 0x15; i++, j++) { 00188 reg_vals[j].addr = i; 00189 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00190 } 00191 for (i = 0x17; i <= 0x18; i++, j++) { 00192 reg_vals[j].addr = i; 00193 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00194 } 00195 for (i = 0x1A; i <= 0x1A; i++, j++) { 00196 reg_vals[j].addr = i; 00197 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00198 } 00199 for (i = 0x1D; i <= 0x1E; i++, j++) { 00200 reg_vals[j].addr = i; 00201 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00202 } 00203 for (i = 0x20; i <= 0x25; i++, j++) { 00204 reg_vals[j].addr = i; 00205 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00206 } 00207 for (i = 0x30; i <= 0x47; i++, j++) { 00208 reg_vals[j].addr = i; 00209 ret |= MS_max30001readRegister(i, &(reg_vals[j].val)); 00210 } 00211 00212 return ret; 00213 } 00214 00215 00216 // This function starts ECG processing 00217 int MAX30001_Helper::MS_Max30001_ECG_InitStart(uint8_t En_ecg, uint8_t Openp, uint8_t Openn, 00218 uint8_t Pol, uint8_t Calp_sel, uint8_t Caln_sel, 00219 uint8_t E_fit, uint8_t Rate, uint8_t Gain, 00220 uint8_t Dhpf, uint8_t Dlpf){ 00221 int ret = 0; 00222 ret = m_max30001->max30001_ECG_InitStart(En_ecg, Openp, Openn, Pol, Calp_sel, Caln_sel, E_fit, Rate, Gain, Dhpf, Dlpf); 00223 ret |= m_max30001->max30001_synch(); 00224 return ret; 00225 } 00226 00227 // This functions stops ECG processing 00228 int MAX30001_Helper::MS_Max30001_ECG_Stop(){ 00229 int ret = 0; 00230 ret = m_max30001->max30001_Stop_ECG(); 00231 return ret; 00232 } 00233 00234 // This functions starts R_to_R processing 00235 int MAX30001_Helper::MS_Max30001_RtoR_InitStart(uint8_t En_rtor, uint8_t Wndw, uint8_t Gain, 00236 uint8_t Pavg, uint8_t Ptsf, uint8_t Hoff, 00237 uint8_t Ravg, uint8_t Rhsf, uint8_t Clr_rrint){ 00238 int ret = 0; 00239 ret = m_max30001->max30001_RtoR_InitStart(En_rtor, Wndw, Gain, 00240 Pavg, Ptsf, Hoff, 00241 Ravg, Rhsf, Clr_rrint); 00242 ret |= m_max30001->max30001_synch(); 00243 return ret; 00244 } 00245 00246 // This functions stops R_to_R processing 00247 int MAX30001_Helper::MS_Max30001_RtoR_Stop(){ 00248 int ret = 0; 00249 ret = m_max30001->max30001_Stop_RtoR(); 00250 return ret; 00251 } 00252 00253 //This function enables the interrupts for specific parameters 00254 int MAX30001_Helper::MS_max30001_INT_assignment(uint8_t en_enint_loc, uint8_t en_eovf_loc, uint8_t en_fstint_loc, 00255 uint8_t en_dcloffint_loc, uint8_t en_bint_loc, uint8_t en_bovf_loc, 00256 uint8_t en_bover_loc, uint8_t en_bundr_loc, uint8_t en_bcgmon_loc, 00257 uint8_t en_pint_loc, uint8_t en_povf_loc, uint8_t en_pedge_loc, 00258 uint8_t en_lonint_loc, uint8_t en_rrint_loc, uint8_t en_samp_loc, 00259 uint8_t intb_Type, uint8_t int2b_Type){ 00260 00261 return m_max30001->max30001_INT_assignment(static_cast<MAX30001::max30001_intrpt_Location_t> (en_enint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_eovf_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_fstint_loc), 00262 static_cast<MAX30001::max30001_intrpt_Location_t> (en_dcloffint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_bint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_bovf_loc), 00263 static_cast<MAX30001::max30001_intrpt_Location_t> (en_bover_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_bundr_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_bcgmon_loc), 00264 static_cast<MAX30001::max30001_intrpt_Location_t> (en_pint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_povf_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_pedge_loc), 00265 static_cast<MAX30001::max30001_intrpt_Location_t> (en_lonint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_rrint_loc), static_cast<MAX30001::max30001_intrpt_Location_t> (en_samp_loc), 00266 static_cast<MAX30001::max30001_intrpt_type_t> (intb_Type), static_cast<MAX30001::max30001_intrpt_type_t> (int2b_Type)); 00267 00268 } 00269 00270 // call sync function of the sensor 00271 int MAX30001_Helper::MS_max30001sync(){ 00272 return m_max30001->max30001_synch(); 00273 } 00274 00275 // That Function Should Only Be called from interrupt context 00276 void MAX30001_Helper::Max30001Helper_AddDataToQueue(uint32_t id, uint32_t *buffer, uint32_t number){ 00277 for(uint32_t i = 0; i != number; ++i){ 00278 if(id == MAX30001_DATA_ECG){ 00279 m_ecg_packet_.ecg = buffer[i]; 00280 enqueue(&mmax30001_queue, &m_ecg_packet_); 00281 m_ecg_packet_.rtor = 0; 00282 m_ecg_packet_.rtor_bpm = 0; 00283 }else if(id == MAX30001_DATA_RTOR){ 00284 m_ecg_packet_.rtor = buffer[i]; 00285 Max30001_Helper_ConvertRtoRtoBPM(m_ecg_packet_.rtor); 00286 m_ecg_packet_.rtor_bpm = m_rtor_last_bpm_; 00287 } 00288 else{ 00289 } 00290 } 00291 } 00292 00293 void MAX30001_Helper::Max30001Helper_setInterruptStatus(bool status) { 00294 m_max30001->m_max30001_int_happened_ = status; 00295 } 00296 00297 bool MAX30001_Helper::Max30001Helper_getInterruptStatus() { 00298 return m_max30001->m_max30001_int_happened_; 00299 } 00300 00301 void MAX30001_Helper::Max30001Helper_max30001_int_handler(void){ 00302 m_max30001->max30001_int_handler(); 00303 } 00304 00305 int MAX30001_Helper::MAX30001_Helper_Queue_Size(void){ 00306 return queue_len(&mmax30001_queue); 00307 } 00308 00309 int MAX30001_Helper:: MAX30001_Helper_Invert_Waveform(void) { 00310 int ret; 00311 uint32_t return_data; 00312 ret = m_max30001->max30001_reg_read(MAX30001::CNFG_EMUX, &return_data); 00313 if(ret != 0) 00314 return ret; 00315 00316 return_data ^= ((1 << 23)); 00317 ret = m_max30001->max30001_reg_write(MAX30001::CNFG_EMUX, return_data); 00318 return ret; 00319 } 00320 00321 void MAX30001_Helper::Max30001_Helper_ConvertRtoRtoBPM(uint16_t rtor_val) { 00322 const float rtor_constant = 0.0078; 00323 if(rtor_val != 0) 00324 m_rtor_last_bpm_ = (uint8_t)(60 /(rtor_constant* rtor_val)); 00325 } 00326 00327 void StreamPacketUint32(uint32_t id, uint32_t *buffer, uint32_t number) { 00328 Peripherals::max30001Helper()->Max30001Helper_AddDataToQueue(id, buffer, number); 00329 } 00330 00331 /** 00332 * @brief Get sensor ID. 00333 * 00334 * @returns Sensor ID number. 00335 */ 00336 unsigned char MAX30001_Helper::get_sensor_id() { 00337 00338 return( SENSOR_ID_MAX30001 ); 00339 00340 }
Generated on Tue Jul 12 2022 20:09:28 by
