mbed library sources

Dependents:   Encrypted my_mbed lklk CyaSSL_DTLS_Cellular ... more

Superseded

This library was superseded by mbed-dev - https://os.mbed.com/users/mbed_official/code/mbed-dev/.

Development branch of the mbed library sources. This library is kept in synch with the latest changes from the mbed SDK and it is not guaranteed to work.

If you are looking for a stable and tested release, please import one of the official mbed library releases:

Import librarymbed

The official Mbed 2 C/C++ SDK provides the software platform and libraries to build your applications.

Committer:
bogdanm
Date:
Mon Aug 19 18:17:02 2013 +0300
Revision:
19:398f4c622e1b
Child:
20:4263a77256ae
Sync with official mbed library release 66

Who changed what in which revision?

UserRevisionLine numberNew contents of line
bogdanm 19:398f4c622e1b 1 /* mbed Microcontroller Library
bogdanm 19:398f4c622e1b 2 * Copyright (c) 2006-2013 ARM Limited
bogdanm 19:398f4c622e1b 3 *
bogdanm 19:398f4c622e1b 4 * Licensed under the Apache License, Version 2.0 (the "License");
bogdanm 19:398f4c622e1b 5 * you may not use this file except in compliance with the License.
bogdanm 19:398f4c622e1b 6 * You may obtain a copy of the License at
bogdanm 19:398f4c622e1b 7 *
bogdanm 19:398f4c622e1b 8 * http://www.apache.org/licenses/LICENSE-2.0
bogdanm 19:398f4c622e1b 9 *
bogdanm 19:398f4c622e1b 10 * Unless required by applicable law or agreed to in writing, software
bogdanm 19:398f4c622e1b 11 * distributed under the License is distributed on an "AS IS" BASIS,
bogdanm 19:398f4c622e1b 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
bogdanm 19:398f4c622e1b 13 * See the License for the specific language governing permissions and
bogdanm 19:398f4c622e1b 14 * limitations under the License.
bogdanm 19:398f4c622e1b 15 */
bogdanm 19:398f4c622e1b 16 #include "analogin_api.h"
bogdanm 19:398f4c622e1b 17 #include "cmsis.h"
bogdanm 19:398f4c622e1b 18 #include "pinmap.h"
bogdanm 19:398f4c622e1b 19 #include "error.h"
bogdanm 19:398f4c622e1b 20
bogdanm 19:398f4c622e1b 21 #define ANALOGIN_MEDIAN_FILTER 1
bogdanm 19:398f4c622e1b 22
bogdanm 19:398f4c622e1b 23 #define ADC_10BIT_RANGE 0x3FF
bogdanm 19:398f4c622e1b 24 #define ADC_12BIT_RANGE 0xFFF
bogdanm 19:398f4c622e1b 25
bogdanm 19:398f4c622e1b 26 static inline int div_round_up(int x, int y) {
bogdanm 19:398f4c622e1b 27 return (x + (y - 1)) / y;
bogdanm 19:398f4c622e1b 28 }
bogdanm 19:398f4c622e1b 29
bogdanm 19:398f4c622e1b 30 static const PinMap PinMap_ADC[] = {
bogdanm 19:398f4c622e1b 31 {P0_11, ADC0_0, 2},
bogdanm 19:398f4c622e1b 32 {P1_0 , ADC0_1, 2},
bogdanm 19:398f4c622e1b 33 {P1_1 , ADC0_2, 2},
bogdanm 19:398f4c622e1b 34 {P1_2 , ADC0_3, 2},
bogdanm 19:398f4c622e1b 35 {P1_4 , ADC0_5, 1},
bogdanm 19:398f4c622e1b 36 {P1_10, ADC0_6, 1},
bogdanm 19:398f4c622e1b 37 {P1_11, ADC0_7, 1},
bogdanm 19:398f4c622e1b 38 {NC , NC , 0}
bogdanm 19:398f4c622e1b 39 };
bogdanm 19:398f4c622e1b 40
bogdanm 19:398f4c622e1b 41 #define ADC_RANGE ADC_10BIT_RANGE
bogdanm 19:398f4c622e1b 42
bogdanm 19:398f4c622e1b 43 void analogin_init(analogin_t *obj, PinName pin) {
bogdanm 19:398f4c622e1b 44 obj->adc = (ADCName)pinmap_peripheral(pin, PinMap_ADC);
bogdanm 19:398f4c622e1b 45 if (obj->adc == (uint32_t)NC) {
bogdanm 19:398f4c622e1b 46 error("ADC pin mapping failed");
bogdanm 19:398f4c622e1b 47 }
bogdanm 19:398f4c622e1b 48
bogdanm 19:398f4c622e1b 49 // Power up ADC
bogdanm 19:398f4c622e1b 50 LPC_SYSCON->PDRUNCFG &= ~ (1 << 4);
bogdanm 19:398f4c622e1b 51 LPC_SYSCON->SYSAHBCLKCTRL |= ((uint32_t)1 << 13);
bogdanm 19:398f4c622e1b 52
bogdanm 19:398f4c622e1b 53 uint32_t offset = (uint32_t)pin & 0xff;
bogdanm 19:398f4c622e1b 54 __IO uint32_t *reg = (__IO uint32_t*)(LPC_IOCON_BASE + offset);
bogdanm 19:398f4c622e1b 55
bogdanm 19:398f4c622e1b 56 // set pin to ADC mode
bogdanm 19:398f4c622e1b 57 *reg &= ~(1 << 7); // set ADMODE = 0 (analog mode)
bogdanm 19:398f4c622e1b 58
bogdanm 19:398f4c622e1b 59 uint32_t PCLK = SystemCoreClock;
bogdanm 19:398f4c622e1b 60 uint32_t MAX_ADC_CLK = 4500000;
bogdanm 19:398f4c622e1b 61 uint32_t clkdiv = div_round_up(PCLK, MAX_ADC_CLK) - 1;
bogdanm 19:398f4c622e1b 62
bogdanm 19:398f4c622e1b 63 LPC_ADC->CR = (0 << 0) // no channels selected
bogdanm 19:398f4c622e1b 64 | (clkdiv << 8) // max of 4.5MHz
bogdanm 19:398f4c622e1b 65 | (0 << 16) // BURST = 0, software controlled
bogdanm 19:398f4c622e1b 66 | ( 0 << 17 ); // CLKS = 0, not applicable
bogdanm 19:398f4c622e1b 67
bogdanm 19:398f4c622e1b 68 pinmap_pinout(pin, PinMap_ADC);
bogdanm 19:398f4c622e1b 69 }
bogdanm 19:398f4c622e1b 70
bogdanm 19:398f4c622e1b 71 static inline uint32_t adc_read(analogin_t *obj) {
bogdanm 19:398f4c622e1b 72 // Select the appropriate channel and start conversion
bogdanm 19:398f4c622e1b 73 LPC_ADC->CR &= ~0xFF;
bogdanm 19:398f4c622e1b 74 LPC_ADC->CR |= 1 << (int)obj->adc;
bogdanm 19:398f4c622e1b 75 LPC_ADC->CR |= 1 << 24;
bogdanm 19:398f4c622e1b 76
bogdanm 19:398f4c622e1b 77 // Repeatedly get the sample data until DONE bit
bogdanm 19:398f4c622e1b 78 unsigned int data;
bogdanm 19:398f4c622e1b 79 do {
bogdanm 19:398f4c622e1b 80 data = LPC_ADC->GDR;
bogdanm 19:398f4c622e1b 81 } while ((data & ((unsigned int)1 << 31)) == 0);
bogdanm 19:398f4c622e1b 82
bogdanm 19:398f4c622e1b 83 // Stop conversion
bogdanm 19:398f4c622e1b 84 LPC_ADC->CR &= ~(1 << 24);
bogdanm 19:398f4c622e1b 85
bogdanm 19:398f4c622e1b 86 return (data >> 6) & ADC_RANGE; // 10 bit
bogdanm 19:398f4c622e1b 87 }
bogdanm 19:398f4c622e1b 88
bogdanm 19:398f4c622e1b 89 static inline void order(uint32_t *a, uint32_t *b) {
bogdanm 19:398f4c622e1b 90 if (*a > *b) {
bogdanm 19:398f4c622e1b 91 uint32_t t = *a;
bogdanm 19:398f4c622e1b 92 *a = *b;
bogdanm 19:398f4c622e1b 93 *b = t;
bogdanm 19:398f4c622e1b 94 }
bogdanm 19:398f4c622e1b 95 }
bogdanm 19:398f4c622e1b 96
bogdanm 19:398f4c622e1b 97 static inline uint32_t adc_read_u32(analogin_t *obj) {
bogdanm 19:398f4c622e1b 98 uint32_t value;
bogdanm 19:398f4c622e1b 99 #if ANALOGIN_MEDIAN_FILTER
bogdanm 19:398f4c622e1b 100 uint32_t v1 = adc_read(obj);
bogdanm 19:398f4c622e1b 101 uint32_t v2 = adc_read(obj);
bogdanm 19:398f4c622e1b 102 uint32_t v3 = adc_read(obj);
bogdanm 19:398f4c622e1b 103 order(&v1, &v2);
bogdanm 19:398f4c622e1b 104 order(&v2, &v3);
bogdanm 19:398f4c622e1b 105 order(&v1, &v2);
bogdanm 19:398f4c622e1b 106 value = v2;
bogdanm 19:398f4c622e1b 107 #else
bogdanm 19:398f4c622e1b 108 value = adc_read(obj);
bogdanm 19:398f4c622e1b 109 #endif
bogdanm 19:398f4c622e1b 110 return value;
bogdanm 19:398f4c622e1b 111 }
bogdanm 19:398f4c622e1b 112
bogdanm 19:398f4c622e1b 113 uint16_t analogin_read_u16(analogin_t *obj) {
bogdanm 19:398f4c622e1b 114 uint32_t value = adc_read_u32(obj);
bogdanm 19:398f4c622e1b 115
bogdanm 19:398f4c622e1b 116 return (value << 6) | ((value >> 4) & 0x003F); // 10 bit
bogdanm 19:398f4c622e1b 117 }
bogdanm 19:398f4c622e1b 118
bogdanm 19:398f4c622e1b 119 float analogin_read(analogin_t *obj) {
bogdanm 19:398f4c622e1b 120 uint32_t value = adc_read_u32(obj);
bogdanm 19:398f4c622e1b 121 return (float)value * (1.0f / (float)ADC_RANGE);
bogdanm 19:398f4c622e1b 122 }