Xmega IEC60730 Class B Library  1.0
 All Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
classb_analog.c
Go to the documentation of this file.
1 /* This file has been prepared for Doxygen automatic documentation generation.*/
2 /**
3  * \file
4  *
5  * \brief This is the code for the ADC and DAC tests.
6  *
7  * \par Application note:
8  * AVR1610: Guide to IEC60730 Class B compliance with XMEGA
9  *
10  * \par Documentation
11  * For comprehensive code documentation, supported compilers, compiler
12  * settings and supported devices see readme.html
13  *
14  * \author
15  * Atmel Corporation: http://www.atmel.com \n
16  * Support email: avr@atmel.com
17  *
18  * Copyright (C) 2012 Atmel Corporation. All rights reserved.
19  *
20  * \page License
21  *
22  * Redistribution and use in source and binary forms, with or without
23  * modification, are permitted provided that the following conditions are met:
24  *
25  * 1. Redistributions of source code must retain the above copyright notice,
26  * this list of conditions and the following disclaimer.
27  *
28  * 2. Redistributions in binary form must reproduce the above copyright notice,
29  * this list of conditions and the following disclaimer in the documentation
30  * and/or other materials provided with the distribution.
31  *
32  * 3. The name of Atmel may not be used to endorse or promote products derived
33  * from this software without specific prior written permission.
34  *
35  * 4. This software may only be redistributed and used in connection with an
36  * Atmel AVR product.
37  *
38  * THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR IMPLIED
39  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
40  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
41  * EXPRESSLY AND SPECIFICALLY DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR
42  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
43  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
44  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
45  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
46  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
47  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
48  * DAMAGE.
49  */
50 
51 #include "classb_analog.h"
52 
53 // Global error variable.
54 extern volatile uint8_t classb_error;
55 
56 
57 /*!
58  * \internal
59  * \brief This test writes a value to the DAC, and checks that the ADC readouts are
60  * within the expected range.
61  */
62 static void classb_dac_adc_test(DAC_t *dacptr, ADC_t *adcptr, uint16_t dac_out, uint16_t adc_assert) {
63 
64  // Deviation in measurements.
65  int16_t adcDev;
66 
67  // Write to DAC and wait until it's stable
68  dacptr->CH0DATA = dac_out;
69  while( !(dacptr->STATUS & DAC_CH0DRE_bm) );
70 
71  // Clear interrupt flag channel 3
72  adcptr->CH3.INTFLAGS = ADC_CH_CHIF_bm;
73  // Start AD-conversions in channels 0 to 3.
74  adcptr->CTRLA |= (ADC_CH0START_bm | ADC_CH1START_bm | ADC_CH2START_bm | ADC_CH3START_bm);
75  // Use channel 3 interrupt flag to detect end of conversion
76  // (channel 3 has the lowest priority).
77  while( !(adcptr->CH3.INTFLAGS & ADC_CH_CHIF_bm) );
78 
79  // Do a range check on the conversion results.
80  adcDev = adcptr->CH0RES - adc_assert;
81  if (abs(adcDev) > CLASSB_ADC_DEV)
83 
84  adcDev = adcptr->CH1RES - adc_assert;
85  if (abs(adcDev) > CLASSB_ADC_DEV)
87 
88  adcDev = adcptr->CH2RES - adc_assert;
89  if (abs(adcDev) > CLASSB_ADC_DEV)
91 
92  adcDev = adcptr->CH3RES - adc_assert;
93  if (abs(adcDev) > CLASSB_ADC_DEV)
95 
96  // Clear interrupt flags.
97  adcptr->CH0.INTFLAGS = ADC_CH_CHIF_bm;
98  adcptr->CH1.INTFLAGS = ADC_CH_CHIF_bm;
99  adcptr->CH2.INTFLAGS = ADC_CH_CHIF_bm;
100  adcptr->CH3.INTFLAGS = ADC_CH_CHIF_bm;
101 }
102 
103 /*! \brief Functional test for the ADC, DAC and analog MUX.
104  *
105  * This function configures the DAC to output a constant voltage, after which
106  * the ADC is set to do 12 bit, signed conversions of the DAC.
107  * Range checking of the conversion results is then done to verify that ADC and DAC
108  * are working correctly.
109  *
110  * \param dacptr Base address for registers of DAC module to test.
111  * \param adcptr Base address for registers of ADC module to test.
112  *
113  */
114 void classb_analog_io_test(DAC_t *dacptr, ADC_t *adcptr)
115 {
116 
117  // Set up the DAC
118  // Single channel, 1V reference, internal output,
119  dacptr->CTRLA = DAC_IDOEN_bm | DAC_ENABLE_bm;
120  dacptr->CTRLB = DAC_CHSEL_SINGLE_gc;
121  dacptr->CTRLC = DAC_REFSEL_INT1V_gc;
122  //dacptr->TIMCTRL = DAC_CONINTVAL_32CLK_gc;
123 
124  // Set up the ADC
125  // All channels will be connected to an internal input.
126  adcptr->CH0.CTRL = ADC_CH_INPUTMODE_INTERNAL_gc;
127  adcptr->CH1.CTRL = ADC_CH_INPUTMODE_INTERNAL_gc;
128  adcptr->CH2.CTRL = ADC_CH_INPUTMODE_INTERNAL_gc;
129  adcptr->CH3.CTRL = ADC_CH_INPUTMODE_INTERNAL_gc;
130 
131  // MUX selection: measure from DAC.
132  adcptr->CH0.MUXCTRL = ADC_CH_MUXINT_DAC_gc;
133  adcptr->CH1.MUXCTRL = ADC_CH_MUXINT_DAC_gc;
134  adcptr->CH2.MUXCTRL = ADC_CH_MUXINT_DAC_gc;
135  adcptr->CH3.MUXCTRL = ADC_CH_MUXINT_DAC_gc;
136 
137  // Enable ADC
138  adcptr->CTRLA = ADC_ENABLE_bm;
139  // Signed conversions, 12 bit resolution
140  adcptr->CTRLB = ADC_CONMODE_bm | ADC_RESOLUTION_12BIT_gc;
141  // 1V reference
142  adcptr->REFCTRL = ADC_REFSEL_INT1V_gc;
143  // Pre-scale clock by 512.
144  adcptr->PRESCALER = ADC_PRESCALER_DIV512_gc;
145 
146 
147  // Write five values to the DAC and read them from the ADC.
148  // -For the DAC the range is (0x000,0xFFF)
149  // -For the ADC the positive range is (0x000,0x7FF).
150  // When The DAC generates 25% of its range, we expect 25% of
151  // the range in the ADC. Similarly on the other cases.
152  classb_dac_adc_test(dacptr, adcptr, 0x000, 0x000);
153  classb_dac_adc_test(dacptr, adcptr, 0x400, 0x200);
154  classb_dac_adc_test(dacptr, adcptr, 0x800, 0x400);
155  classb_dac_adc_test(dacptr, adcptr, 0xC00, 0x600);
156  classb_dac_adc_test(dacptr, adcptr, 0xFFF, 0x7FF);
157 
158 
159  // Disable the ADC and DAC
160  adcptr->CTRLA &= ~ADC_ENABLE_bm;
161  dacptr->CTRLA &= ~DAC_ENABLE_bm;
162 }