CAC_smartcushion / Mbed OS 4Bridge_ADISense1000_Example_copy

Fork of ADISense1000_Example_FW by Analog Devices

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers utils.c Source File

utils.c

00001 #include <stdlib.h>
00002 
00003 #include "utils.h"
00004 #include "inc/adi_sense_log.h"
00005 
00006 void utils_printStatus(
00007     ADI_SENSE_STATUS  *pStatus)
00008 {
00009     ADI_SENSE_LOG_INFO("Status Summary:");
00010 
00011     if (pStatus->deviceStatus  == 0)
00012     {
00013         ADI_SENSE_LOG_INFO("\tNo errors detected");
00014     }
00015     else
00016     {
00017         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_BUSY )
00018             ADI_SENSE_LOG_INFO("\tCommand running");
00019         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_DATAREADY )
00020             ADI_SENSE_LOG_INFO("\tData ready");
00021         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_ERROR )
00022             ADI_SENSE_LOG_INFO("\tActive Errors - RESET REQUIRED");
00023         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_FIFO_ERROR )
00024             ADI_SENSE_LOG_INFO("\tActive FIFO Errors - ATTENTION REQUIRED");
00025         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_CONFIG_ERROR )
00026             ADI_SENSE_LOG_INFO("\tActive Configuration Errors - ATTENTION REQUIRED");
00027         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_LUT_ERROR )
00028             ADI_SENSE_LOG_INFO("\tActive Look-Up Table Errors - ATTENTION REQUIRED");
00029 
00030         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_ERROR )
00031         {
00032             ADI_SENSE_LOG_INFO("\tActive Errors - ATTENTION REQUIRED");
00033             ADI_SENSE_LOG_INFO("\t\tLast Error Code: %u (0x%X)",
00034                                pStatus->errorCode , pStatus->errorCode );
00035 
00036             if (pStatus->diagnosticsStatus  == 0)
00037             {
00038                 ADI_SENSE_LOG_INFO("\t\tNo diagnostics faults detected");
00039             }
00040             else
00041             {
00042                 ADI_SENSE_LOG_INFO("\t\tActive diagnostics faults:");
00043 
00044                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_CHECKSUM_ERROR )
00045                     ADI_SENSE_LOG_INFO("\t\t\tInternal Checksum fault detected");
00046                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_COMMS_ERROR )
00047                     ADI_SENSE_LOG_INFO("\t\t\tInternal Communications fault detected");
00048                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_SUPPLY_MONITOR_ERROR )
00049                     ADI_SENSE_LOG_INFO("\t\t\tSupply Monitor fault detected");
00050                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_SUPPLY_CAP_ERROR )
00051                     ADI_SENSE_LOG_INFO("\t\t\tSupply Regulator Capacitor fault detected");
00052                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_AINM_UV_ERROR )
00053                     ADI_SENSE_LOG_INFO("\t\t\tNegative Analog Input Under-Voltage fault detected");
00054                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_AINM_OV_ERROR )
00055                     ADI_SENSE_LOG_INFO("\t\t\tNegative Analog Input Over-Voltage fault detected");
00056                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_AINP_UV_ERROR )
00057                     ADI_SENSE_LOG_INFO("\t\t\tPositive Analog Input Under-Voltage fault detected");
00058                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_AINP_OV_ERROR )
00059                     ADI_SENSE_LOG_INFO("\t\t\tPositive Analog Input Over-Voltage fault detected");
00060                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_CONVERSION_ERROR )
00061                     ADI_SENSE_LOG_INFO("\t\t\tInternal ADC Conversions fault detected");
00062                 if (pStatus->diagnosticsStatus  & ADI_SENSE_DIAGNOSTICS_STATUS_CALIBRATION_ERROR )
00063                     ADI_SENSE_LOG_INFO("\t\t\tInternal Device Calibrations fault detected");
00064             }
00065         }
00066 
00067         if (pStatus->deviceStatus  & ADI_SENSE_DEVICE_STATUS_ALERT )
00068         {
00069             ADI_SENSE_LOG_INFO("\tActive Alerts - ATTENTION REQUIRED:");
00070             ADI_SENSE_LOG_INFO("\t\tLast Alert Code: %u (0x%X)",
00071                                pStatus->alertCode , pStatus->alertCode );
00072 
00073             for (unsigned i = 0; i < ADI_SENSE_1000_MAX_CHANNELS ; i++)
00074             {
00075                 if (pStatus->channelAlerts [i] == 0)
00076                     continue;
00077 
00078                 ADI_SENSE_LOG_INFO("\t\tChannel #%u:", i);
00079                 ADI_SENSE_LOG_INFO("\t\t\tLast Alert Code: %u (0x%X)",
00080                                    pStatus->channelAlertCodes [i],
00081                                    pStatus->channelAlertCodes [i]);
00082                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_TIMEOUT )
00083                     ADI_SENSE_LOG_INFO("\t\t\tTimeout alert detected");
00084                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_UNDER_RANGE )
00085                     ADI_SENSE_LOG_INFO("\t\t\tUnder Range alert detected");
00086                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_OVER_RANGE )
00087                     ADI_SENSE_LOG_INFO("\t\t\tOver Range alert detected");
00088                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_LOW_LIMIT )
00089                     ADI_SENSE_LOG_INFO("\t\t\tLow limit alert detected");
00090                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_HIGH_LIMIT )
00091                     ADI_SENSE_LOG_INFO("\t\t\tHigh Limit alert detected");
00092                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_SENSOR_OPEN )
00093                     ADI_SENSE_LOG_INFO("\t\t\tSensor Fault alert detected");
00094                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_REF_DETECT )
00095                     ADI_SENSE_LOG_INFO("\t\t\tReference Detection alert detected");
00096                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_CONFIG_ERR )
00097                     ADI_SENSE_LOG_INFO("\t\t\tConfiguration Error alert detected");
00098                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_LUT_ERR )
00099                     ADI_SENSE_LOG_INFO("\t\t\tLook-Up Table Error alert detected");
00100                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_SENSOR_NOT_READY )
00101                     ADI_SENSE_LOG_INFO("\t\t\tSensor Not Ready alert detected");
00102                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_COMP_NOT_READY )
00103                     ADI_SENSE_LOG_INFO("\t\t\tCompensation Channel Not Ready alert detected");
00104                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_UNDER_VOLTAGE )
00105                     ADI_SENSE_LOG_INFO("\t\t\tUnder Voltage alert detected");
00106                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_OVER_VOLTAGE )
00107                     ADI_SENSE_LOG_INFO("\t\t\tOver Voltage alert detected");
00108                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_LUT_UNDER_RANGE )
00109                     ADI_SENSE_LOG_INFO("\t\t\tUnder Look-Up Table Range alert detected");
00110                 if (pStatus->channelAlerts [i] & ADI_SENSE_CHANNEL_ALERT_LUT_OVER_RANGE )
00111                     ADI_SENSE_LOG_INFO("\t\t\tOver Look-Up Table Range alert detected");
00112             }
00113         }
00114     }
00115 }
00116 
00117 void utils_printSamples(
00118     ADI_SENSE_DATA_SAMPLE  *pSampleBuffer,
00119     uint32_t nNumSamples)
00120 {
00121     for (uint32_t i = 0; i < nNumSamples; i++)
00122     {
00123         ADI_SENSE_LOG_INFO("Sample # %2d Channel # %2d :: Raw %8d  :: Processed %.7f :: flags: %s %s",
00124                            i+1,
00125                            pSampleBuffer[i].channelId,
00126                            pSampleBuffer[i].rawValue,
00127                            pSampleBuffer[i].processedValue,
00128                            pSampleBuffer[i].status & ADI_SENSE_DEVICE_STATUS_ERROR  ? "ERROR" : "",
00129                            pSampleBuffer[i].status & ADI_SENSE_DEVICE_STATUS_ALERT  ? "ALERT" : "");
00130     }
00131 }
00132 
00133 static void gpioCallbackFn(ADI_SENSE_GPIO_PIN  ePinId, void * pArg)
00134 {
00135     volatile bool_t *pbFlag = (volatile bool_t *)pArg;
00136     *pbFlag = true;
00137 }
00138 
00139 ADI_SENSE_RESULT  utils_registerCallbacks(
00140     ADI_SENSE_DEVICE_HANDLE  hDevice,
00141     volatile bool_t *pbDataReady,
00142     volatile bool_t *pbError,
00143     volatile bool_t *pbAlert)
00144 {
00145     ADI_SENSE_RESULT  res;
00146 
00147     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_DATAREADY ,
00148                                          gpioCallbackFn, (void *)pbDataReady);
00149     if (res != ADI_SENSE_SUCCESS )
00150     {
00151         ADI_SENSE_LOG_ERROR("Failed to register DATAREADY callback");
00152         return res;
00153     }
00154 
00155     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_ERROR ,
00156                                          gpioCallbackFn, (void *)pbError);
00157     if (res != ADI_SENSE_SUCCESS )
00158     {
00159         ADI_SENSE_LOG_ERROR("Failed to register ERROR callback");
00160         return res;
00161     }
00162 
00163     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_ALERT ,
00164                                          gpioCallbackFn, (void *)pbAlert);
00165     if (res != ADI_SENSE_SUCCESS )
00166     {
00167         ADI_SENSE_LOG_ERROR("Failed to register ALERT callback");
00168         return res;
00169     }
00170 
00171     return ADI_SENSE_SUCCESS ;
00172 }
00173 
00174 ADI_SENSE_RESULT  utils_deregisterCallbacks(
00175     ADI_SENSE_DEVICE_HANDLE  hDevice)
00176 {
00177     ADI_SENSE_RESULT  res;
00178 
00179     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_DATAREADY ,
00180                                          NULL, NULL);
00181     if (res != ADI_SENSE_SUCCESS )
00182     {
00183         ADI_SENSE_LOG_ERROR("Failed to deregister DATAREADY callback");
00184         return res;
00185     }
00186 
00187     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_ERROR ,
00188                                          NULL, NULL);
00189     if (res != ADI_SENSE_SUCCESS )
00190     {
00191         ADI_SENSE_LOG_ERROR("Failed to deregister ERROR callback");
00192         return res;
00193     }
00194 
00195     res = adi_sense_RegisterGpioCallback(hDevice, ADI_SENSE_GPIO_PIN_ALERT ,
00196                                          NULL, NULL);
00197     if (res != ADI_SENSE_SUCCESS )
00198     {
00199         ADI_SENSE_LOG_INFO("Failed to deregister ALERT callback");
00200         return res;
00201     }
00202 
00203     return ADI_SENSE_SUCCESS ;
00204 }
00205 
00206 ADI_SENSE_RESULT  utils_runMeasurement(
00207     ADI_SENSE_DEVICE_HANDLE  hDevice,
00208     ADI_SENSE_MEASUREMENT_MODE  eMeasurementMode)
00209 {
00210     ADI_SENSE_RESULT  res;
00211 
00212     volatile bool_t bDataReady = false;
00213     volatile bool_t bError = false;
00214     volatile bool_t bAlert = false;
00215     res = utils_registerCallbacks(hDevice, &bDataReady, &bError, &bAlert);
00216     if (res != ADI_SENSE_SUCCESS )
00217         return res;
00218 
00219     /*
00220      * Retrieve the number of samples per cycle, per DATAREADY pulse, etc. for this configuration.
00221      */
00222     ADI_SENSE_1000_OPERATING_MODE  eOperatingMode;
00223     ADI_SENSE_1000_DATAREADY_MODE  eDataReadyMode;
00224     uint32_t nSamplesPerDataready;
00225     uint32_t nSamplesPerCycle;
00226     res = adi_sense_1000_GetDataReadyModeInfo(hDevice,
00227                                               eMeasurementMode,
00228                                               &eOperatingMode,
00229                                               &eDataReadyMode,
00230                                               &nSamplesPerDataready,
00231                                               &nSamplesPerCycle);
00232     if (res != ADI_SENSE_SUCCESS )
00233         return res;
00234 
00235     /*
00236      * Allocate a buffer to store the samples retrieved on each DATAREADY pulse
00237      * However, if the DATAREADY pulse is per-conversion, allocate a bigger buffer
00238      * to accumulate a full cycle of samples before printing them
00239      */
00240     ADI_SENSE_DATA_SAMPLE  *pSampleBuffer;
00241     if (eDataReadyMode == ADI_SENSE_1000_DATAREADY_PER_CONVERSION )
00242         pSampleBuffer = malloc(sizeof(ADI_SENSE_DATA_SAMPLE ) * nSamplesPerCycle);
00243     else
00244         pSampleBuffer = malloc(sizeof(ADI_SENSE_DATA_SAMPLE ) * nSamplesPerDataready);
00245     if (pSampleBuffer == NULL)
00246     {
00247         ADI_SENSE_LOG_ERROR("Failed to allocate sample buffer");
00248         return ADI_SENSE_NO_MEM ;
00249     }
00250 
00251     /*
00252      * Kick off the measurement cycle(s) here
00253      */
00254     res = adi_sense_StartMeasurement(hDevice, eMeasurementMode);
00255     if (res != ADI_SENSE_SUCCESS )
00256     {
00257         ADI_SENSE_LOG_ERROR("Failed to start measurement");
00258         return res;
00259     }
00260 
00261     /*
00262      * Loop continuously unless operating mode is single-cycle
00263      */
00264     do {
00265         ADI_SENSE_STATUS  status;
00266         uint32_t nCurrentSamples;
00267         uint32_t nReturned;
00268         nCurrentSamples = 0;
00269 
00270         /*
00271          * Accumulate the samples from a cycle and print them
00272          * NOTE: requires a sufficient idle time between cycles to allow printing to occur
00273          */
00274         do {
00275             /*
00276              * Wait for the cycle to complete, continuously checking DATAREADY until it is asserted
00277              */
00278             while (! (bDataReady || bError))
00279                 ;
00280 
00281             if (! bError)
00282             {
00283                 /*
00284                  * Retrieve the data samples from the measurement cycle, if no error has occurred
00285                  */
00286                 bDataReady = false;
00287                 res = adi_sense_GetData(hDevice, eMeasurementMode, &pSampleBuffer[nCurrentSamples], nSamplesPerDataready, &nReturned);
00288                 nCurrentSamples += nReturned;
00289                 if (res != ADI_SENSE_SUCCESS )
00290                 {
00291                     if (res == ADI_SENSE_INCOMPLETE )
00292                     {
00293                         /* For this case, let's get the device status and print
00294                          * any samples we did get */
00295                         ADI_SENSE_LOG_WARN("Failed to retrieve all requested data samples");
00296                         break;
00297                     }
00298                     else
00299                     {
00300                         ADI_SENSE_LOG_WARN("Failed to retrieve data samples from device");
00301                         return res;
00302                     }
00303                 }
00304             }
00305         } while (!bError && (nCurrentSamples < nSamplesPerCycle));
00306 
00307         /*
00308          * Display the data samples
00309          */
00310         utils_printSamples(pSampleBuffer, nCurrentSamples);
00311 
00312         /*
00313          * Check and print device status if errors/alerts have been triggered
00314          */
00315         if (bError || bAlert)
00316         {
00317             res = adi_sense_GetStatus(hDevice, &status);
00318             if (res != ADI_SENSE_SUCCESS )
00319             {
00320                 ADI_SENSE_LOG_ERROR("Failed to retrieve device status");
00321                 return res;
00322             }
00323 
00324             if (status.deviceStatus  &
00325                 (ADI_SENSE_DEVICE_STATUS_ERROR  | ADI_SENSE_DEVICE_STATUS_ALERT ))
00326             {
00327                 utils_printStatus(&status);
00328 
00329                 /* Break out of the loop if any errors are raised */
00330                 if (bError)
00331                     break;
00332             }
00333         }
00334     } while (eOperatingMode != ADI_SENSE_1000_OPERATING_MODE_SINGLECYCLE );
00335 
00336     res = adi_sense_StopMeasurement(hDevice);
00337     if (res != ADI_SENSE_SUCCESS )
00338     {
00339         ADI_SENSE_LOG_ERROR("Failed to send stop measurement");
00340         return res;
00341     }
00342 
00343     free(pSampleBuffer);
00344 
00345     res = utils_deregisterCallbacks(hDevice);
00346     if (res != ADI_SENSE_SUCCESS )
00347         return res;
00348 
00349     return ADI_SENSE_SUCCESS ;
00350 }
00351 
00352 ADI_SENSE_RESULT  utils_printCalTable(
00353     ADI_SENSE_DEVICE_HANDLE  hDevice)
00354 {
00355     ADI_SENSE_RESULT  res;
00356     unsigned dataLen, nRows, nColumns, maxLen = 1024;
00357 
00358     float *pCalDataBuffer = malloc(maxLen);
00359     if (pCalDataBuffer == NULL)
00360     {
00361         ADI_SENSE_LOG_ERROR("Failed to allocate calibration data buffer");
00362         return ADI_SENSE_NO_MEM ;
00363     }
00364 
00365     res = adi_sense_1000_ReadCalTable(hDevice,
00366                                       pCalDataBuffer, maxLen,
00367                                       &dataLen, &nRows, &nColumns);
00368     if (res != ADI_SENSE_SUCCESS )
00369     {
00370         ADI_SENSE_LOG_ERROR("Failed to read calibration data");
00371         free(pCalDataBuffer);
00372         return res;
00373     }
00374 
00375     ADI_SENSE_LOG_INFO("Calibration Table:\r\n");
00376     ADI_SENSE_LOG_INFO("%6s| %10s | %10s | %10s |", "index", "25", "-40", "85");
00377     for (unsigned row = 0; row < nRows; row++)
00378     {
00379         ADI_SENSE_LOG_INFO("%6d| %10f | %10f | %10f |",
00380                            row,
00381                            pCalDataBuffer[(row * nColumns) + 0],
00382                            pCalDataBuffer[(row * nColumns) + 1],
00383                            pCalDataBuffer[(row * nColumns) + 2]);
00384     }
00385 
00386     free(pCalDataBuffer);
00387     return ADI_SENSE_SUCCESS ;
00388 }
00389