Complete interrupt based test application for the STMicrolectronics' X-NUCLEO-6180XA1 Proximity and ambient light sensor expansion board.

Dependencies:   X_NUCLEO_6180XA1 mbed

Fork of HelloWorld_6180XA1_AppExample by ST Expansion SW Team

Complete interrupt based test application for the STMicrolectronics' X-NUCLEO-6180XA1 Proximity and ambient light sensor expansion board.
The application reads the on board red switch and reports the measured ALS or range accordingly.
A demonstration of resources de-allocation and system restart is also provided by means of Blue Button press.

Committer:
Davidroid
Date:
Fri Mar 03 15:11:39 2017 +0000
Revision:
3:d3719ebf51c4
Parent:
0:b706d6b7c1d3
Child:
4:84dfc00ae7b3
+ Added SW setting for F429ZI MCU board. This requires a HW patch, i.e. to solder Pin 6 of CN8 Arduino connector (A5).; + Some modifications and indentation corrected to fit mbed coding style.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mapellil 0:b706d6b7c1d3 1 #include "mbed.h"
mapellil 0:b706d6b7c1d3 2 #include "x_nucleo_6180xa1.h"
mapellil 0:b706d6b7c1d3 3 #include <string.h>
mapellil 0:b706d6b7c1d3 4 #include <stdlib.h>
mapellil 0:b706d6b7c1d3 5 #include <stdio.h>
mapellil 0:b706d6b7c1d3 6 #include <assert.h>
mapellil 0:b706d6b7c1d3 7
mapellil 0:b706d6b7c1d3 8 /* This VL6180X Expansion board test application performs a range measurement and an als measurement in interrupt mode
mapellil 0:b706d6b7c1d3 9 on the onboard embedded top sensor.
mapellil 0:b706d6b7c1d3 10 The board red slider select on the flight the measurement type as ALS or RANGE; the measured data is diplayed on the
mapellil 0:b706d6b7c1d3 11 on bord 4digits display.
mapellil 0:b706d6b7c1d3 12
mapellil 0:b706d6b7c1d3 13 User Blue button allows to stop current measurement and the entire program releasing all the resources.
mapellil 0:b706d6b7c1d3 14 Reset button is used to restart the program. */
mapellil 0:b706d6b7c1d3 15
mapellil 0:b706d6b7c1d3 16 /* Polling operating modes don`t require callback function that handles IRQ
Davidroid 3:d3719ebf51c4 17 Callback IRQ functions are used only for measure that require interrupt. */
mapellil 0:b706d6b7c1d3 18
mapellil 0:b706d6b7c1d3 19 /* GetMeasurement is asynchronous! It returns NOT_READY if the measurement value
mapellil 0:b706d6b7c1d3 20 is not ready to be read from the corresponding register. So you need to wait
Davidroid 3:d3719ebf51c4 21 for the result to be ready. */
Davidroid 3:d3719ebf51c4 22
mapellil 0:b706d6b7c1d3 23
mapellil 0:b706d6b7c1d3 24 #define VL6180X_I2C_SDA D14
mapellil 0:b706d6b7c1d3 25 #define VL6180X_I2C_SCL D15
mapellil 0:b706d6b7c1d3 26
mapellil 0:b706d6b7c1d3 27 #define RANGE 0
mapellil 0:b706d6b7c1d3 28 #define ALS 1
mapellil 0:b706d6b7c1d3 29
Davidroid 3:d3719ebf51c4 30 #define DELAY 2000 // 2Sec
Davidroid 3:d3719ebf51c4 31
Davidroid 3:d3719ebf51c4 32
Davidroid 3:d3719ebf51c4 33 /* Expansion board */
Davidroid 3:d3719ebf51c4 34 static X_NUCLEO_6180XA1 *board = NULL;
Davidroid 3:d3719ebf51c4 35
Davidroid 3:d3719ebf51c4 36 /* Measure data */
mapellil 0:b706d6b7c1d3 37 MeasureData_t data_sensor_top;
Davidroid 3:d3719ebf51c4 38
Davidroid 3:d3719ebf51c4 39 /* Operating mode */
mapellil 0:b706d6b7c1d3 40 OperatingMode operating_mode, prev_operating_mode;
Davidroid 3:d3719ebf51c4 41 enum OpModeIntPoll_t{ PollMeasure, IntMeasure };
mapellil 0:b706d6b7c1d3 42
Davidroid 3:d3719ebf51c4 43 /* Flags that handle interrupt request */
Davidroid 3:d3719ebf51c4 44 bool int_sensor_top = false, int_stop_measure = false;
mapellil 0:b706d6b7c1d3 45
mapellil 0:b706d6b7c1d3 46 /* ISR callback function of the sensor_top */
mapellil 0:b706d6b7c1d3 47 void SensorTopIRQ(void)
mapellil 0:b706d6b7c1d3 48 {
Davidroid 3:d3719ebf51c4 49 int_sensor_top = true;
Davidroid 3:d3719ebf51c4 50 board->sensor_top->DisableInterruptMeasureDetectionIRQ();
Davidroid 3:d3719ebf51c4 51 }
mapellil 0:b706d6b7c1d3 52
mapellil 0:b706d6b7c1d3 53 /* ISR callback function of the user blue button to stop program */
mapellil 0:b706d6b7c1d3 54 void StopMeasureIRQ(void)
mapellil 0:b706d6b7c1d3 55 {
Davidroid 3:d3719ebf51c4 56 int_stop_measure = true;
mapellil 0:b706d6b7c1d3 57 }
mapellil 0:b706d6b7c1d3 58
mapellil 0:b706d6b7c1d3 59 /* On board 4 digit local display refresh */
mapellil 0:b706d6b7c1d3 60 void DisplayRefresh(OperatingMode op_mode)
Davidroid 3:d3719ebf51c4 61 {
Davidroid 3:d3719ebf51c4 62 char str[5];
Davidroid 3:d3719ebf51c4 63
Davidroid 3:d3719ebf51c4 64 if (op_mode==range_continuous_interrupt || op_mode==range_continuous_polling) {
Davidroid 3:d3719ebf51c4 65 if (data_sensor_top.range_mm!=0xFFFFFFFF) {
Davidroid 3:d3719ebf51c4 66 sprintf(str,"%d",data_sensor_top.range_mm);
Davidroid 3:d3719ebf51c4 67 } else {
Davidroid 3:d3719ebf51c4 68 sprintf(str,"%s","----");
Davidroid 3:d3719ebf51c4 69 }
Davidroid 3:d3719ebf51c4 70 } else if (op_mode==als_continuous_interrupt || op_mode==als_continuous_polling) {
Davidroid 3:d3719ebf51c4 71 if (data_sensor_top.lux!=0xFFFFFFFF) {
Davidroid 3:d3719ebf51c4 72 sprintf(str,"%d",data_sensor_top.lux);
Davidroid 3:d3719ebf51c4 73 } else {
Davidroid 3:d3719ebf51c4 74 sprintf(str,"%s","----");
Davidroid 3:d3719ebf51c4 75 }
Davidroid 3:d3719ebf51c4 76 }
Davidroid 3:d3719ebf51c4 77 board->display->DisplayString(str, strlen(str));
mapellil 0:b706d6b7c1d3 78 }
mapellil 0:b706d6b7c1d3 79
mapellil 0:b706d6b7c1d3 80 /* On board red slider position check */
Davidroid 3:d3719ebf51c4 81 OperatingMode CheckSlider(enum OpModeIntPoll_t OpMode)
Davidroid 3:d3719ebf51c4 82 {
Davidroid 3:d3719ebf51c4 83 OperatingMode ret;
Davidroid 3:d3719ebf51c4 84 int measure = board->RdSwitch();
mapellil 0:b706d6b7c1d3 85
Davidroid 3:d3719ebf51c4 86 switch (OpMode) {
Davidroid 3:d3719ebf51c4 87 case PollMeasure:
Davidroid 3:d3719ebf51c4 88 if (measure==RANGE) {
Davidroid 3:d3719ebf51c4 89 ret = range_continuous_polling;
Davidroid 3:d3719ebf51c4 90 } else if (measure==ALS) {
Davidroid 3:d3719ebf51c4 91 ret = als_continuous_polling;
Davidroid 3:d3719ebf51c4 92 }
Davidroid 3:d3719ebf51c4 93 break;
Davidroid 3:d3719ebf51c4 94 case IntMeasure:
Davidroid 3:d3719ebf51c4 95 if (measure==RANGE) {
Davidroid 3:d3719ebf51c4 96 ret = range_continuous_interrupt;
Davidroid 3:d3719ebf51c4 97 } else if (measure==ALS) {
Davidroid 3:d3719ebf51c4 98 ret = als_continuous_interrupt;
Davidroid 3:d3719ebf51c4 99 }
Davidroid 3:d3719ebf51c4 100 break;
Davidroid 3:d3719ebf51c4 101 }
Davidroid 3:d3719ebf51c4 102 return ret;
mapellil 0:b706d6b7c1d3 103 }
mapellil 0:b706d6b7c1d3 104
mapellil 0:b706d6b7c1d3 105 /* Print on USB Serial the started OperatingMode */
mapellil 0:b706d6b7c1d3 106 void PrintStartMessage(OperatingMode op_mode)
mapellil 0:b706d6b7c1d3 107 {
Davidroid 3:d3719ebf51c4 108 if (op_mode==range_continuous_interrupt) {
Davidroid 3:d3719ebf51c4 109 printf("\nStarted range continuous interrupt measure\n\r");
Davidroid 3:d3719ebf51c4 110 } else if (prev_operating_mode==als_continuous_interrupt) {
Davidroid 3:d3719ebf51c4 111 printf("\nStarted als continuous interrupt measure\n\r");
Davidroid 3:d3719ebf51c4 112 }
mapellil 0:b706d6b7c1d3 113 }
mapellil 0:b706d6b7c1d3 114
mapellil 0:b706d6b7c1d3 115 /* Print on USB Serial the stopped OperatingMode */
mapellil 0:b706d6b7c1d3 116 void PrintStopMessage(OperatingMode op_mode)
mapellil 0:b706d6b7c1d3 117 {
Davidroid 3:d3719ebf51c4 118 if (op_mode==range_continuous_interrupt) {
Davidroid 3:d3719ebf51c4 119 printf("Stopped range continuous interrupt measure\n\r");
Davidroid 3:d3719ebf51c4 120 } else if (prev_operating_mode==als_continuous_interrupt) {
Davidroid 3:d3719ebf51c4 121 printf("Stopped als continuous interrupt measure\n\r");
Davidroid 3:d3719ebf51c4 122 }
mapellil 0:b706d6b7c1d3 123 }
mapellil 0:b706d6b7c1d3 124
mapellil 0:b706d6b7c1d3 125 /* Print on board 4 Digit display the indicated message <= 4 char */
mapellil 0:b706d6b7c1d3 126 void DisplayMsg(const char * msg)
mapellil 0:b706d6b7c1d3 127 {
Davidroid 3:d3719ebf51c4 128 Timer timer;
Davidroid 3:d3719ebf51c4 129 char str[5];
Davidroid 3:d3719ebf51c4 130
Davidroid 3:d3719ebf51c4 131 timer.start();
Davidroid 3:d3719ebf51c4 132 for (int i=0; i<DELAY; i=timer.read_ms())
Davidroid 3:d3719ebf51c4 133 {
Davidroid 3:d3719ebf51c4 134 sprintf(str,"%s",msg);
Davidroid 3:d3719ebf51c4 135 board->display->DisplayString(str, strlen(str));
Davidroid 3:d3719ebf51c4 136 }
Davidroid 3:d3719ebf51c4 137 timer.stop();
mapellil 0:b706d6b7c1d3 138 }
mapellil 0:b706d6b7c1d3 139
Davidroid 3:d3719ebf51c4 140 /* Handle continuous ALS or Range measurement. */
mapellil 0:b706d6b7c1d3 141 void IntContinousALSorRangeMeasure (DevI2C *device_i2c) {
Davidroid 3:d3719ebf51c4 142 int status;
Davidroid 3:d3719ebf51c4 143
Davidroid 3:d3719ebf51c4 144 /* Creates the 6180XA1 expansion board singleton obj */
Davidroid 3:d3719ebf51c4 145 #ifdef TARGET_STM32F429
Davidroid 3:d3719ebf51c4 146 board = X_NUCLEO_6180XA1::Instance(device_i2c, A5, A2, D13, D2);
Davidroid 3:d3719ebf51c4 147 #else
Davidroid 3:d3719ebf51c4 148 board = X_NUCLEO_6180XA1::Instance(device_i2c, A3, A2, D13, D2);
Davidroid 3:d3719ebf51c4 149 #endif
Davidroid 3:d3719ebf51c4 150 DisplayMsg("INT");
Davidroid 3:d3719ebf51c4 151
Davidroid 3:d3719ebf51c4 152 /* Init the 6180XA1 expansion board with default values */
Davidroid 3:d3719ebf51c4 153 status = board->InitBoard();
Davidroid 3:d3719ebf51c4 154 if (status) {
Davidroid 3:d3719ebf51c4 155 printf("Failed to init board!\n\r");
Davidroid 3:d3719ebf51c4 156 }
Davidroid 3:d3719ebf51c4 157
Davidroid 3:d3719ebf51c4 158 /* Check the red slider position for ALS/Range measure */
Davidroid 3:d3719ebf51c4 159 operating_mode=CheckSlider(IntMeasure);
Davidroid 3:d3719ebf51c4 160
Davidroid 3:d3719ebf51c4 161 /* Start the measure on sensor top */
Davidroid 3:d3719ebf51c4 162 status = board->sensor_top->StartMeasurement(operating_mode, SensorTopIRQ, NULL, NULL);
Davidroid 3:d3719ebf51c4 163 if (!status) {
Davidroid 3:d3719ebf51c4 164 prev_operating_mode=operating_mode;
Davidroid 3:d3719ebf51c4 165 PrintStartMessage(operating_mode);
Davidroid 3:d3719ebf51c4 166 while (true) {
Davidroid 3:d3719ebf51c4 167 if (int_sensor_top) { /* 6180 isr was triggered */
Davidroid 3:d3719ebf51c4 168 int_sensor_top = false;
Davidroid 3:d3719ebf51c4 169 status = board->sensor_top->HandleIRQ(operating_mode, &data_sensor_top); /* handle the isr and read the meaure */
Davidroid 3:d3719ebf51c4 170 DisplayRefresh(operating_mode);
Davidroid 3:d3719ebf51c4 171 }
Davidroid 3:d3719ebf51c4 172 if (int_stop_measure) { /* Blue Button isr was triggered */
Davidroid 3:d3719ebf51c4 173 status = board->sensor_top->StopMeasurement(prev_operating_mode); /* stop the measure and exit */
Davidroid 3:d3719ebf51c4 174 if (!status) {
Davidroid 3:d3719ebf51c4 175 PrintStopMessage(prev_operating_mode);
Davidroid 3:d3719ebf51c4 176 }
Davidroid 3:d3719ebf51c4 177 int_stop_measure = false;
Davidroid 3:d3719ebf51c4 178 printf("\nProgram stopped!\n\n\r");
Davidroid 3:d3719ebf51c4 179 break;
Davidroid 3:d3719ebf51c4 180 }
Davidroid 3:d3719ebf51c4 181 operating_mode = CheckSlider(IntMeasure); /* check if red slider was moved */
Davidroid 3:d3719ebf51c4 182 if (operating_mode!=prev_operating_mode) {
Davidroid 3:d3719ebf51c4 183 DisplayRefresh(prev_operating_mode);
Davidroid 3:d3719ebf51c4 184 status = board->sensor_top->StopMeasurement(prev_operating_mode); /* stop the running measure */
Davidroid 3:d3719ebf51c4 185 if (!status) {
Davidroid 3:d3719ebf51c4 186 PrintStopMessage(prev_operating_mode);
Davidroid 3:d3719ebf51c4 187 }
Davidroid 3:d3719ebf51c4 188 prev_operating_mode = operating_mode;
Davidroid 3:d3719ebf51c4 189 status = board->sensor_top->StartMeasurement(operating_mode, SensorTopIRQ, NULL, NULL); /* start the new measure */
Davidroid 3:d3719ebf51c4 190 if (!status) {
Davidroid 3:d3719ebf51c4 191 PrintStartMessage(operating_mode);
Davidroid 3:d3719ebf51c4 192 }
Davidroid 3:d3719ebf51c4 193 } else {
Davidroid 3:d3719ebf51c4 194 DisplayRefresh(operating_mode);
Davidroid 3:d3719ebf51c4 195 }
Davidroid 3:d3719ebf51c4 196 }
Davidroid 3:d3719ebf51c4 197 }
Davidroid 3:d3719ebf51c4 198 DisplayMsg("BYE");
Davidroid 3:d3719ebf51c4 199 }
mapellil 0:b706d6b7c1d3 200
mapellil 0:b706d6b7c1d3 201 /*=================================== Main ==================================
mapellil 0:b706d6b7c1d3 202 Move the VL6180X Expansion board red slider to switch between ALS or Range
mapellil 0:b706d6b7c1d3 203 measures.
mapellil 0:b706d6b7c1d3 204 Press the blue user button to stop the measurements in progress
mapellil 0:b706d6b7c1d3 205 =============================================================================*/
mapellil 0:b706d6b7c1d3 206 int main()
mapellil 0:b706d6b7c1d3 207 {
Davidroid 3:d3719ebf51c4 208 #if USER_BUTTON==PC_13 // Cross compiling for Nucleo-F401
Davidroid 3:d3719ebf51c4 209 InterruptIn stop_button (USER_BUTTON);
Davidroid 3:d3719ebf51c4 210 stop_button.rise (&StopMeasureIRQ);
mapellil 0:b706d6b7c1d3 211 #endif
Davidroid 3:d3719ebf51c4 212 DevI2C *device_i2c = new DevI2C(VL6180X_I2C_SDA, VL6180X_I2C_SCL);
Davidroid 3:d3719ebf51c4 213
Davidroid 3:d3719ebf51c4 214 /* Start continous measures Interrupt based */
Davidroid 3:d3719ebf51c4 215 IntContinousALSorRangeMeasure (device_i2c);
mapellil 0:b706d6b7c1d3 216 }
mapellil 0:b706d6b7c1d3 217