MAX32620HSP (MAXREFDES100) RPC Example for Graphical User Interface

Dependencies:   USBDevice

Fork of HSP_Release by Jerry Bradshaw

This is an example program for the MAX32620HSP (MAXREFDES100 Health Sensor Platform). It demonstrates all the features of the platform and works with a companion graphical user interface (GUI) to help evaluate/configure/monitor the board. Go to the MAXREFDES100 product page and click on "design resources" to download the companion software. The GUI connects to the board through an RPC interface on a virtual serial port over the USB interface.

The RPC interface provides access to all the features of the board and is available to interface with other development environments such Matlab. This firmware provides realtime data streaming through the RPC interface over USB, and also provides the ability to log the data to flash for untethered battery operation. The data logging settings are configured through the GUI, and the GUI also provides the interface to download logged data.

Details on the RPC interface can be found here: HSP RPC Interface Documentation

Windows

With this program loaded, the MAX32620HSP will appear on your computer as a serial port. On Mac and Linux, this will happen by default. For Windows, you need to install a driver: HSP serial port windows driver

For more details about this platform and how to use it, see the MAXREFDES100 product page.

Committer:
jbradshaw
Date:
Tue Apr 25 10:47:10 2017 -0500
Revision:
3:8e9b9f5818aa
Parent:
1:9490836294ea
Removed Bulk Erasing, instead a small number of bytes are sampled from each and every page to determine if sector is "dirty", if so sector is erased
Prevents device from sleeping when the firmware detects a series of binary flash page RPC transfers, this increases flash page transfers by %450
when 200mS elapse with the last flash page transfer, normal sleep behaviour is resumed

Who changed what in which revision?

UserRevisionLine numberNew contents of line
jbradshaw 0:e4a10ed6eb92 1 /*******************************************************************************
jbradshaw 1:9490836294ea 2 / * Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved.
jbradshaw 0:e4a10ed6eb92 3 *
jbradshaw 0:e4a10ed6eb92 4 * Permission is hereby granted, free of charge, to any person obtaining a
jbradshaw 0:e4a10ed6eb92 5 * copy of this software and associated documentation files (the "Software"),
jbradshaw 0:e4a10ed6eb92 6 * to deal in the Software without restriction, including without limitation
jbradshaw 0:e4a10ed6eb92 7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
jbradshaw 0:e4a10ed6eb92 8 * and/or sell copies of the Software, and to permit persons to whom the
jbradshaw 0:e4a10ed6eb92 9 * Software is furnished to do so, subject to the following conditions:
jbradshaw 0:e4a10ed6eb92 10 *
jbradshaw 0:e4a10ed6eb92 11 * The above copyright notice and this permission notice shall be included
jbradshaw 0:e4a10ed6eb92 12 * in all copies or substantial portions of the Software.
jbradshaw 0:e4a10ed6eb92 13 *
jbradshaw 0:e4a10ed6eb92 14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
jbradshaw 0:e4a10ed6eb92 15 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
jbradshaw 0:e4a10ed6eb92 16 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
jbradshaw 0:e4a10ed6eb92 17 * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES
jbradshaw 0:e4a10ed6eb92 18 * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
jbradshaw 0:e4a10ed6eb92 19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
jbradshaw 0:e4a10ed6eb92 20 * OTHER DEALINGS IN THE SOFTWARE.
jbradshaw 0:e4a10ed6eb92 21 *
jbradshaw 0:e4a10ed6eb92 22 * Except as contained in this notice, the name of Maxim Integrated
jbradshaw 0:e4a10ed6eb92 23 * Products, Inc. shall not be used except as stated in the Maxim Integrated
jbradshaw 0:e4a10ed6eb92 24 * Products, Inc. Branding Policy.
jbradshaw 0:e4a10ed6eb92 25 *
jbradshaw 0:e4a10ed6eb92 26 * The mere transfer of this software does not imply any licenses
jbradshaw 0:e4a10ed6eb92 27 * of trade secrets, proprietary technology, copyrights, patents,
jbradshaw 0:e4a10ed6eb92 28 * trademarks, maskwork rights, or any other form of intellectual
jbradshaw 0:e4a10ed6eb92 29 * property whatsoever. Maxim Integrated Products, Inc. retains all
jbradshaw 0:e4a10ed6eb92 30 * ownership rights.
jbradshaw 0:e4a10ed6eb92 31 *******************************************************************************/
jbradshaw 1:9490836294ea 32 /**
jbradshaw 1:9490836294ea 33 * Maxim Integrated MAX30101 Oximeter chip
jbradshaw 1:9490836294ea 34 *
jbradshaw 1:9490836294ea 35 * IMPORTANT: The code below will also need MAX14720.cpp and MAX14720.h
jbradshaw 1:9490836294ea 36 *
jbradshaw 1:9490836294ea 37 * @code
jbradshaw 1:9490836294ea 38 * #include "mbed.h"
jbradshaw 1:9490836294ea 39 * #include "MAX14720.h"
jbradshaw 1:9490836294ea 40 * #include "MAX30101.h"
jbradshaw 1:9490836294ea 41 *
jbradshaw 1:9490836294ea 42 *
jbradshaw 1:9490836294ea 43 * /// define the HVOUT Boost Voltage default for the MAX14720 PMIC
jbradshaw 1:9490836294ea 44 * #define HVOUT_VOLTAGE 4500 // set to 4500 mV
jbradshaw 1:9490836294ea 45 *
jbradshaw 1:9490836294ea 46 * /// define all I2C addresses
jbradshaw 1:9490836294ea 47 * #define MAX14720_I2C_SLAVE_ADDR (0x54)
jbradshaw 1:9490836294ea 48 * #define MAX30101_I2C_SLAVE_ADDR (0xAE)
jbradshaw 1:9490836294ea 49 *
jbradshaw 1:9490836294ea 50 * /// Settings for the HR initialization
jbradshaw 1:9490836294ea 51 * #define FIFO_WATERLEVEL_MARK 15
jbradshaw 1:9490836294ea 52 * #define SAMPLE_AVG 2
jbradshaw 1:9490836294ea 53 * #define SAMPLE_RATE 1
jbradshaw 1:9490836294ea 54 * #define PULSE_WIDTH 2
jbradshaw 1:9490836294ea 55 * #define RED_LED_CURRENT 0x1F
jbradshaw 1:9490836294ea 56 *
jbradshaw 1:9490836294ea 57 * /// Buffer size for streaming data out.
jbradshaw 1:9490836294ea 58 * #define BUFFER_LENGTH 50
jbradshaw 1:9490836294ea 59 *
jbradshaw 1:9490836294ea 60 *
jbradshaw 1:9490836294ea 61 * /// I2C Master 2
jbradshaw 1:9490836294ea 62 * I2C i2c2(I2C2_SDA, I2C2_SCL); // used by MAX14720, MAX30101, LIS2DH
jbradshaw 1:9490836294ea 63 * /// SPI Master 0 with SPI0_SS for use with MAX30001
jbradshaw 1:9490836294ea 64 * SPI spi(SPI0_MOSI, SPI0_MISO, SPI0_SCK, SPI0_SS); // used by MAX30001
jbradshaw 1:9490836294ea 65 *
jbradshaw 1:9490836294ea 66 * /// PMIC
jbradshaw 1:9490836294ea 67 * MAX14720 max14720(&i2c2, MAX14720_I2C_SLAVE_ADDR);
jbradshaw 1:9490836294ea 68 * /// Optical Oximeter
jbradshaw 1:9490836294ea 69 * MAX30101 max30101(&i2c2, MAX30101_I2C_SLAVE_ADDR);
jbradshaw 1:9490836294ea 70 * InterruptIn max30101_Interrupt(P4_0);
jbradshaw 1:9490836294ea 71 *
jbradshaw 1:9490836294ea 72 * //@brief Creating a buffer to hold the data
jbradshaw 1:9490836294ea 73 * uint32_t oxiBuffer[BUFFER_LENGTH];
jbradshaw 1:9490836294ea 74 * int oxiIndex = 0;
jbradshaw 1:9490836294ea 75 * char data_trigger = 0;
jbradshaw 1:9490836294ea 76 *
jbradshaw 0:e4a10ed6eb92 77 *
jbradshaw 1:9490836294ea 78 * //@brief Creates a packet that will be streamed via USB Serial
jbradshaw 1:9490836294ea 79 * //@brief the packet created will be inserted into a fifo to be streamed at a later time
jbradshaw 1:9490836294ea 80 * //@param id Streaming ID
jbradshaw 1:9490836294ea 81 * //@param buffer Pointer to a uint32 array that contains the data to include in the packet
jbradshaw 1:9490836294ea 82 * //@param number Number of elements in the buffer
jbradshaw 1:9490836294ea 83 * //
jbradshaw 1:9490836294ea 84 * void StreamPacketUint32_ex(uint32_t id, uint32_t *buffer, uint32_t number) {
jbradshaw 1:9490836294ea 85 * int i;
jbradshaw 1:9490836294ea 86 * if (id == MAX30101_OXIMETER_DATA + 1) {
jbradshaw 1:9490836294ea 87 *
jbradshaw 1:9490836294ea 88 * for (i = 0; i < number; i++) {
jbradshaw 1:9490836294ea 89 * oxiBuffer[oxiIndex] = buffer[i];
jbradshaw 1:9490836294ea 90 * oxiIndex++;
jbradshaw 1:9490836294ea 91 *
jbradshaw 1:9490836294ea 92 * if (oxiIndex > BUFFER_LENGTH)
jbradshaw 1:9490836294ea 93 * {
jbradshaw 1:9490836294ea 94 * data_trigger = 1;
jbradshaw 1:9490836294ea 95 * oxiIndex = 0;
jbradshaw 1:9490836294ea 96 * }
jbradshaw 1:9490836294ea 97 * }
jbradshaw 1:9490836294ea 98 * }
jbradshaw 1:9490836294ea 99 * }
jbradshaw 1:9490836294ea 100 *
jbradshaw 1:9490836294ea 101 * int main() {
jbradshaw 1:9490836294ea 102 * // hold results for returning functions
jbradshaw 1:9490836294ea 103 * int result;
jbradshaw 1:9490836294ea 104 *
jbradshaw 1:9490836294ea 105 * // initialize HVOUT on the MAX14720 PMIC
jbradshaw 1:9490836294ea 106 * result = max14720.init();
jbradshaw 1:9490836294ea 107 * if (result == MAX14720_ERROR){
jbradshaw 1:9490836294ea 108 * printf("Error initializing MAX14720");
jbradshaw 1:9490836294ea 109 * }
jbradshaw 1:9490836294ea 110 * max14720.boostEn = MAX14720::BOOST_ENABLED;
jbradshaw 1:9490836294ea 111 * max14720.boostSetVoltage(HVOUT_VOLTAGE);
jbradshaw 1:9490836294ea 112 *
jbradshaw 1:9490836294ea 113 * // MAX30101 initialize interrupt
jbradshaw 1:9490836294ea 114 * max30101.onDataAvailable(&StreamPacketUint32_ex);
jbradshaw 1:9490836294ea 115 * max30101_Interrupt.fall(&MAX30101::MAX30101MidIntHandler);
jbradshaw 1:9490836294ea 116 *
jbradshaw 1:9490836294ea 117 * // This is the HR mode only (IR LED only)
jbradshaw 1:9490836294ea 118 * max30101.HRmode_init(FIFO_WATERLEVEL_MARK, SAMPLE_AVG, SAMPLE_RATE,PULSE_WIDTH, RED_LED_CURRENT);
jbradshaw 1:9490836294ea 119 *
jbradshaw 1:9490836294ea 120 * printf("Please wait for data to start streaming\n");
jbradshaw 1:9490836294ea 121 * fflush(stdout);
jbradshaw 1:9490836294ea 122 *
jbradshaw 1:9490836294ea 123 * while (1) {
jbradshaw 1:9490836294ea 124 * if(data_trigger == 1)
jbradshaw 1:9490836294ea 125 * {
jbradshaw 1:9490836294ea 126 * printf("%ld ", oxiBuffer[oxiIndex]); // Print the ECG data on a serial port terminal software
jbradshaw 1:9490836294ea 127 * fflush(stdout);
jbradshaw 1:9490836294ea 128 * }
jbradshaw 1:9490836294ea 129 * }
jbradshaw 1:9490836294ea 130 * }
jbradshaw 1:9490836294ea 131 * @endcode
jbradshaw 1:9490836294ea 132 *
jbradshaw 0:e4a10ed6eb92 133 */
jbradshaw 0:e4a10ed6eb92 134
jbradshaw 0:e4a10ed6eb92 135 #ifndef _MAX30101_H_
jbradshaw 0:e4a10ed6eb92 136 #define _MAX30101_H_
jbradshaw 0:e4a10ed6eb92 137
jbradshaw 0:e4a10ed6eb92 138 #include "mbed.h"
jbradshaw 0:e4a10ed6eb92 139
jbradshaw 0:e4a10ed6eb92 140 #define MAX30101_RAW_DATA_SIZE 3 * 4 * 32
jbradshaw 0:e4a10ed6eb92 141 #define MAX30101_PROC_DATA_SIZE 4 * 32
jbradshaw 0:e4a10ed6eb92 142
jbradshaw 0:e4a10ed6eb92 143 #define MAX30101_OXIMETER_DATA 0x10
jbradshaw 0:e4a10ed6eb92 144
jbradshaw 0:e4a10ed6eb92 145 #define CHUNK_SIZE 252
jbradshaw 0:e4a10ed6eb92 146
jbradshaw 1:9490836294ea 147 ///< MAX30101 Register addresses
jbradshaw 0:e4a10ed6eb92 148
jbradshaw 0:e4a10ed6eb92 149 #define MAX30101_INT_PORT 4
jbradshaw 0:e4a10ed6eb92 150 #define MAX30101_INT_PIN 0
jbradshaw 0:e4a10ed6eb92 151 #define MAX30101_MASTER_NUM 2
jbradshaw 0:e4a10ed6eb92 152
jbradshaw 0:e4a10ed6eb92 153 /**
jbradshaw 0:e4a10ed6eb92 154 * Maxim Integrated MAX30101 Oximeter chip
jbradshaw 0:e4a10ed6eb92 155 */
jbradshaw 0:e4a10ed6eb92 156 class MAX30101 {
jbradshaw 0:e4a10ed6eb92 157 public:
jbradshaw 1:9490836294ea 158 float max30101_final_temp; ///< Global declaration
jbradshaw 1:9490836294ea 159 uint32_t max30101_buffer[MAX30101_PROC_DATA_SIZE]; ///< final Processed data
jbradshaw 1:9490836294ea 160 char max30101_rawData[MAX30101_RAW_DATA_SIZE]; ///< raw data from the chip
jbradshaw 0:e4a10ed6eb92 161
jbradshaw 1:9490836294ea 162 typedef enum { ///< MAX30101 Register addresses
jbradshaw 0:e4a10ed6eb92 163
jbradshaw 1:9490836294ea 164 ///< Status
jbradshaw 0:e4a10ed6eb92 165 REG_INT_STAT_1 = 0x00,
jbradshaw 0:e4a10ed6eb92 166 REG_INT_STAT_2 = 0x01,
jbradshaw 0:e4a10ed6eb92 167 REG_INT_EN_1 = 0x02,
jbradshaw 0:e4a10ed6eb92 168 REG_INT_EN_2 = 0x03,
jbradshaw 0:e4a10ed6eb92 169
jbradshaw 0:e4a10ed6eb92 170 REG_FIFO_W_PTR = 0x04,
jbradshaw 0:e4a10ed6eb92 171 REG_FIFO_OVF_CNT = 0x05,
jbradshaw 0:e4a10ed6eb92 172 REG_FIFO_R_PTR = 0x06,
jbradshaw 0:e4a10ed6eb92 173 REG_FIFO_DATA = 0x07,
jbradshaw 1:9490836294ea 174 ///< Configuration
jbradshaw 0:e4a10ed6eb92 175 REG_FIFO_CFG = 0x08,
jbradshaw 0:e4a10ed6eb92 176 REG_MODE_CFG = 0x09,
jbradshaw 0:e4a10ed6eb92 177 REG_SPO2_CFG = 0x0A,
jbradshaw 0:e4a10ed6eb92 178 REG_LED1_PA = 0x0C,
jbradshaw 0:e4a10ed6eb92 179 REG_LED2_PA = 0x0D,
jbradshaw 0:e4a10ed6eb92 180 REG_LED3_PA = 0x0E,
jbradshaw 0:e4a10ed6eb92 181 REG_PILOT_PA = 0x10,
jbradshaw 0:e4a10ed6eb92 182 REG_SLT2_SLT1 = 0x11,
jbradshaw 0:e4a10ed6eb92 183 REG_SLT4_SLT3 = 0x12,
jbradshaw 1:9490836294ea 184 ///< Die Temp
jbradshaw 0:e4a10ed6eb92 185 REG_TINT = 0x1F,
jbradshaw 0:e4a10ed6eb92 186 REG_TFRAC = 0x20,
jbradshaw 0:e4a10ed6eb92 187 REG_TEMP_EN = 0x21,
jbradshaw 1:9490836294ea 188 ///< Proximity Func
jbradshaw 0:e4a10ed6eb92 189 REG_PROX_INT_THR = 0x30,
jbradshaw 0:e4a10ed6eb92 190 /* Part ID */
jbradshaw 0:e4a10ed6eb92 191 REG_REV_ID = 0xFE,
jbradshaw 0:e4a10ed6eb92 192 REG_ID = 0xFF,
jbradshaw 0:e4a10ed6eb92 193 } MAX30101_REG_map_t;
jbradshaw 0:e4a10ed6eb92 194
jbradshaw 0:e4a10ed6eb92 195 /**********/
jbradshaw 0:e4a10ed6eb92 196 /* STATUS */
jbradshaw 0:e4a10ed6eb92 197 /**********/
jbradshaw 0:e4a10ed6eb92 198 /// @brief STATUS1 (0x00)
jbradshaw 1:9490836294ea 199 typedef union max30101_Interrupt_Status_1_reg {
jbradshaw 0:e4a10ed6eb92 200 char all;
jbradshaw 0:e4a10ed6eb92 201 struct {
jbradshaw 0:e4a10ed6eb92 202 char pwr_rdy : 1;
jbradshaw 0:e4a10ed6eb92 203 char reserved : 3;
jbradshaw 0:e4a10ed6eb92 204 char prox_int : 1;
jbradshaw 0:e4a10ed6eb92 205 char alc_ovf : 1;
jbradshaw 0:e4a10ed6eb92 206 char ppg_rdy : 1;
jbradshaw 0:e4a10ed6eb92 207 char a_full : 1;
jbradshaw 0:e4a10ed6eb92 208 } bit;
jbradshaw 1:9490836294ea 209 } max30101_Interrupt_Status_1_t;
jbradshaw 0:e4a10ed6eb92 210
jbradshaw 0:e4a10ed6eb92 211 /// @brief STATUS2 (0x01)
jbradshaw 1:9490836294ea 212 typedef union max30101_Interrupt_Status_2_reg {
jbradshaw 0:e4a10ed6eb92 213 char all;
jbradshaw 0:e4a10ed6eb92 214 struct {
jbradshaw 0:e4a10ed6eb92 215 char reserved1 : 1;
jbradshaw 0:e4a10ed6eb92 216 char die_temp_rdy : 1;
jbradshaw 0:e4a10ed6eb92 217 char reserved2 : 6;
jbradshaw 0:e4a10ed6eb92 218 } bit;
jbradshaw 1:9490836294ea 219 } max30101_Interrupt_Status_2_t;
jbradshaw 0:e4a10ed6eb92 220
jbradshaw 0:e4a10ed6eb92 221 /// @brief INTERRUPT_ENABLE1 (0x02)
jbradshaw 1:9490836294ea 222 typedef union max30101_Interrupt_Enable_1_reg {
jbradshaw 1:9490836294ea 223 char all;
jbradshaw 0:e4a10ed6eb92 224 struct {
jbradshaw 1:9490836294ea 225 char reserved1 : 4;
jbradshaw 1:9490836294ea 226 char prox_int_en : 1;
jbradshaw 1:9490836294ea 227 char alc_ovf_en : 1;
jbradshaw 1:9490836294ea 228 char ppg_rdy_en : 1;
jbradshaw 1:9490836294ea 229 char a_full_en : 1;
jbradshaw 0:e4a10ed6eb92 230 } bit;
jbradshaw 1:9490836294ea 231 } max30101_Interrupt_Enable_1_t;
jbradshaw 0:e4a10ed6eb92 232
jbradshaw 0:e4a10ed6eb92 233 /// @brief INTERRUPT_ENABLE2 (0x03)
jbradshaw 1:9490836294ea 234 typedef union max30101_Interrupt_Enable_2_reg {
jbradshaw 1:9490836294ea 235 char all;
jbradshaw 0:e4a10ed6eb92 236 struct {
jbradshaw 1:9490836294ea 237 char reserved1 : 1;
jbradshaw 1:9490836294ea 238 char die_temp_rdy_en : 1;
jbradshaw 1:9490836294ea 239 char reserved2 : 6;
jbradshaw 0:e4a10ed6eb92 240 } bit;
jbradshaw 1:9490836294ea 241 } max30101_Interrupt_Enable_2_t;
jbradshaw 0:e4a10ed6eb92 242
jbradshaw 0:e4a10ed6eb92 243 /*********/
jbradshaw 0:e4a10ed6eb92 244 /* FIFO */
jbradshaw 0:e4a10ed6eb92 245 /*********/
jbradshaw 0:e4a10ed6eb92 246 // 0x04
jbradshaw 0:e4a10ed6eb92 247 /// @brief FIFO_WR_PTR (0x04)
jbradshaw 1:9490836294ea 248 typedef union max30101_fifo_wr_ptr_reg {
jbradshaw 1:9490836294ea 249 char all;
jbradshaw 0:e4a10ed6eb92 250 struct {
jbradshaw 1:9490836294ea 251 char fifo_wr_ptr : 5;
jbradshaw 1:9490836294ea 252 char reserved1 : 3;
jbradshaw 0:e4a10ed6eb92 253 } bit;
jbradshaw 1:9490836294ea 254 } max30101_fifo_wr_ptr_t;
jbradshaw 0:e4a10ed6eb92 255
jbradshaw 0:e4a10ed6eb92 256 /// @brief OVF_COUNTER (0x05)
jbradshaw 1:9490836294ea 257 typedef union max30101_ovf_counter_reg {
jbradshaw 1:9490836294ea 258 char all;
jbradshaw 0:e4a10ed6eb92 259 struct {
jbradshaw 1:9490836294ea 260 char fifo_ovf_counter : 5;
jbradshaw 1:9490836294ea 261 char reserved1 : 3;
jbradshaw 0:e4a10ed6eb92 262 } bit;
jbradshaw 1:9490836294ea 263 } max30101_ovf_counter_reg_t;
jbradshaw 0:e4a10ed6eb92 264
jbradshaw 0:e4a10ed6eb92 265 /// @brief FIFO_READ_PTR (0x06)
jbradshaw 1:9490836294ea 266 typedef union max30101_fifo_rd_ptr_reg {
jbradshaw 1:9490836294ea 267 char all;
jbradshaw 0:e4a10ed6eb92 268 struct {
jbradshaw 1:9490836294ea 269 char fifo_rd_ptr : 5;
jbradshaw 1:9490836294ea 270 char reserved1 : 3;
jbradshaw 0:e4a10ed6eb92 271 } bit;
jbradshaw 1:9490836294ea 272 } max30101_fifo_rd_ptr_t;
jbradshaw 0:e4a10ed6eb92 273
jbradshaw 0:e4a10ed6eb92 274 /********************/
jbradshaw 0:e4a10ed6eb92 275 /* Configuration */
jbradshaw 0:e4a10ed6eb92 276 /********************/
jbradshaw 0:e4a10ed6eb92 277 // 0x08
jbradshaw 0:e4a10ed6eb92 278 /// @brief FIFO_CONFIGURATION (0x08)
jbradshaw 1:9490836294ea 279 typedef union max30101_fifo_configuration_reg {
jbradshaw 1:9490836294ea 280 char all;
jbradshaw 0:e4a10ed6eb92 281 struct {
jbradshaw 1:9490836294ea 282 char fifo_a_full : 4;
jbradshaw 1:9490836294ea 283 char fifo_roll_over_en : 1;
jbradshaw 1:9490836294ea 284 char smp_ave : 3;
jbradshaw 0:e4a10ed6eb92 285 } bit;
jbradshaw 1:9490836294ea 286 } max30101_fifo_configuration_t;
jbradshaw 0:e4a10ed6eb92 287
jbradshaw 0:e4a10ed6eb92 288 /// @brief MODE_CONFIGURATION (0x09)
jbradshaw 1:9490836294ea 289 typedef union max30101_mode_configuration_reg {
jbradshaw 1:9490836294ea 290 char all;
jbradshaw 0:e4a10ed6eb92 291 struct {
jbradshaw 1:9490836294ea 292 char mode : 3;
jbradshaw 1:9490836294ea 293 char reserved1 : 3;
jbradshaw 1:9490836294ea 294 char reset : 1;
jbradshaw 1:9490836294ea 295 char shdn : 1;
jbradshaw 0:e4a10ed6eb92 296 } bit;
jbradshaw 1:9490836294ea 297 } max30101_mode_configuration_t;
jbradshaw 0:e4a10ed6eb92 298
jbradshaw 0:e4a10ed6eb92 299 /// @brief SPO2_CONGIGURATION (0x0A)
jbradshaw 1:9490836294ea 300 typedef union max30101_spo2_configuration_reg {
jbradshaw 1:9490836294ea 301 char all;
jbradshaw 0:e4a10ed6eb92 302 struct {
jbradshaw 1:9490836294ea 303 char led_pw : 2;
jbradshaw 1:9490836294ea 304 char spo2_sr : 3;
jbradshaw 1:9490836294ea 305 char spo2_adc_rge : 2;
jbradshaw 1:9490836294ea 306 char reserved1 : 1;
jbradshaw 0:e4a10ed6eb92 307 } bit;
jbradshaw 1:9490836294ea 308 } max30101_spo2_configuration_t;
jbradshaw 0:e4a10ed6eb92 309
jbradshaw 1:9490836294ea 310 typedef union max30101_multiLED_mode_ctrl_1_reg {
jbradshaw 1:9490836294ea 311 char all;
jbradshaw 0:e4a10ed6eb92 312 struct {
jbradshaw 1:9490836294ea 313 char slot1 : 3;
jbradshaw 1:9490836294ea 314 char reserved : 1;
jbradshaw 1:9490836294ea 315 char slot2 : 3;
jbradshaw 1:9490836294ea 316 char reserved1 : 1;
jbradshaw 0:e4a10ed6eb92 317 } bit;
jbradshaw 1:9490836294ea 318 } max30101_multiLED_mode_ctrl_1_t;
jbradshaw 0:e4a10ed6eb92 319
jbradshaw 1:9490836294ea 320 typedef union max30101_multiLED_mode_ctrl_2_reg {
jbradshaw 1:9490836294ea 321 char all;
jbradshaw 0:e4a10ed6eb92 322 struct {
jbradshaw 1:9490836294ea 323 char slot3 : 3;
jbradshaw 1:9490836294ea 324 char reserved : 1;
jbradshaw 1:9490836294ea 325 char slot4 : 3;
jbradshaw 1:9490836294ea 326 char reserved1 : 1;
jbradshaw 0:e4a10ed6eb92 327 } bit;
jbradshaw 1:9490836294ea 328 } max30101_multiLED_mode_ctrl_2_t;
jbradshaw 0:e4a10ed6eb92 329
jbradshaw 0:e4a10ed6eb92 330 /********************/
jbradshaw 0:e4a10ed6eb92 331 /* Die Temperature */
jbradshaw 0:e4a10ed6eb92 332 /********************/
jbradshaw 0:e4a10ed6eb92 333
jbradshaw 1:9490836294ea 334 char max30101_tinit;
jbradshaw 0:e4a10ed6eb92 335
jbradshaw 1:9490836294ea 336 char max30101_tfrac;
jbradshaw 0:e4a10ed6eb92 337
jbradshaw 1:9490836294ea 338 typedef union max30101_die_temp_config {
jbradshaw 1:9490836294ea 339 char all;
jbradshaw 0:e4a10ed6eb92 340 struct {
jbradshaw 1:9490836294ea 341 char temp_en : 1;
jbradshaw 1:9490836294ea 342 char reserved : 7;
jbradshaw 0:e4a10ed6eb92 343 } bit;
jbradshaw 1:9490836294ea 344 } max30101_die_temp_config_t;
jbradshaw 1:9490836294ea 345
jbradshaw 0:e4a10ed6eb92 346 /***** Function Prototypes *****/
jbradshaw 0:e4a10ed6eb92 347
jbradshaw 1:9490836294ea 348 char max30101_prox_int_thresh;
jbradshaw 0:e4a10ed6eb92 349
jbradshaw 0:e4a10ed6eb92 350 /**
jbradshaw 1:9490836294ea 351 * @brief MAX30101 constructor.
jbradshaw 0:e4a10ed6eb92 352 * @param sda mbed pin to use for SDA line of I2C interface.
jbradshaw 0:e4a10ed6eb92 353 * @param scl mbed pin to use for SCL line of I2C interface.
jbradshaw 0:e4a10ed6eb92 354 */
jbradshaw 0:e4a10ed6eb92 355 MAX30101(PinName sda, PinName scl, int slaveAddress);
jbradshaw 0:e4a10ed6eb92 356
jbradshaw 0:e4a10ed6eb92 357 /**
jbradshaw 1:9490836294ea 358 * @brief MAX30101 constructor.
jbradshaw 0:e4a10ed6eb92 359 * @param i2c I2C object to use.
jbradshaw 0:e4a10ed6eb92 360 */
jbradshaw 0:e4a10ed6eb92 361 MAX30101(I2C *i2c, int slaveAddress);
jbradshaw 0:e4a10ed6eb92 362
jbradshaw 0:e4a10ed6eb92 363 /**
jbradshaw 1:9490836294ea 364 * @brief MAX30101 destructor.
jbradshaw 0:e4a10ed6eb92 365 */
jbradshaw 0:e4a10ed6eb92 366 ~MAX30101(void);
jbradshaw 0:e4a10ed6eb92 367
jbradshaw 0:e4a10ed6eb92 368 /**
jbradshaw 1:9490836294ea 369 * @brief Allows reading from MAX30101 register
jbradshaw 0:e4a10ed6eb92 370 * @param reg: is the register address, to read from (look at max30101.h and the
jbradshaw 0:e4a10ed6eb92 371 * data sheet for details)
jbradshaw 0:e4a10ed6eb92 372 * @param value: is the pointer to the value read from the register
jbradshaw 0:e4a10ed6eb92 373 * @returns 0-if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 374 */
jbradshaw 0:e4a10ed6eb92 375 int i2c_reg_read(MAX30101_REG_map_t reg, char *value);
jbradshaw 0:e4a10ed6eb92 376
jbradshaw 0:e4a10ed6eb92 377 /**
jbradshaw 0:e4a10ed6eb92 378 * @brief Allows writing to MAX30101 register
jbradshaw 0:e4a10ed6eb92 379 * @param reg: is the register address, to read from (look at max30101.h and
jbradshaw 1:9490836294ea 380 * the data sheet for details)
jbradshaw 0:e4a10ed6eb92 381 * @param value: is the value to write to the register
jbradshaw 0:e4a10ed6eb92 382 * @returns 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 383 */
jbradshaw 0:e4a10ed6eb92 384 int i2c_reg_write(MAX30101_REG_map_t reg, char value);
jbradshaw 0:e4a10ed6eb92 385
jbradshaw 0:e4a10ed6eb92 386 /**
jbradshaw 0:e4a10ed6eb92 387 * @brief This function sets up for the SpO2 mode. The data is returned in
jbradshaw 0:e4a10ed6eb92 388 * the callback function
jbradshaw 0:e4a10ed6eb92 389 * @brief max30101_int_handler in global array: buffer[]. SP mode handles two LED (Red,IR) data. Hence it
jbradshaw 0:e4a10ed6eb92 390 * @brief can fill up the FIFO up to a maximum of 3bytes/sample x 32 x 2 = 192bytes.
jbradshaw 0:e4a10ed6eb92 391 * @param fifo_waterlevel_mark: corresponds to FIFO_A_FULL, In FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 392 * @param sample_avg: corresponds to SMP_AVE, in FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 393 * @param sample_rate: corresponds to SPO2_SR, IN SpO2 Configuration Register (0x0A)
jbradshaw 0:e4a10ed6eb92 394 * @param pulse_width: corresponds to LED_PW in SpO2 Configuration register(0x0A)
jbradshaw 0:e4a10ed6eb92 395 * @param red_led_current: corresponds to LED1_PA register (0x0C). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 396 * @param ir_led_current: corresponds to LED2_PA register (0x0D). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 397 * @returns 0-if everything is good. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 398 */
jbradshaw 0:e4a10ed6eb92 399 int SpO2mode_init(uint8_t fifo_waterlevel_mark, uint8_t sample_avg,
jbradshaw 0:e4a10ed6eb92 400 uint8_t sample_rate, uint8_t pulse_width,
jbradshaw 0:e4a10ed6eb92 401 uint8_t red_led_current, uint8_t ir_led_current);
jbradshaw 0:e4a10ed6eb92 402
jbradshaw 0:e4a10ed6eb92 403 /**
jbradshaw 1:9490836294ea 404 * @brief This function will stop the SpO2 mode and turn off all operating LED�s.
jbradshaw 0:e4a10ed6eb92 405 * @return 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 406 */
jbradshaw 0:e4a10ed6eb92 407 int SpO2mode_stop(void);
jbradshaw 0:e4a10ed6eb92 408
jbradshaw 0:e4a10ed6eb92 409 /**
jbradshaw 0:e4a10ed6eb92 410 * @brief This function sets up for the HR mode. The data is returned in thecallback function
jbradshaw 0:e4a10ed6eb92 411 * @brief max30101_int_handler in global array: buffer[].HR mode handles one LED (Red) data. Hence it can fill
jbradshaw 0:e4a10ed6eb92 412 * @brief up the FIFO up to a maximum of 3bytes/sample x 32 = 96bytes.
jbradshaw 0:e4a10ed6eb92 413 * @brief fifo_waterlevel_mark: corresponds to FIFO_A_FULL, In FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 414 * @param sample_avg: corresponds to SMP_AVE, in FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 415 * @param sample_rate:corresponds to SPO2_SR, IN SpO2 Configuration Register (0x0A)
jbradshaw 0:e4a10ed6eb92 416 * @param pulse_width: corresponds to LED_PW in SpO2 Configuration Register(0x0A)
jbradshaw 0:e4a10ed6eb92 417 * @param red_led_current: corresponds to LED1_PA register (0x0C). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 418 * @returns 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 419 */
jbradshaw 0:e4a10ed6eb92 420 int HRmode_init(uint8_t fifo_waterlevel_mark, uint8_t sample_avg,
jbradshaw 0:e4a10ed6eb92 421 uint8_t sample_rate, uint8_t pulse_width,
jbradshaw 0:e4a10ed6eb92 422 uint8_t red_led_current);
jbradshaw 0:e4a10ed6eb92 423
jbradshaw 0:e4a10ed6eb92 424 /**
jbradshaw 0:e4a10ed6eb92 425 * @brief This function will stop the HR mode and turn off all operating
jbradshaw 0:e4a10ed6eb92 426 * LED’s.
jbradshaw 0:e4a10ed6eb92 427 * @return 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 428 */
jbradshaw 0:e4a10ed6eb92 429 int HRmode_stop(void);
jbradshaw 0:e4a10ed6eb92 430
jbradshaw 0:e4a10ed6eb92 431 /**
jbradshaw 0:e4a10ed6eb92 432 *@brief This function sets up for the Multi-mode. The data is returned in the callback function max30101_int_handler in global array:
jbradshaw 0:e4a10ed6eb92 433 *@brief buffer[]. Multi-LED mode can handle 1 to 4 LED combinations. Hence it can fill up the FIFO up to a maximum of
jbradshaw 0:e4a10ed6eb92 434 *@brief 3bytes/sample x 32 x 4 = 384bytes.
jbradshaw 0:e4a10ed6eb92 435 *@param fifo_waterlevel_mark: corresponds to FIFO_A_FULL, In FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 436 *@param sample_avg: corresponds to SMP_AVE, in FIFO Configuration Register (0x08)
jbradshaw 0:e4a10ed6eb92 437 *@param sample_rate:corresponds to SPO2_SR, IN SpO2 Configuration Register (0x0A)
jbradshaw 0:e4a10ed6eb92 438 *@param pulse_width: corresponds to LED_PW in SpO2 Configuration register(0x0A)
jbradshaw 0:e4a10ed6eb92 439 *@param red_led_current: corresponds to LED1_PA register (0x0C). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 440 *@param ir_led_current: corresponds to LED2_PA register (0x0D). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 441 *@param green_led_current: corresponds to LED3_PA register (0x0E). Please see data sheet for values
jbradshaw 0:e4a10ed6eb92 442 *@param slot_1,…,slot_4: corresponds to Multi-LED Mode control Registers (0x11-0x12).
jbradshaw 0:e4a10ed6eb92 443 *@returns 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 444 */
jbradshaw 0:e4a10ed6eb92 445 int Multimode_init(uint8_t fifo_waterlevel_mark, uint8_t sample_avg,
jbradshaw 0:e4a10ed6eb92 446 uint8_t sample_rate, uint8_t pulse_width,
jbradshaw 0:e4a10ed6eb92 447 uint8_t red_led_current, uint8_t ir_led_current,
jbradshaw 0:e4a10ed6eb92 448 uint8_t green_led_current, uint8_t slot_1, uint8_t slot_2,
jbradshaw 0:e4a10ed6eb92 449 uint8_t slot_3, uint8_t slot_4);
jbradshaw 0:e4a10ed6eb92 450
jbradshaw 0:e4a10ed6eb92 451 /**
jbradshaw 0:e4a10ed6eb92 452 * @brief This function will stop the Multi-mode and turn off all operating LED’s.
jbradshaw 0:e4a10ed6eb92 453 * @returns 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 454 */
jbradshaw 0:e4a10ed6eb92 455 int Multimode_stop(void);
jbradshaw 0:e4a10ed6eb92 456
jbradshaw 0:e4a10ed6eb92 457 /**
jbradshaw 0:e4a10ed6eb92 458 * @brief This is a function that sets up for temperature read and should be called after one of the mode
jbradshaw 0:e4a10ed6eb92 459 * @brief has been setup. The data is returned in the callback function max30101_int_handler. This
jbradshaw 0:e4a10ed6eb92 460 * @brief function needs to be called every time temperature reading is required.
jbradshaw 0:e4a10ed6eb92 461 * @brief Call the temp function after one of the MODES have been started
jbradshaw 0:e4a10ed6eb92 462 * @brief Note that the temp is disabled after one read... also, it is not necessary
jbradshaw 0:e4a10ed6eb92 463 * @brief to read the temp frequently...
jbradshaw 0:e4a10ed6eb92 464 * @returns 0-if if no error. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 465 */
jbradshaw 0:e4a10ed6eb92 466 int tempread(void);
jbradshaw 0:e4a10ed6eb92 467
jbradshaw 0:e4a10ed6eb92 468 /**
jbradshaw 0:e4a10ed6eb92 469 *@brief This is a callback function which collects the data from the FIFO of the MAX30101 in a 32-bit
jbradshaw 0:e4a10ed6eb92 470 *@brief unsigned global array called max30101_buffer[]. Upon every interrupt from the MAX30101, this
jbradshaw 0:e4a10ed6eb92 471 *@brief function is called to service the FIFO of the MAX30101. This callback function also services the
jbradshaw 0:e4a10ed6eb92 472 *@brief interrupt for the temp data. The temp data is collected in a floating point global variable
jbradshaw 0:e4a10ed6eb92 473 *@brief final_temp.
jbradshaw 0:e4a10ed6eb92 474 *@param max30101_buffer[], global uint32_t
jbradshaw 0:e4a10ed6eb92 475 *@returns 0-if everything is good. A non-zero value indicates an error.
jbradshaw 0:e4a10ed6eb92 476 */
jbradshaw 0:e4a10ed6eb92 477 int int_handler(void);
jbradshaw 1:9490836294ea 478
jbradshaw 1:9490836294ea 479 /**
jbradshaw 1:9490836294ea 480 * @brief encapsulates the int_handler above
jbradshaw 1:9490836294ea 481 */
jbradshaw 1:9490836294ea 482 static void MidIntHandler(void);
jbradshaw 1:9490836294ea 483
jbradshaw 0:e4a10ed6eb92 484 /**
jbradshaw 0:e4a10ed6eb92 485 * @brief type definition for data interrupt
jbradshaw 0:e4a10ed6eb92 486 */
jbradshaw 0:e4a10ed6eb92 487 typedef void (*DataCallbackFunction)(uint32_t id, uint32_t *buffer,
jbradshaw 0:e4a10ed6eb92 488 uint32_t length);
jbradshaw 0:e4a10ed6eb92 489 /**
jbradshaw 0:e4a10ed6eb92 490 * @brief type definition for general interrupt
jbradshaw 0:e4a10ed6eb92 491 */
jbradshaw 0:e4a10ed6eb92 492 typedef void (*InterruptFunction)();
jbradshaw 0:e4a10ed6eb92 493
jbradshaw 0:e4a10ed6eb92 494 /**
jbradshaw 0:e4a10ed6eb92 495 * @brief Used to connect a callback for when interrupt data is available
jbradshaw 0:e4a10ed6eb92 496 */
jbradshaw 0:e4a10ed6eb92 497 void onInterrupt(InterruptFunction _onInterrupt);
jbradshaw 0:e4a10ed6eb92 498
jbradshaw 0:e4a10ed6eb92 499 /**
jbradshaw 0:e4a10ed6eb92 500 * @brief Used to connect a callback for when interrupt data is available
jbradshaw 0:e4a10ed6eb92 501 */
jbradshaw 0:e4a10ed6eb92 502 void onDataAvailable(DataCallbackFunction _onDataAvailable);
jbradshaw 0:e4a10ed6eb92 503
jbradshaw 0:e4a10ed6eb92 504 static MAX30101 *instance;
jbradshaw 0:e4a10ed6eb92 505
jbradshaw 0:e4a10ed6eb92 506 private:
jbradshaw 1:9490836294ea 507 /**
jbradshaw 1:9490836294ea 508 * @brief Used to notify an external function that interrupt data is available
jbradshaw 1:9490836294ea 509 * @param id type of data available
jbradshaw 1:9490836294ea 510 * @param buffer 32-bit buffer that points to the data
jbradshaw 1:9490836294ea 511 * @param length length of 32-bit elements available
jbradshaw 1:9490836294ea 512 */
jbradshaw 0:e4a10ed6eb92 513 void dataAvailable(uint32_t id, uint32_t *buffer, uint32_t length);
jbradshaw 1:9490836294ea 514
jbradshaw 1:9490836294ea 515
jbradshaw 1:9490836294ea 516 /**
jbradshaw 1:9490836294ea 517 * @brief Executed on interrupt (callback function at the end of the interrupt)
jbradshaw 1:9490836294ea 518 * @param id type of data available
jbradshaw 1:9490836294ea 519 * @param buffer 32-bit buffer that points to the data
jbradshaw 1:9490836294ea 520 * @param length length of 32-bit elements available
jbradshaw 1:9490836294ea 521 */
jbradshaw 0:e4a10ed6eb92 522 void interruptPostCallback(void);
jbradshaw 1:9490836294ea 523
jbradshaw 0:e4a10ed6eb92 524 /// callback function when interrupt data is available
jbradshaw 0:e4a10ed6eb92 525 DataCallbackFunction onDataAvailableCallback;
jbradshaw 1:9490836294ea 526
jbradshaw 0:e4a10ed6eb92 527 /// callback function when interrupt data is available
jbradshaw 0:e4a10ed6eb92 528 InterruptFunction onInterruptCallback;
jbradshaw 1:9490836294ea 529
jbradshaw 1:9490836294ea 530 /**
jbradshaw 1:9490836294ea 531 * @brief Read from an I2C device (Read I2c wrapper method)
jbradshaw 1:9490836294ea 532 * @param slaveAddress slave address to use with transaction
jbradshaw 1:9490836294ea 533 * @param writeData pointer of data to write
jbradshaw 1:9490836294ea 534 * @param writeCount number of data to write
jbradshaw 1:9490836294ea 535 * @param readData pointer to buffer to read to
jbradshaw 1:9490836294ea 536 * @param readCount number of bytes to read
jbradshaw 1:9490836294ea 537 */
jbradshaw 1:9490836294ea 538
jbradshaw 0:e4a10ed6eb92 539 int I2CM_Read(int slaveAddress, char *writeData, char writeCount, char *readData, char readCount);
jbradshaw 1:9490836294ea 540
jbradshaw 1:9490836294ea 541 /**
jbradshaw 1:9490836294ea 542 * @brief Write to an I2C device (I2C wrapper method)
jbradshaw 1:9490836294ea 543 * @param slaveAddress slave address to use with transaction
jbradshaw 1:9490836294ea 544 * @param writeData1 pointer of data to write
jbradshaw 1:9490836294ea 545 * @param writeCount1 number of data to write
jbradshaw 1:9490836294ea 546 * @param writeData2 pointer to buffer to read to
jbradshaw 1:9490836294ea 547 * @param writeCount2 number of bytes to read
jbradshaw 1:9490836294ea 548 */
jbradshaw 0:e4a10ed6eb92 549 int I2CM_Write(int slaveAddress, char *writeData1, char writeCount1, char *writeData2, char writeCount2);
jbradshaw 1:9490836294ea 550
jbradshaw 1:9490836294ea 551 /// @brief pointer to I2C object
jbradshaw 0:e4a10ed6eb92 552 I2C *i2c;
jbradshaw 1:9490836294ea 553
jbradshaw 1:9490836294ea 554 /// @brief flag to track if this object is the owner (created) the I2C object
jbradshaw 0:e4a10ed6eb92 555 bool i2c_owner;
jbradshaw 1:9490836294ea 556
jbradshaw 1:9490836294ea 557 /// @brief Device slave address
jbradshaw 0:e4a10ed6eb92 558 int slaveAddress;
jbradshaw 0:e4a10ed6eb92 559 };
jbradshaw 0:e4a10ed6eb92 560
jbradshaw 1:9490836294ea 561 /**
jbradshaw 1:9490836294ea 562 * @brief Resets the I2C block, when needed
jbradshaw 1:9490836294ea 563 */
jbradshaw 0:e4a10ed6eb92 564 extern void I2CM_Init_Reset(uint8_t index, int speed);
jbradshaw 0:e4a10ed6eb92 565
jbradshaw 1:9490836294ea 566
jbradshaw 0:e4a10ed6eb92 567
jbradshaw 0:e4a10ed6eb92 568 #endif /* _MAX30101_H_ */