Support KL25z USB logger

Dependents:   kl25z_Usb_Logger

Fork of FastAnalogIn by Erik -

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers FastAnalogIn_LPC11UXX.cpp Source File

FastAnalogIn_LPC11UXX.cpp

00001 #ifdef TARGET_LPC11UXX
00002 
00003 #include "FastAnalogIn.h"
00004 static inline int div_round_up(int x, int y)
00005 {
00006     return (x + (y - 1)) / y;
00007 }
00008 
00009 #define LPC_IOCON0_BASE (LPC_IOCON_BASE)
00010 #define LPC_IOCON1_BASE (LPC_IOCON_BASE + 0x60)
00011 #define MAX_ADC_CLK     4500000
00012 
00013 static const PinMap PinMap_ADC[] = {
00014     {P0_11, ADC0_0, 0x02},
00015     {P0_12, ADC0_1, 0x02},
00016     {P0_13, ADC0_2, 0x02},
00017     {P0_14, ADC0_3, 0x02},
00018     {P0_15, ADC0_4, 0x02},
00019     {P0_16, ADC0_5, 0x01},
00020     {P0_22, ADC0_6, 0x01},
00021     {P0_23, ADC0_7, 0x01},
00022     {NC   , NC    , 0   }
00023 };
00024 
00025 static int channel_usage[8] = {0,0,0,0,0,0,0,0};
00026 
00027 
00028 
00029 FastAnalogIn::FastAnalogIn(PinName pin, bool enabled)
00030 {
00031     ADCnumber = (ADCName)pinmap_peripheral(pin, PinMap_ADC);
00032     if (ADCnumber == (uint32_t)NC)
00033         error("ADC pin mapping failed");
00034     datareg = (uint32_t*) (&LPC_ADC->DR0 + ADCnumber);
00035     
00036     // Power up ADC
00037     LPC_SYSCON->PDRUNCFG &= ~ (1 << 4);
00038     LPC_SYSCON->SYSAHBCLKCTRL |= ((uint32_t)1 << 13);
00039  
00040     uint32_t pin_number = (uint32_t)pin;
00041     __IO uint32_t *reg = (pin_number < 32) ? (__IO uint32_t*)(LPC_IOCON0_BASE + 4 * pin_number) : (__IO uint32_t*)(LPC_IOCON1_BASE + 4 * (pin_number - 32));
00042  
00043     // set pin to ADC mode
00044     *reg &= ~(1 << 7); // set ADMODE = 0 (analog mode)
00045  
00046     uint32_t clkdiv = div_round_up(SystemCoreClock, MAX_ADC_CLK) - 1;
00047  
00048     LPC_ADC->CR = (0 << 0)      // no channels selected
00049                 | (clkdiv << 8) // max of 4.5MHz
00050                 | (1 << 16)     // BURST = 1, hardware controlled
00051                 | ( 0 << 17 );  // CLKS = 0, we stick to 10 bit mode
00052     
00053     pinmap_pinout(pin, PinMap_ADC);
00054 
00055     //Enable channel
00056     running = false;
00057     enable(enabled);
00058 
00059 }
00060 
00061 void FastAnalogIn::enable(bool enabled)
00062 {
00063     //If currently not running
00064     if (!running) {
00065         if (enabled) {
00066             //Enable the ADC channel
00067             channel_usage[ADCnumber]++;
00068             LPC_ADC->CR |= (1<<ADCnumber);
00069             running = true;
00070         } else
00071             disable();
00072     }
00073 }
00074 
00075 void FastAnalogIn::disable( void )
00076 {
00077     //If currently running
00078     if (running) {
00079         channel_usage[ADCnumber]--;
00080         
00081         if (channel_usage[ADCnumber]==0)
00082             LPC_ADC->CR &= ~(1<<ADCnumber);
00083     }
00084     running = false;
00085 }
00086 
00087 unsigned short FastAnalogIn::read_u16( void )
00088 {
00089     unsigned int retval;
00090     //If object is enabled return current value of datareg
00091     if (running)
00092         retval = *datareg;
00093  
00094     //If it isn't running, enable it and wait until new value is written to datareg
00095     else {
00096         //Force a read to clear done bit, enable the ADC channel
00097         retval = *datareg;
00098         enable();
00099         //Wait until it is converted
00100         while(1) {
00101             retval = *datareg;
00102             if ((retval>>31) == 1)
00103                 break;
00104         }
00105         //Disable again
00106         disable();
00107     }
00108     
00109     //Do same thing as standard mbed lib, unused bit 0-3, replicate 4-7 in it
00110     retval &= ~0xFFFF003F;
00111     retval |= (retval >> 6) & 0x003F;
00112     return retval;
00113 }
00114 #endif //defined TARGET_LPC11UXX