]> rtime.felk.cvut.cz Git - pes-rpp/rpp-lib.git/blob - rpp/src/drv/adc.c
Finished to implement AIN RPP API.
[pes-rpp/rpp-lib.git] / rpp / src / drv / adc.c
1 /* Copyright (C) 2012-2013 Czech Technical University in Prague
2  *
3  * Authors:
4  *     - Michal Horn
5  *     - Carlos Jenkins <carlos@jenkins.co.cr>
6  *
7  * This program is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
19  *
20  * File : adc.c
21  * Abstract:
22  *     RPP driver implementation for ADC.
23  *
24  * References:
25  *     ti_drv_adc.c
26  */
27
28
29 #include "drv/adc.h"
30
31 // Semaphore for ADC conversion
32 xSemaphoreHandle adcSemaphore_ADC1GRP1;
33
34
35 void drv_adc_init()
36 {
37     // Create semaphore
38     vSemaphoreCreateBinary(adcSemaphore_ADC1GRP1);
39
40     // Low level init
41     adcInit();
42 }
43
44
45 /**
46  * Function called by ADC interrupt handler, stores data from ADC
47  *
48  * If conversion has finished on ADC, store measured data and detect weather right number of channels was measured.
49  * If memory overrun was detected, set appropriate flag, reset ADC FIFO to be allow future measurement.
50  *
51  *   @param[in] adc Pointer to ADC module:
52  *              - adcREG1: ADC1 module pointer
53  *              - adcREG2: ADC2 module pointer
54  *   @param[in] group Hardware group of ADC module:
55  *              - adcGROUP0: ADC event group
56  *              - adcGROUP1: ADC group 1
57  *              - adcGROUP2: ADC group 2
58  */
59 void adcNotification(adcBASE_t *adc, uint32_t group)
60 {
61     if(adcIsConversionComplete(adc, group) == ADC_CONVERSION_IS_FINISHED) {
62
63         // ADC1
64         if(adc == adcREG1) {
65             switch(group) {
66                 case adcGROUP0:
67                     // Group0 is unused on RPP
68                     break;
69                 case adcGROUP1:
70                     xSemaphoreGiveFromISR(adcSemaphore_ADC1GRP1, NULL);
71                     break;
72                 default:
73                     // Group2 is unused on RPP
74                     break;
75             }
76         // ADC2
77         } else {
78             switch(group) {
79                 case adcGROUP0:
80                     // Group0 is unused on RPP
81                     break;
82                 case adcGROUP1:
83                     // Group1 is unused on RPP
84                     break;
85                 default:
86                     // Group2 is unused on RPP
87                     break;
88             }
89         }
90     }
91 }
92
93
94 uint32_t drv_adc_generic_read(adcBASE_t *adc, uint32_t group,
95                                xSemaphoreHandle adcSemaphore, adcData_t* data)
96 {
97     // Calibrate
98     adcCalibration(adc);
99     adcMidPointCalibration(adc);
100
101     // Start conversion
102     adcEnableNotification(adc, group);
103     adcStartConversion(adc, group);
104
105     // Wait for conversion to complete
106     xSemaphoreTake(adcSemaphore, portMAX_DELAY);
107     adcDisableNotification(adc, group);
108
109     // Get data
110     uint32_t channels = adcGetData(adc, group, data);
111
112     // Check if memory overrun
113     if(adcIsFifoFull(adc, group) == ADC_FIFO_OVERFLOW) {
114         // FIXME Should report somehow.
115         adcResetFiFo(adc, group);
116     }
117
118     return channels;
119 }
120
121
122 uint32_t drv_adc_read(adcData_t* data)
123 {
124     return drv_adc_generic_read(adcREG1,
125                                  adcGROUP1,
126                                  adcSemaphore_ADC1GRP1,
127                                  data
128                             );
129 }
130
131 // FIXME make it work again
132 uint32_t adc_get_port_val(uint32_t* config, uint32_t num_channels,
133                            uint32_t* values) {
134     /*
135     uint32_t i;
136     adcBASE_t* adcReg = (adcBASE_t *)config[0];
137     uint32_t adcGroup = config[1];
138
139     adcData.adc_data = adc_data_origin;
140     adcData.ch_count = num_channels;
141     if (read_adc(adcReg, adcGroup) == 1)
142         return 1;
143
144     for (i = 0; i < num_channels; i++) {
145         values[i] = adcData.adc_data[i].value;
146         values[i+num_channels] = adcData.adc_data[i].id;
147     }
148     adcData.adc_data = NULL;
149     */
150     return 0;
151 }
152