Dependencies:   mbed

Revision:
0:f75c555dc52b
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Tue Jan 05 10:46:48 2010 +0000
@@ -0,0 +1,160 @@
+// analog input p20 (ADC0[5], pin 3) test with stats
+
+#include "mbed.h"
+
+// Code from Simon Ford 2010-01-04
+void mbedAdcInit()
+{
+    // power on, clk divider /4
+    LPC_SC->PCONP |= (1 << 12);          
+    LPC_SC->PCLKSEL0 &= ~(0x3 << 24);    
+
+    // software-controlled ADC settings
+    LPC_ADC->ADCR = (0 << 0) // SEL: 0 = no channels selected
+              | (200 << 8)    // CLKDIV: PCLK max ~= 25MHz, /25 to give safe 1MHz
+              | (0 << 16)    // BURST: 0 = software control 
+              | (0 << 17)    // CLKS: not applicable 
+              | (1 << 21)    // PDN: 1 = operational
+              | (0 << 24)    // START: 0 = no start
+              | (0 << 27);   // EDGE: not applicable
+
+    // setup P1_31 as sel 3 (ADC), mode 2 (no pull)    
+    LPC_PINCON->PINSEL3 &= ~((unsigned int)0x3 << 30);
+    LPC_PINCON->PINSEL3 |= (unsigned int)0x3 << 30;
+    
+    LPC_PINCON->PINMODE3 &= ~((unsigned int)0x3 << 30);
+    LPC_PINCON->PINMODE3 |= (unsigned int)0x2 << 30;
+
+}
+
+unsigned int mbedGetVal()
+{
+    // Select channel and start conversion
+    LPC_ADC->ADCR &= ~0xFF;
+    LPC_ADC->ADCR |= 1 << 5; // ADC0[5]
+    LPC_ADC->ADCR |= 1 << 24;
+
+    // Repeatedly get the sample data until DONE bit
+    unsigned int data;
+    do {
+       data = LPC_ADC->ADGDR;
+    } while ((data & ((unsigned int)1 << 31)) == 0);
+       data = LPC_ADC->ADGDR;
+
+    // Stop conversion    
+    LPC_ADC->ADCR &= ~(1 << 24);
+
+    return data;
+}
+
+// Code gleaned from MBED forum
+void DispInfo()
+{
+    printf("SystemCoreClock = %d Hz\n", SystemCoreClock);
+ 
+    int Fin = 12000000; // 12MHz XTAL
+    
+    printf("PLL Registers:\n");
+    printf(" - PLL0CFG = 0x%08X\n", LPC_SC->PLL0CFG);
+    printf(" - CLKCFG  = 0x%08X\n", LPC_SC->CCLKCFG);
+    
+    int M = (LPC_SC->PLL0CFG & 0xFFFF) + 1;
+    int N = (LPC_SC->PLL0CFG >> 16) + 1;
+    int CCLKDIV = LPC_SC->CCLKCFG + 1;
+
+    printf("Clock Variables:\n");
+    printf(" - Fin = %d\n", Fin);
+    printf(" - M   = %d\n", M);
+    printf(" - N   = %d\n", N);
+    printf(" - CCLKDIV = %d\n", CCLKDIV);
+
+    int Fcco = (2 * M * 12000000) / N;
+    int CCLK = Fcco / CCLKDIV;
+
+    printf("Clock Results:\n");    
+    printf(" - Fcco = %d\n", Fcco);
+    printf(" - CCLK = %d\n", CCLK);    
+
+    printf("PCLKSEL0 = 0x%08x\n",  LPC_SC->PCLKSEL0);    
+    printf("PCLKSEL1 = 0x%08x\n",  LPC_SC->PCLKSEL1);    
+    
+}
+
+int main() {
+
+    const int NUM_LOOPS = 100;
+    const int NUM_SAMPS = 1024;
+    
+    mbedAdcInit();
+    wait_ms(100);
+
+    DispInfo();
+
+    // Table of deviation counts
+    const int DEV_HIST_SIZE = 10;
+    int devTable[DEV_HIST_SIZE+1];
+    for (int i = 0; i < DEV_HIST_SIZE+1; i++)
+        devTable[i] = 0;
+
+    // Run many times
+    double mean;
+    double lowestStdDev = 1024;
+    double highestStdDev = 0;
+    double sumForMean = 0;
+    for (int j = 0; j < NUM_LOOPS; j++)
+    {
+        // Get ADC readings
+        unsigned int adgdrVals[NUM_SAMPS];
+        unsigned int samples[NUM_SAMPS];
+        for(int i=0; i<NUM_SAMPS; i++) {
+            adgdrVals[i] = mbedGetVal();
+            samples[i] = (adgdrVals[i] >> 5) & 0x3ff;
+            wait_ms(1);
+        }
+    
+        // Calculate mean
+        double localSum = 0;
+        for(int i=0; i<NUM_SAMPS; i++)
+            localSum += samples[i];
+        double localMean = localSum / NUM_SAMPS;
+        sumForMean += localSum;
+        
+        // Calculate std-dev sum
+        double sumSqrDiffs = 0;
+        for(int i=0; i<NUM_SAMPS; i++)
+            sumSqrDiffs += (samples[i] - localMean) * (samples[i] - localMean);
+            
+        // Calculate stdDev and see if low/high
+        double stdDev = sqrt(sumSqrDiffs / NUM_SAMPS);
+        if (lowestStdDev > stdDev)
+            lowestStdDev = stdDev;
+        if (highestStdDev < stdDev)
+            highestStdDev = stdDev;
+        
+        // Histogram of values
+        for (int i = 0; i < NUM_SAMPS; i++)
+        {
+            int outOfBoundsDist = int(fabs(samples[i] - localMean));
+            if (outOfBoundsDist >= DEV_HIST_SIZE)
+                devTable[DEV_HIST_SIZE]++;
+            else
+                devTable[outOfBoundsDist]++;
+        }
+        
+        // Show results that are out of bounds
+        printf("Results out of bounds for pass %d:\n", j);
+        for(int i=0; i<NUM_SAMPS; i++) {
+            if (fabs(samples[i] - localMean) > 5)
+                printf("%5d, 0x%04X, %d\n", i, adgdrVals[i], samples[i]);
+        }
+    }
+    
+    // Show overall stats
+    mean = sumForMean / NUM_SAMPS / NUM_LOOPS;
+    printf("Mean: %.2f\n", mean);
+    printf("Std-dev (highest, lowest): %.2f, %.2f\n", highestStdDev, lowestStdDev);
+    printf("Deviation Table\n");
+    printf("Dist.\tCount\n");
+    for (int i = 0; i < DEV_HIST_SIZE+1; i++)
+        printf("%s%d\t%d\n", i == DEV_HIST_SIZE ? "> " : "", i, devTable[i]);
+}