ScienceSensorHub using the MAX32630FTHR

Dependencies:   Adafruit_FeatherOLED BMI160_Fork OneWire SDFileSystem TSL2561 USBDevice VEML6070 max32630fthr

Committer:
smatthew
Date:
Wed Jun 21 01:06:37 2017 +0000
Revision:
0:15959decb4ea
initial commit

Who changed what in which revision?

UserRevisionLine numberNew contents of line
smatthew 0:15959decb4ea 1 #include "mbed.h"
smatthew 0:15959decb4ea 2 #include "max32630fthr.h"
smatthew 0:15959decb4ea 3 #include "OneWire.h"
smatthew 0:15959decb4ea 4 #include "USBSerial.h"
smatthew 0:15959decb4ea 5 #include "bmi160.h"
smatthew 0:15959decb4ea 6 #include "TSL2561.h"
smatthew 0:15959decb4ea 7 #include "Adafruit_SSD1306.h"
smatthew 0:15959decb4ea 8 #include "VEML6070.h"
smatthew 0:15959decb4ea 9 #include "SDFileSystem.h"
smatthew 0:15959decb4ea 10
smatthew 0:15959decb4ea 11 #define BUFF_LENGTH 9
smatthew 0:15959decb4ea 12
smatthew 0:15959decb4ea 13
smatthew 0:15959decb4ea 14 MAX32630FTHR pegasus(MAX32630FTHR::VIO_3V3);
smatthew 0:15959decb4ea 15
smatthew 0:15959decb4ea 16 AnalogIn batMonitor(AIN_0);
smatthew 0:15959decb4ea 17
smatthew 0:15959decb4ea 18 // Hardware serial port over DAPLink
smatthew 0:15959decb4ea 19 Serial daplink(P2_1, P2_0);
smatthew 0:15959decb4ea 20
smatthew 0:15959decb4ea 21 // UART 2. Connected to ScienceSensorBus0
smatthew 0:15959decb4ea 22 RawSerial uart2(P3_1, P3_0);
smatthew 0:15959decb4ea 23
smatthew 0:15959decb4ea 24 // UART 3. Connected to ScienceSensorBus1
smatthew 0:15959decb4ea 25 //Serial uart3(P5_4, P5_3);
smatthew 0:15959decb4ea 26
smatthew 0:15959decb4ea 27 // Virtual serial port over USB
smatthew 0:15959decb4ea 28 USBSerial microUSB;
smatthew 0:15959decb4ea 29
smatthew 0:15959decb4ea 30
smatthew 0:15959decb4ea 31 using namespace OneWire;
smatthew 0:15959decb4ea 32 using namespace RomCommands;
smatthew 0:15959decb4ea 33
smatthew 0:15959decb4ea 34 DigitalOut rLED(LED1, LED_ON);
smatthew 0:15959decb4ea 35 DigitalOut gLED(LED2, LED_OFF);
smatthew 0:15959decb4ea 36 DigitalOut bLED(LED3, LED_OFF);
smatthew 0:15959decb4ea 37
smatthew 0:15959decb4ea 38 //Buttons A,B,C on FeatherWingOLED
smatthew 0:15959decb4ea 39 DigitalIn aButton(P5_3, PullUp);
smatthew 0:15959decb4ea 40 DigitalIn bButton(P3_3, PullUp);
smatthew 0:15959decb4ea 41 DigitalIn cButton(P3_2, PullUp);
smatthew 0:15959decb4ea 42
smatthew 0:15959decb4ea 43 InterruptIn imuInt(P3_6);
smatthew 0:15959decb4ea 44
smatthew 0:15959decb4ea 45 //Get 1-Wire Master (owm) instance
smatthew 0:15959decb4ea 46 // (extWeakPup, extStrongPup)
smatthew 0:15959decb4ea 47 MCU_OWM owm(false, true);
smatthew 0:15959decb4ea 48
smatthew 0:15959decb4ea 49 //Make sure owm is initialized
smatthew 0:15959decb4ea 50 OneWireMaster::CmdResult result = owm.OWInitMaster();
smatthew 0:15959decb4ea 51
smatthew 0:15959decb4ea 52 //
smatthew 0:15959decb4ea 53 SDFileSystem sd(P0_5, P0_6, P0_4, P0_7, "sd"); // mosi, miso, sclk, cs
smatthew 0:15959decb4ea 54
smatthew 0:15959decb4ea 55 //Setup I2C busses
smatthew 0:15959decb4ea 56 I2C i2cBus(P5_7, P6_0); //Actually i2c2
smatthew 0:15959decb4ea 57 I2C i2cBus1(P3_4, P3_5);
smatthew 0:15959decb4ea 58
smatthew 0:15959decb4ea 59 //Setup FeatherOLED
smatthew 0:15959decb4ea 60 Adafruit_SSD1306_I2c featherOLED(i2cBus1);
smatthew 0:15959decb4ea 61
smatthew 0:15959decb4ea 62 //Setup PMIC
smatthew 0:15959decb4ea 63 MAX14690 pmic(i2cBus);
smatthew 0:15959decb4ea 64
smatthew 0:15959decb4ea 65 // Variable Definitions
smatthew 0:15959decb4ea 66 uint8_t screenMode = 0;
smatthew 0:15959decb4ea 67 uint8_t screenMax = 4;
smatthew 0:15959decb4ea 68 event_callback_t serialRXCb;
smatthew 0:15959decb4ea 69 uint16_t co2Level = 420;
smatthew 0:15959decb4ea 70 char rx_buf[BUFF_LENGTH + 1];
smatthew 0:15959decb4ea 71 volatile int rx_in=0;
smatthew 0:15959decb4ea 72 volatile int rx_out=0;
smatthew 0:15959decb4ea 73
smatthew 0:15959decb4ea 74 // Circular buffers for serial TX and RX data - used by interrupt routines
smatthew 0:15959decb4ea 75 const int buffer_size = 255;
smatthew 0:15959decb4ea 76 // might need to increase buffer size for high baud rates
smatthew 0:15959decb4ea 77 char tx_buffer[buffer_size+1];
smatthew 0:15959decb4ea 78 char rx_buffer[buffer_size+1];
smatthew 0:15959decb4ea 79
smatthew 0:15959decb4ea 80 void doubleTapDetected(void)
smatthew 0:15959decb4ea 81 {
smatthew 0:15959decb4ea 82 rLED = !rLED;
smatthew 0:15959decb4ea 83 screenMode = (screenMode + 1) % screenMax;
smatthew 0:15959decb4ea 84 }
smatthew 0:15959decb4ea 85
smatthew 0:15959decb4ea 86 // Interupt Routine to read in data from serial port
smatthew 0:15959decb4ea 87 void serialRX(void)
smatthew 0:15959decb4ea 88 {
smatthew 0:15959decb4ea 89 bLED = LED_ON;
smatthew 0:15959decb4ea 90 // Loop just in case more than one character is in UART's receive FIFO buffer
smatthew 0:15959decb4ea 91 // Stop if buffer full
smatthew 0:15959decb4ea 92 while ((uart2.readable()) && (((rx_in + 1) % buffer_size) != rx_out)) {
smatthew 0:15959decb4ea 93 rx_buffer[rx_in] = uart2.getc();
smatthew 0:15959decb4ea 94 // Uncomment to Echo to USB serial to watch data flow
smatthew 0:15959decb4ea 95 // monitor_device.putc(rx_buffer[rx_in]);
smatthew 0:15959decb4ea 96 rx_in = (rx_in + 1) % buffer_size;
smatthew 0:15959decb4ea 97 }
smatthew 0:15959decb4ea 98 bLED = LED_OFF;
smatthew 0:15959decb4ea 99 return;
smatthew 0:15959decb4ea 100 }
smatthew 0:15959decb4ea 101
smatthew 0:15959decb4ea 102
smatthew 0:15959decb4ea 103
smatthew 0:15959decb4ea 104 // main() runs in its own thread in the OS
smatthew 0:15959decb4ea 105 // (note the calls to Thread::wait below for delays)
smatthew 0:15959decb4ea 106 int main()
smatthew 0:15959decb4ea 107 {
smatthew 0:15959decb4ea 108
smatthew 0:15959decb4ea 109 uart2.attach(&serialRX, Serial::RxIrq);
smatthew 0:15959decb4ea 110 imuInt.mode(PullDown);
smatthew 0:15959decb4ea 111
smatthew 0:15959decb4ea 112 pmic.monCfg = MAX14690::MON_BAT;
smatthew 0:15959decb4ea 113 char tVar, pmicStatusA, pmicStatusB;
smatthew 0:15959decb4ea 114 pmic.readReg(MAX14690::REG_BOOT_CFG, &tVar);
smatthew 0:15959decb4ea 115 pmic.readReg(MAX14690::REG_STATUS_A, &pmicStatusA);
smatthew 0:15959decb4ea 116 pmic.readReg(MAX14690::REG_STATUS_B, &pmicStatusB);
smatthew 0:15959decb4ea 117 gLED = LED_ON;
smatthew 0:15959decb4ea 118 rLED = LED_ON;
smatthew 0:15959decb4ea 119 char co2cmd[9]= {0xff,0x01,0x86,0x00,0x00,0x00,0x00,0x00,0x79};
smatthew 0:15959decb4ea 120 char co2rtrn[9];
smatthew 0:15959decb4ea 121
smatthew 0:15959decb4ea 122
smatthew 0:15959decb4ea 123 i2cBus.frequency(100000);
smatthew 0:15959decb4ea 124 i2cBus1.frequency(400000);
smatthew 0:15959decb4ea 125
smatthew 0:15959decb4ea 126 uint32_t failures = 0;
smatthew 0:15959decb4ea 127
smatthew 0:15959decb4ea 128 DigitalIn uSDdetect(P2_2, PullUp);
smatthew 0:15959decb4ea 129 static const uint32_t N = 14400;
smatthew 0:15959decb4ea 130 uint32_t samples = 0;
smatthew 0:15959decb4ea 131 float accYaxisBuff[N];
smatthew 0:15959decb4ea 132 float accZaxisBuff[N];
smatthew 0:15959decb4ea 133 float gyroXaxisBuff[N];
smatthew 0:15959decb4ea 134 int32_t pulseWidthBuff[N];
smatthew 0:15959decb4ea 135
smatthew 0:15959decb4ea 136 //Sensor data vars
smatthew 0:15959decb4ea 137 BMI160::SensorData accData;
smatthew 0:15959decb4ea 138 BMI160::SensorData gyroData;
smatthew 0:15959decb4ea 139 BMI160::SensorTime sensorTime;
smatthew 0:15959decb4ea 140
smatthew 0:15959decb4ea 141 //Configure Color Sensor Instance. (Attached to I2C2)
smatthew 0:15959decb4ea 142 // TCS3472_I2C rgbSensor(i2cBus);
smatthew 0:15959decb4ea 143
smatthew 0:15959decb4ea 144 //get Lux Sensor instance and configure it.
smatthew 0:15959decb4ea 145 TSL2561 luxSensor(i2cBus, TSL2561_ADDRESS_GND);
smatthew 0:15959decb4ea 146
smatthew 0:15959decb4ea 147 //Get UV Sensor Instance & Configure It.
smatthew 0:15959decb4ea 148 VEML6070 uvSensor(i2cBus);
smatthew 0:15959decb4ea 149 uvSensor.begin(VEML6070_4_T);
smatthew 0:15959decb4ea 150
smatthew 0:15959decb4ea 151 //Get IMU instance and configure it
smatthew 0:15959decb4ea 152 BMI160_I2C imu(i2cBus, BMI160_I2C::I2C_ADRS_SDO_LO);
smatthew 0:15959decb4ea 153
smatthew 0:15959decb4ea 154 //Power up sensors in normal mode
smatthew 0:15959decb4ea 155 if(imu.setSensorPowerMode(BMI160::GYRO, BMI160::NORMAL) != BMI160::RTN_NO_ERROR) {
smatthew 0:15959decb4ea 156 printf("Failed to set gyroscope power mode\n");
smatthew 0:15959decb4ea 157 failures++;
smatthew 0:15959decb4ea 158 }
smatthew 0:15959decb4ea 159
smatthew 0:15959decb4ea 160 wait(0.1);
smatthew 0:15959decb4ea 161
smatthew 0:15959decb4ea 162 if(imu.setSensorPowerMode(BMI160::ACC, BMI160::NORMAL) != BMI160::RTN_NO_ERROR) {
smatthew 0:15959decb4ea 163 printf("Failed to set accelerometer power mode\n");
smatthew 0:15959decb4ea 164 failures++;
smatthew 0:15959decb4ea 165 }
smatthew 0:15959decb4ea 166 wait(0.1);
smatthew 0:15959decb4ea 167
smatthew 0:15959decb4ea 168 BMI160::AccConfig accConfig;
smatthew 0:15959decb4ea 169 BMI160::AccConfig accConfigRead;
smatthew 0:15959decb4ea 170 accConfig.range = BMI160::SENS_4G;
smatthew 0:15959decb4ea 171 accConfig.us = BMI160::ACC_US_OFF;
smatthew 0:15959decb4ea 172 accConfig.bwp = BMI160::ACC_BWP_2;
smatthew 0:15959decb4ea 173 accConfig.odr = BMI160::ACC_ODR_11;
smatthew 0:15959decb4ea 174
smatthew 0:15959decb4ea 175 imu.writeRegister(BMI160::CMD, 0xB1); //Reset the interrupt engine
smatthew 0:15959decb4ea 176 imu.writeRegister(BMI160::INT_EN_0, 0x30); // Set DoubleTap Detection Interrupt
smatthew 0:15959decb4ea 177 imu.writeRegister(BMI160::INT_OUT_CTRL, 0b00001010); // Interrupt Output Control
smatthew 0:15959decb4ea 178 imu.writeRegister(BMI160::INT_LATCH, 0b00000100); // Interrupt Latch.
smatthew 0:15959decb4ea 179 imu.writeRegister(BMI160::INT_MAP_0, 0b00110000); // Map DoubleTap to Interrupt 1
smatthew 0:15959decb4ea 180 imu.writeRegister(BMI160::INT_TAP_0, 0b00000111);
smatthew 0:15959decb4ea 181 imu.writeRegister(BMI160::INT_TAP_1, 0b00001010);
smatthew 0:15959decb4ea 182 imuInt.fall(&doubleTapDetected);
smatthew 0:15959decb4ea 183
smatthew 0:15959decb4ea 184 Thread::wait(50);
smatthew 0:15959decb4ea 185
smatthew 0:15959decb4ea 186 featherOLED.clearDisplay();
smatthew 0:15959decb4ea 187 featherOLED.setTextCursor(0,0);
smatthew 0:15959decb4ea 188 featherOLED.printf("%ux%u OLED Display\r\n", featherOLED.width(), featherOLED.height());
smatthew 0:15959decb4ea 189 featherOLED.printf("HelloWorld \r");
smatthew 0:15959decb4ea 190 featherOLED.display();
smatthew 0:15959decb4ea 191
smatthew 0:15959decb4ea 192 FILE *fp = fopen("/sd/myfile.txt", "w");
smatthew 0:15959decb4ea 193 fprintf(fp, "Begin Logging!\n");
smatthew 0:15959decb4ea 194 // fclose(fp);
smatthew 0:15959decb4ea 195 rLED = LED_OFF;
smatthew 0:15959decb4ea 196
smatthew 0:15959decb4ea 197 while (true) {
smatthew 0:15959decb4ea 198 gLED = !gLED;
smatthew 0:15959decb4ea 199 pmic.readReg(MAX14690::REG_STATUS_A, &pmicStatusA);
smatthew 0:15959decb4ea 200 pmic.readReg(MAX14690::REG_STATUS_B, &pmicStatusB);
smatthew 0:15959decb4ea 201 featherOLED.clearDisplay();
smatthew 0:15959decb4ea 202 featherOLED.setTextCursor(0,0);
smatthew 0:15959decb4ea 203 switch (screenMode) {
smatthew 0:15959decb4ea 204 case 0x00 : //Main Screen
smatthew 0:15959decb4ea 205 featherOLED.printf("MAX32630FTHR OLED\n");
smatthew 0:15959decb4ea 206 featherOLED.printf("ScienceSensorHub\r\n");
smatthew 0:15959decb4ea 207 featherOLED.printf("by Scott Roberts\r\n");
smatthew 0:15959decb4ea 208 break;
smatthew 0:15959decb4ea 209 case 0x01 : //Light Values
smatthew 0:15959decb4ea 210 featherOLED.printf("Plant Sensors\r\n");
smatthew 0:15959decb4ea 211 featherOLED.printf("Lux: %+5.2f \r\n", luxSensor.lux());
smatthew 0:15959decb4ea 212 featherOLED.printf("UV: %+3u\r\n", uvSensor.readUV());
smatthew 0:15959decb4ea 213 featherOLED.printf("CO2: %3u ",co2Level);
smatthew 0:15959decb4ea 214
smatthew 0:15959decb4ea 215 break;
smatthew 0:15959decb4ea 216 case 0x02 : //IMU Values
smatthew 0:15959decb4ea 217 featherOLED.printf("IMU Values\r\n");
smatthew 0:15959decb4ea 218 imu.getSensorXYZ(accData, accConfig.range);
smatthew 0:15959decb4ea 219 featherOLED.printf("X: %f\r\n",accData.xAxis.scaled);
smatthew 0:15959decb4ea 220 featherOLED.printf("Y: %f\r\n",accData.yAxis.scaled);
smatthew 0:15959decb4ea 221 featherOLED.printf("Z: %f\r\n",accData.zAxis.scaled);
smatthew 0:15959decb4ea 222 break;
smatthew 0:15959decb4ea 223 case 0x03 : //Diagnostics
smatthew 0:15959decb4ea 224 featherOLED.printf("Diagnostics\r\n");
smatthew 0:15959decb4ea 225 featherOLED.printf("B: %5.3f \r\n",batMonitor.read()*5.0f);
smatthew 0:15959decb4ea 226 if((pmicStatusB & 0x08) != 0) featherOLED.printf("USBok/");
smatthew 0:15959decb4ea 227 if((pmicStatusB & 0x01) ==1) featherOLED.printf("ChgTmo/");
smatthew 0:15959decb4ea 228 switch(pmicStatusA & 0x07) {
smatthew 0:15959decb4ea 229 case 0x00 :
smatthew 0:15959decb4ea 230 featherOLED.printf("Coff/");
smatthew 0:15959decb4ea 231 break;
smatthew 0:15959decb4ea 232 case 0x01 :
smatthew 0:15959decb4ea 233 featherOLED.printf("LTemp/");
smatthew 0:15959decb4ea 234 break;
smatthew 0:15959decb4ea 235 case 0x02 :
smatthew 0:15959decb4ea 236 featherOLED.printf("PreC/");
smatthew 0:15959decb4ea 237 break;
smatthew 0:15959decb4ea 238 case 0x03 :
smatthew 0:15959decb4ea 239 featherOLED.printf("FCCC/");
smatthew 0:15959decb4ea 240 break;
smatthew 0:15959decb4ea 241 case 0x04 :
smatthew 0:15959decb4ea 242 featherOLED.printf("FCCV/");
smatthew 0:15959decb4ea 243 break;
smatthew 0:15959decb4ea 244 case 0x05 :
smatthew 0:15959decb4ea 245 featherOLED.printf("MCinPr/");
smatthew 0:15959decb4ea 246 break;
smatthew 0:15959decb4ea 247 case 0x06 :
smatthew 0:15959decb4ea 248 featherOLED.printf("MTdone/");
smatthew 0:15959decb4ea 249 break;
smatthew 0:15959decb4ea 250 case 0x07 :
smatthew 0:15959decb4ea 251 featherOLED.printf("Cfault/");
smatthew 0:15959decb4ea 252 break;
smatthew 0:15959decb4ea 253 }
smatthew 0:15959decb4ea 254 break;
smatthew 0:15959decb4ea 255 case 0x04 : //Oops
smatthew 0:15959decb4ea 256 featherOLED.printf("Misc\r\n");
smatthew 0:15959decb4ea 257 break;
smatthew 0:15959decb4ea 258
smatthew 0:15959decb4ea 259 }
smatthew 0:15959decb4ea 260
smatthew 0:15959decb4ea 261
smatthew 0:15959decb4ea 262 featherOLED.display();
smatthew 0:15959decb4ea 263
smatthew 0:15959decb4ea 264 Thread::wait(750);
smatthew 0:15959decb4ea 265 }
smatthew 0:15959decb4ea 266 }
smatthew 0:15959decb4ea 267