James Reynolds / AD594x Driver
Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

Go to the documentation of this file.
00001 /*!
00002  *****************************************************************************
00003   @file:    main.cpp
00004   @author:  J. Reynolds
00005   @brief:   An example of using the impedance example provided by AD with Mbed
00006 -----------------------------------------------------------------------------
00007 @license: https://github.com/analogdevicesinc/ad5940-examples/blob/master/LICENSE (accessed on March 8, 2021)
00008 
00009 This file is a MODIFIED VERSION of the source code provided from Analog Devices!
00010 https://github.com/analogdevicesinc/ad5940-examples/tree/master/examples/AD5940_Impedance
00011 
00012 Tested using the AD5941 on a custom board using the NUCLEO-L552ZE-Q with a bare metal profile.
00013 
00014 *****************************************************************************/
00015 
00016 #include "mbed.h"
00017 #include "Impedance.h"
00018 #include "ad5940.h"
00019 
00020 
00021 
00022 #define WAIT_TIME_MS 500 
00023 DigitalOut led1(LED1);
00024 
00025 #define APPBUFF_SIZE 512
00026 uint32_t AppBuff[APPBUFF_SIZE];
00027 
00028 int32_t ImpedanceShowResult(uint32_t *pData, uint32_t DataCount)
00029 {
00030   float freq;
00031 
00032   fImpPol_Type *pImp = (fImpPol_Type*)pData;
00033   AppIMPCtrl(IMPCTRL_GETFREQ, &freq);
00034 
00035   printf("Freq:%.2f ", freq);
00036   /*Process data*/
00037   for(int i=0;i<DataCount;i++)
00038   {
00039     printf("RzMag: %f Ohm , RzPhase: %f \n",pImp[i].Magnitude,pImp[i].Phase*180/MATH_PI);
00040   }
00041   return 0;
00042 }
00043 
00044 static int32_t AD5940PlatformCfg(void)
00045 {
00046   CLKCfg_Type clk_cfg;
00047   FIFOCfg_Type fifo_cfg;
00048   AGPIOCfg_Type gpio_cfg;
00049 
00050   /* Use hardware reset */
00051   AD5940_HWReset();
00052   AD5940_Initialize();
00053   /* Platform configuration */
00054   /* Step1. Configure clock */
00055   clk_cfg.ADCClkDiv = ADCCLKDIV_1;
00056   clk_cfg.ADCCLkSrc = ADCCLKSRC_HFOSC;
00057   clk_cfg.SysClkDiv = SYSCLKDIV_1;
00058   clk_cfg.SysClkSrc = SYSCLKSRC_HFOSC;
00059   clk_cfg.HfOSC32MHzMode = bFALSE;
00060   clk_cfg.HFOSCEn = bTRUE;
00061   clk_cfg.HFXTALEn = bFALSE;
00062   clk_cfg.LFOSCEn = bTRUE;
00063   AD5940_CLKCfg(&clk_cfg);
00064   /* Step2. Configure FIFO and Sequencer*/
00065   fifo_cfg.FIFOEn = bFALSE;
00066   fifo_cfg.FIFOMode = FIFOMODE_FIFO;
00067   fifo_cfg.FIFOSize = FIFOSIZE_4KB;                       /* 4kB for FIFO, The reset 2kB for sequencer */
00068   fifo_cfg.FIFOSrc = FIFOSRC_DFT;
00069   fifo_cfg.FIFOThresh = 4;//AppIMPCfg.FifoThresh;        /* DFT result. One pair for RCAL, another for Rz. One DFT result have real part and imaginary part */
00070   AD5940_FIFOCfg(&fifo_cfg);
00071   fifo_cfg.FIFOEn = bTRUE;
00072   AD5940_FIFOCfg(&fifo_cfg);
00073   
00074   /* Step3. Interrupt controller */
00075   AD5940_INTCCfg(AFEINTC_1, AFEINTSRC_ALLINT, bTRUE);   /* Enable all interrupt in INTC1, so we can check INTC flags */
00076   AD5940_INTCClrFlag(AFEINTSRC_ALLINT);
00077   AD5940_INTCCfg(AFEINTC_0, AFEINTSRC_DATAFIFOTHRESH, bTRUE); 
00078   AD5940_INTCClrFlag(AFEINTSRC_ALLINT);
00079   /* Step4: Reconfigure GPIO */
00080   gpio_cfg.FuncSet = GP0_INT|GP1_SLEEP|GP2_SYNC;
00081   gpio_cfg.InputEnSet = 0;
00082   gpio_cfg.OutputEnSet = AGPIO_Pin0|AGPIO_Pin1|AGPIO_Pin2;
00083   gpio_cfg.OutVal = 0;
00084   gpio_cfg.PullEnSet = 0;
00085   AD5940_AGPIOCfg(&gpio_cfg);
00086   AD5940_SleepKeyCtrlS(SLPKEY_UNLOCK);  /* Allow AFE to enter sleep mode. */
00087   return 0;
00088 }
00089 
00090 void AD5940ImpedanceStructInit(void)
00091 {
00092   AppIMPCfg_Type *pImpedanceCfg;
00093   
00094   AppIMPGetCfg(&pImpedanceCfg);
00095   /* Step1: configure initialization sequence Info */
00096   pImpedanceCfg->SeqStartAddr = 0;
00097   pImpedanceCfg->MaxSeqLen = 512; /* @todo add checker in function */
00098 
00099   pImpedanceCfg->RcalVal = 10000.0;
00100   pImpedanceCfg->SinFreq = 60000.0;
00101   pImpedanceCfg->FifoThresh = 4;
00102   pImpedanceCfg->DacVoltPP = 800;
00103     
00104 
00105     pImpedanceCfg->DswitchSel = SWD_AIN1;
00106     pImpedanceCfg->PswitchSel = SWP_AIN1;
00107     pImpedanceCfg->NswitchSel = SWN_AIN3;
00108     pImpedanceCfg->TswitchSel = SWT_AIN3;
00109     /* The dummy sensor is as low as 5kOhm. We need to make sure RTIA is small enough that HSTIA won't be saturated. */
00110     pImpedanceCfg->HstiaRtiaSel = HSTIARTIA_5K; 
00111     
00112     /* Configure the sweep function. */
00113     pImpedanceCfg->SweepCfg.SweepEn = bTRUE;
00114     pImpedanceCfg->SweepCfg.SweepStart = 1e2f;  /* Start from 100Hz */
00115     pImpedanceCfg->SweepCfg.SweepStop = 50e3f;  /* Stop at 500kHz */
00116     pImpedanceCfg->SweepCfg.SweepPoints = 50;
00117     pImpedanceCfg->SweepCfg.SweepLog = bTRUE;
00118     /* Configure Power Mode. Use HP mode if frequency is higher than 80kHz. */
00119     pImpedanceCfg->PwrMod = AFEPWR_LP;
00120     /* Configure filters if necessary */
00121     pImpedanceCfg->ADCSinc3Osr = ADCSINC3OSR_2;     /* Sample rate is 800kSPS/2 = 400kSPS */
00122   pImpedanceCfg->DftNum = DFTNUM_16384;
00123   pImpedanceCfg->DftSrc = DFTSRC_SINC3;
00124 }
00125 
00126 int main()
00127 {
00128     printf("AD5940 Impedance test on Mbed OS %d.%d.%d.\n", MBED_MAJOR_VERSION, MBED_MINOR_VERSION, MBED_PATCH_VERSION);
00129   uint32_t temp;  
00130   AD5940PlatformCfg();
00131   AD5940ImpedanceStructInit();
00132   
00133   AppIMPInit(AppBuff, APPBUFF_SIZE);    /* Initialize IMP application. Provide a buffer, which is used to store sequencer commands */
00134   AppIMPCtrl(IMPCTRL_START, 0);          /* Control IMP measurement to start. Second parameter has no meaning with this command. */
00135  
00136   while(1)
00137   {
00138     if(AD5940_GetMCUIntFlag())
00139     {
00140       AD5940_ClrMCUIntFlag();
00141       temp = APPBUFF_SIZE;
00142       AppIMPISR (AppBuff, &temp);
00143       ImpedanceShowResult(AppBuff, temp);
00144     }
00145   }
00146 }