]> git.friedersdorff.com Git - max/tmk_keyboard.git/blob - tmk_core/tool/mbed/mbed-sdk/libraries/mbed/targets/hal/TARGET_STM/TARGET_STM32F0/analogout_api.c
Merge commit '1fe4406f374291ab2e86e95a97341fd9c475fcb8'
[max/tmk_keyboard.git] / tmk_core / tool / mbed / mbed-sdk / libraries / mbed / targets / hal / TARGET_STM / TARGET_STM32F0 / analogout_api.c
1 /* mbed Microcontroller Library
2  * Copyright (c) 2014, STMicroelectronics
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright notice,
9  *    this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright notice,
11  *    this list of conditions and the following disclaimer in the documentation
12  *    and/or other materials provided with the distribution.
13  * 3. Neither the name of STMicroelectronics nor the names of its contributors
14  *    may be used to endorse or promote products derived from this software
15  *    without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
21  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
23  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
24  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
25  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 #include "mbed_assert.h"
29 #include "analogout_api.h"
30
31 #if DEVICE_ANALOGOUT
32
33 #include "cmsis.h"
34 #include "pinmap.h"
35 #include "mbed_error.h"
36 #include "PeripheralPins.h"
37
38 #define DAC_RANGE (0xFFF) // 12 bits
39
40 static DAC_HandleTypeDef DacHandle;
41
42 void analogout_init(dac_t *obj, PinName pin)
43 {
44     DAC_ChannelConfTypeDef sConfig;
45
46     DacHandle.Instance = DAC;
47
48     // Get the peripheral name (DAC_1, ...) from the pin and assign it to the object
49     obj->dac = (DACName)pinmap_peripheral(pin, PinMap_DAC);
50     MBED_ASSERT(obj->dac != (DACName)NC);
51
52     // Configure GPIO
53     pinmap_pinout(pin, PinMap_DAC);
54
55     // Save the channel for future use
56     obj->pin = pin;
57
58     // Enable DAC clock
59     __DAC1_CLK_ENABLE();
60
61     // Configure DAC
62     sConfig.DAC_Trigger      = DAC_TRIGGER_NONE;
63     sConfig.DAC_OutputBuffer = DAC_OUTPUTBUFFER_DISABLE;
64
65     if (pin == PA_4) {
66         HAL_DAC_ConfigChannel(&DacHandle, &sConfig, DAC_CHANNEL_1);
67     } else { // PA_5
68         HAL_DAC_ConfigChannel(&DacHandle, &sConfig, DAC_CHANNEL_2);
69     }
70
71     analogout_write_u16(obj, 0);
72 }
73
74 void analogout_free(dac_t *obj)
75 {
76     // Reset DAC and disable clock
77     __DAC1_FORCE_RESET();
78     __DAC1_RELEASE_RESET();
79     __DAC1_CLK_DISABLE();
80
81     // Configure GPIO
82     pin_function(obj->pin, STM_PIN_DATA(STM_MODE_INPUT, GPIO_NOPULL, 0));
83 }
84
85 static inline void dac_write(dac_t *obj, uint16_t value)
86 {
87     if (obj->pin == PA_4) {
88         HAL_DAC_SetValue(&DacHandle, DAC_CHANNEL_1, DAC_ALIGN_12B_R, value);
89         HAL_DAC_Start(&DacHandle, DAC_CHANNEL_1);
90     } else { // PA_5
91         HAL_DAC_SetValue(&DacHandle, DAC_CHANNEL_2, DAC_ALIGN_12B_R, value);
92         HAL_DAC_Start(&DacHandle, DAC_CHANNEL_2);
93     }
94 }
95
96 static inline int dac_read(dac_t *obj)
97 {
98     if (obj->pin == PA_4) {
99         return (int)HAL_DAC_GetValue(&DacHandle, DAC_CHANNEL_1);
100     } else { // PA_5
101         return (int)HAL_DAC_GetValue(&DacHandle, DAC_CHANNEL_2);
102     }
103 }
104
105 void analogout_write(dac_t *obj, float value)
106 {
107     if (value < 0.0f) {
108         dac_write(obj, 0); // Min value
109     } else if (value > 1.0f) {
110         dac_write(obj, (uint16_t)DAC_RANGE); // Max value
111     } else {
112         dac_write(obj, (uint16_t)(value * (float)DAC_RANGE));
113     }
114 }
115
116 void analogout_write_u16(dac_t *obj, uint16_t value)
117 {
118     if (value > (uint16_t)DAC_RANGE) {
119         dac_write(obj, (uint16_t)DAC_RANGE); // Max value
120     } else {
121         dac_write(obj, value);
122     }
123 }
124
125 float analogout_read(dac_t *obj)
126 {
127     uint32_t value = dac_read(obj);
128     return (float)((float)value * (1.0f / (float)DAC_RANGE));
129 }
130
131 uint16_t analogout_read_u16(dac_t *obj)
132 {
133     return (uint16_t)dac_read(obj);
134 }
135
136 #endif // DEVICE_ANALOGOUT