1
+ #include " stm32g4_hal.h"
2
+
3
+ #if defined(STM32G4xx) && !defined(ARDUINO_B_G431B_ESC1)
4
+
5
+ #include " ../../../../communication/SimpleFOCDebug.h"
6
+ #define _TRGO_NOT_AVAILABLE 12345
7
+
8
+
9
+ // timer to injected TRGO
10
+ // https://github.com/stm32duino/Arduino_Core_STM32/blob/6588dee03382e73ed42c4a5e473900ab3b79d6e4/system/Drivers/STM32G4xx_HAL_Driver/Inc/stm32g4xx_hal_adc_ex.h#L217
11
+ uint32_t _timerToInjectedTRGO (HardwareTimer* timer){
12
+ if (timer->getHandle ()->Instance == TIM1)
13
+ return ADC_EXTERNALTRIGINJEC_T1_TRGO;
14
+ #ifdef TIM2 // if defined timer 2
15
+ else if (timer->getHandle ()->Instance == TIM2)
16
+ return ADC_EXTERNALTRIGINJEC_T2_TRGO;
17
+ #endif
18
+ #ifdef TIM3 // if defined timer 3
19
+ else if (timer->getHandle ()->Instance == TIM2)
20
+ return ADC_EXTERNALTRIGINJEC_T3_TRGO;
21
+ #endif
22
+ #ifdef TIM4 // if defined timer 4
23
+ else if (timer->getHandle ()->Instance == TIM4)
24
+ return ADC_EXTERNALTRIGINJEC_T4_TRGO;
25
+ #endif
26
+ #ifdef TIM6 // if defined timer 6
27
+ else if (timer->getHandle ()->Instance == TIM6)
28
+ return ADC_EXTERNALTRIGINJEC_T6_TRGO;
29
+ #endif
30
+ #ifdef TIM7 // if defined timer 7
31
+ else if (timer->getHandle ()->Instance == TIM7)
32
+ return ADC_EXTERNALTRIGINJEC_T7_TRGO;
33
+ #endif
34
+ #ifdef TIM8 // if defined timer 8
35
+ else if (timer->getHandle ()->Instance == TIM8)
36
+ return ADC_EXTERNALTRIGINJEC_T8_TRGO;
37
+ #endif
38
+ #ifdef TIM15 // if defined timer 15
39
+ else if (timer->getHandle ()->Instance == TIM15)
40
+ return ADC_EXTERNALTRIGINJEC_T15_TRGO;
41
+ #endif
42
+ #ifdef TIM20 // if defined timer 15
43
+ else if (timer->getHandle ()->Instance == TIM20)
44
+ return ADC_EXTERNALTRIGINJEC_T20_TRGO;
45
+ #endif
46
+ else
47
+ return _TRGO_NOT_AVAILABLE;
48
+ }
49
+
50
+ // timer to regular TRGO
51
+ // https://github.com/stm32duino/Arduino_Core_STM32/blob/6588dee03382e73ed42c4a5e473900ab3b79d6e4/system/Drivers/STM32G4xx_HAL_Driver/Inc/stm32g4xx_hal_adc.h#L519
52
+ uint32_t _timerToRegularTRGO (HardwareTimer* timer){
53
+ if (timer->getHandle ()->Instance == TIM1)
54
+ return ADC_EXTERNALTRIG_T1_TRGO;
55
+ #ifdef TIM2 // if defined timer 2
56
+ else if (timer->getHandle ()->Instance == TIM2)
57
+ return ADC_EXTERNALTRIG_T2_TRGO;
58
+ #endif
59
+ #ifdef TIM3 // if defined timer 3
60
+ else if (timer->getHandle ()->Instance == TIM2)
61
+ return ADC_EXTERNALTRIG_T3_TRGO;
62
+ #endif
63
+ #ifdef TIM4 // if defined timer 4
64
+ else if (timer->getHandle ()->Instance == TIM4)
65
+ return ADC_EXTERNALTRIG_T4_TRGO;
66
+ #endif
67
+ #ifdef TIM6 // if defined timer 6
68
+ else if (timer->getHandle ()->Instance == TIM6)
69
+ return ADC_EXTERNALTRIG_T6_TRGO;
70
+ #endif
71
+ #ifdef TIM7 // if defined timer 7
72
+ else if (timer->getHandle ()->Instance == TIM7)
73
+ return ADC_EXTERNALTRIG_T7_TRGO;
74
+ #endif
75
+ #ifdef TIM8 // if defined timer 8
76
+ else if (timer->getHandle ()->Instance == TIM8)
77
+ return ADC_EXTERNALTRIG_T7_TRGO;
78
+ #endif
79
+ #ifdef TIM15 // if defined timer 15
80
+ else if (timer->getHandle ()->Instance == TIM15)
81
+ return ADC_EXTERNALTRIG_T15_TRGO;
82
+ #endif
83
+ #ifdef TIM20 // if defined timer 15
84
+ else if (timer->getHandle ()->Instance == TIM20)
85
+ return ADC_EXTERNALTRIG_T20_TRGO;
86
+ #endif
87
+ else
88
+ return _TRGO_NOT_AVAILABLE;
89
+ }
90
+
91
+ ADC_HandleTypeDef hadc;
92
+
93
+ int _adc_init (Stm32CurrentSenseParams* cs_params, const STM32DriverParams* driver_params)
94
+ {
95
+ ADC_InjectionConfTypeDef sConfigInjected ;
96
+ /* *Configure the global features of the ADC (Clock, Resolution, Data Alignment and number of conversion)
97
+ */
98
+ hadc.Instance = (ADC_TypeDef *)pinmap_peripheral (analogInputToPinName (cs_params->pins [0 ]), PinMap_ADC);
99
+
100
+ if (hadc.Instance == ADC1) {
101
+ #ifdef __HAL_RCC_ADC1_CLK_ENABLE
102
+ __HAL_RCC_ADC1_CLK_ENABLE ();
103
+ #endif
104
+ #ifdef __HAL_RCC_ADC12_CLK_ENABLE
105
+ __HAL_RCC_ADC12_CLK_ENABLE ();
106
+ #endif
107
+ }
108
+ #ifdef ADC2
109
+ else if (hadc.Instance == ADC2) {
110
+ #ifdef __HAL_RCC_ADC2_CLK_ENABLE
111
+ __HAL_RCC_ADC2_CLK_ENABLE ();
112
+ #endif
113
+ #ifdef __HAL_RCC_ADC12_CLK_ENABLE
114
+ __HAL_RCC_ADC12_CLK_ENABLE ();
115
+ #endif
116
+ }
117
+ #endif
118
+ #ifdef ADC3
119
+ else if (hadc.Instance == ADC3) {
120
+ #ifdef __HAL_RCC_ADC3_CLK_ENABLE
121
+ __HAL_RCC_ADC3_CLK_ENABLE ();
122
+ #endif
123
+ #ifdef __HAL_RCC_ADC34_CLK_ENABLE
124
+ __HAL_RCC_ADC34_CLK_ENABLE ();
125
+ #endif
126
+ #if defined(ADC345_COMMON)
127
+ __HAL_RCC_ADC345_CLK_ENABLE ();
128
+ #endif
129
+ }
130
+ #endif
131
+ else {
132
+ #ifdef SIMPLEFOC_STM32_DEBUG
133
+ SIMPLEFOC_DEBUG (" STM32-CS: ERR: Pin does not belong to any ADC!" );
134
+ #endif
135
+ return -1 ; // error not a valid ADC instance
136
+ }
137
+
138
+ hadc.Init .ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV4;
139
+ hadc.Init .Resolution = ADC_RESOLUTION_12B;
140
+ hadc.Init .ScanConvMode = ENABLE;
141
+ hadc.Init .ContinuousConvMode = ENABLE;
142
+ hadc.Init .DiscontinuousConvMode = DISABLE;
143
+ hadc.Init .ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
144
+ hadc.Init .ExternalTrigConv = ADC_SOFTWARE_START; // for now
145
+ hadc.Init .DataAlign = ADC_DATAALIGN_RIGHT;
146
+ hadc.Init .NbrOfConversion = 1 ;
147
+ hadc.Init .DMAContinuousRequests = DISABLE;
148
+ hadc.Init .EOCSelection = ADC_EOC_SINGLE_CONV;
149
+ HAL_ADC_Init (&hadc);
150
+ /* *Configure for the selected ADC regular channel to be converted.
151
+ */
152
+
153
+ /* *Configures for the selected ADC injected channel its corresponding rank in the sequencer and its sample time
154
+ */
155
+ sConfigInjected .InjectedNbrOfConversion = _isset (cs_params->pins [2 ]) ? 3 : 2 ;
156
+ sConfigInjected .InjectedSamplingTime = ADC_SAMPLETIME_2CYCLES_5;
157
+ sConfigInjected .ExternalTrigInjecConvEdge = ADC_EXTERNALTRIGINJECCONV_EDGE_RISING;
158
+ sConfigInjected .AutoInjectedConv = DISABLE;
159
+ sConfigInjected .InjectedDiscontinuousConvMode = DISABLE;
160
+ sConfigInjected .InjectedOffset = 0 ;
161
+
162
+ // automating TRGO flag finding - hardware specific
163
+ uint8_t tim_num = 0 ;
164
+ while (driver_params->timers [tim_num] != NP && tim_num < 6 ){
165
+ uint32_t trigger_flag = _timerToInjectedTRGO (driver_params->timers [tim_num++]);
166
+ if (trigger_flag == _TRGO_NOT_AVAILABLE) continue ; // timer does not have valid trgo for injected channels
167
+
168
+ // if the code comes here, it has found the timer available
169
+ // timer does have trgo flag for injected channels
170
+ sConfigInjected .ExternalTrigInjecConv = trigger_flag;
171
+
172
+ // this will be the timer with which the ADC will sync
173
+ cs_params->timer_handle = driver_params->timers [tim_num-1 ];
174
+ // done
175
+ break ;
176
+ }
177
+ if ( cs_params->timer_handle == NP ){
178
+ // not possible to use these timers for low-side current sense
179
+ #ifdef SIMPLEFOC_STM32_DEBUG
180
+ SIMPLEFOC_DEBUG (" STM32-CS: ERR: cannot sync any timer to injected channels!" );
181
+ #endif
182
+ return -1 ;
183
+ }
184
+ // display which timer is being used
185
+ #ifdef SIMPLEFOC_STM32_DEBUG
186
+ // it would be better to use the getTimerNumber from driver
187
+ SIMPLEFOC_DEBUG (" STM32-CS: injected trigger for timer index: " , get_timer_index (cs_params->timer_handle ->getHandle ()->Instance ) + 1 );
188
+ #endif
189
+
190
+ // first channel
191
+ sConfigInjected .InjectedRank = 1 ;
192
+ sConfigInjected .InjectedChannel = STM_PIN_CHANNEL (pinmap_function (analogInputToPinName (cs_params->pins [0 ]), PinMap_ADC));
193
+ HAL_ADCEx_InjectedConfigChannel (&hadc, &sConfigInjected );
194
+ // second channel
195
+ sConfigInjected .InjectedRank = 2 ;
196
+ sConfigInjected .InjectedChannel = STM_PIN_CHANNEL (pinmap_function (analogInputToPinName (cs_params->pins [1 ]), PinMap_ADC));
197
+ HAL_ADCEx_InjectedConfigChannel (&hadc, &sConfigInjected );
198
+
199
+ // third channel - if exists
200
+ if (_isset (cs_params->pins [2 ])){
201
+ sConfigInjected .InjectedRank = 3 ;
202
+ sConfigInjected .InjectedChannel = STM_PIN_CHANNEL (pinmap_function (analogInputToPinName (cs_params->pins [2 ]), PinMap_ADC));
203
+ HAL_ADCEx_InjectedConfigChannel (&hadc, &sConfigInjected );
204
+ }
205
+
206
+ // enable interrupt
207
+ HAL_NVIC_SetPriority (ADC1_2_IRQn, 0 , 0 );
208
+ HAL_NVIC_EnableIRQ (ADC1_2_IRQn);
209
+
210
+ cs_params->adc_handle = &hadc;
211
+ return 0 ;
212
+ }
213
+
214
+ void _adc_gpio_init (Stm32CurrentSenseParams* cs_params, const int pinA, const int pinB, const int pinC)
215
+ {
216
+ uint8_t cnt = 0 ;
217
+ if (_isset (pinA)){
218
+ pinmap_pinout (analogInputToPinName (pinA), PinMap_ADC);
219
+ cs_params->pins [cnt++] = pinA;
220
+ }
221
+ if (_isset (pinB)){
222
+ pinmap_pinout (analogInputToPinName (pinB), PinMap_ADC);
223
+ cs_params->pins [cnt++] = pinB;
224
+ }
225
+ if (_isset (pinC)){
226
+ pinmap_pinout (analogInputToPinName (pinC), PinMap_ADC);
227
+ cs_params->pins [cnt] = pinC;
228
+ }
229
+ }
230
+
231
+ extern " C" {
232
+ void ADC_IRQHandler (void )
233
+ {
234
+ HAL_ADC_IRQHandler (&hadc);
235
+ }
236
+ }
237
+
238
+ #endif
0 commit comments