dRonin  adbada4
dRonin firmware
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
pios_sys.c
Go to the documentation of this file.
1 
17 /*
18  * This program is free software; you can redistribute it and/or modify
19  * it under the terms of the GNU General Public License as published by
20  * the Free Software Foundation; either version 3 of the License, or
21  * (at your option) any later version.
22  *
23  * This program is distributed in the hope that it will be useful, but
24  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
25  * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
26  * for more details.
27  *
28  * You should have received a copy of the GNU General Public License along
29  * with this program; if not, see <http://www.gnu.org/licenses/>
30  */
31 
32 /* Project Includes */
33 #include "pios.h"
34 
35 #if defined(PIOS_INCLUDE_SYS)
36 
37 /* Private Function Prototypes */
38 void NVIC_Configuration(void);
39 void SysTick_Handler(void);
40 
41 /* Local Macros */
42 #define MEM8(addr) (*((volatile uint8_t *)(addr)))
43 #define MEM16(addr) (*((volatile uint16_t *)(addr)))
44 #define MEM32(addr) (*((volatile uint32_t *)(addr)))
45 
49 void PIOS_SYS_Init(void)
50 {
51  PWR_PVDLevelConfig(PWR_PVDLevel_7);
52  PWR_PVDCmd(ENABLE);
53 
54  // Wait for VCC to exceed 2.9V
55  while (PWR_GetFlagStatus(PWR_FLAG_PVDO) == SET);
56 
57 #if !defined(PIOS_INCLUDE_CHIBIOS)
58  /* Setup STM32 system (RCC, clock, PLL and Flash configuration) - CMSIS Function */
59  SystemInit();
60  SystemCoreClockUpdate(); /* update SystemCoreClock for use elsewhere */
61 #endif /* !defined(PIOS_INCLUDE_CHIBIOS) */
62 
63  /*
64  * @todo might make sense to fetch the bus clocks and save them somewhere to avoid
65  * having to use the clunky get-all-clocks API everytime we need one.
66  */
67 
68  /* Initialise Basic NVIC */
69  /* do this early to ensure that we take exceptions in the right place */
70  NVIC_Configuration();
71 
72  /* Enable specific rather than generic hard faults */
73  SCB->SHCSR |= SCB_SHCSR_USGFAULTENA_Msk | SCB_SHCSR_BUSFAULTENA_Msk | SCB_SHCSR_MEMFAULTENA_Msk;
74 
75  /* Init the delay system */
77 
78  /*
79  * Turn on all the peripheral clocks.
80  * Micromanaging clocks makes no sense given the power situation in the system, so
81  * light up everything we might reasonably use here and just leave it on.
82  */
83  RCC_AHB1PeriphClockCmd(
84  RCC_AHB1Periph_GPIOA |
85  RCC_AHB1Periph_GPIOB |
86  RCC_AHB1Periph_GPIOC |
87  RCC_AHB1Periph_GPIOD |
88  RCC_AHB1Periph_GPIOE |
89  RCC_AHB1Periph_GPIOF |
90  RCC_AHB1Periph_GPIOG |
91  RCC_AHB1Periph_GPIOH |
92  RCC_AHB1Periph_GPIOI |
93  RCC_AHB1Periph_CRC |
94  RCC_AHB1Periph_FLITF |
95  RCC_AHB1Periph_SRAM1 |
96  RCC_AHB1Periph_SRAM2 |
97  RCC_AHB1Periph_BKPSRAM |
98  RCC_AHB1Periph_DMA1 |
99  RCC_AHB1Periph_DMA2 |
100  //RCC_AHB1Periph_ETH_MAC | No ethernet
101  //RCC_AHB1Periph_ETH_MAC_Tx |
102  //RCC_AHB1Periph_ETH_MAC_Rx |
103  //RCC_AHB1Periph_ETH_MAC_PTP |
104  //RCC_AHB1Periph_OTG_HS | No high-speed USB (requires external PHY)
105  //RCC_AHB1Periph_OTG_HS_ULPI | No ULPI PHY (see above)
106  0, ENABLE);
107  RCC_AHB2PeriphClockCmd(
108  //RCC_AHB2Periph_DCMI | No camera @todo might make sense later for basic vision support?
109  //RCC_AHB2Periph_CRYP | No crypto
110  //RCC_AHB2Periph_HASH | No hash generator
111  //RCC_AHB2Periph_RNG | No random numbers @todo might be good to have later if entropy is desired
112  //RCC_AHB2Periph_OTG_FS |
113  0, ENABLE);
114  RCC_AHB3PeriphClockCmd(
115  //RCC_AHB3Periph_FSMC | No external static memory
116  0, ENABLE);
117  RCC_APB1PeriphClockCmd(
118  RCC_APB1Periph_TIM2 |
119  RCC_APB1Periph_TIM3 |
120  RCC_APB1Periph_TIM4 |
121  RCC_APB1Periph_TIM5 |
122  RCC_APB1Periph_TIM6 |
123  RCC_APB1Periph_TIM7 |
124  RCC_APB1Periph_TIM12 |
125  RCC_APB1Periph_TIM13 |
126  RCC_APB1Periph_TIM14 |
127  RCC_APB1Periph_WWDG |
128  RCC_APB1Periph_SPI2 |
129  RCC_APB1Periph_SPI3 |
130  RCC_APB1Periph_USART2 |
131  RCC_APB1Periph_USART3 |
132  RCC_APB1Periph_UART4 |
133  RCC_APB1Periph_UART5 |
134  RCC_APB1Periph_I2C1 |
135  RCC_APB1Periph_I2C2 |
136  RCC_APB1Periph_I2C3 |
137  RCC_APB1Periph_CAN1 |
138  RCC_APB1Periph_CAN2 |
139  RCC_APB1Periph_PWR |
140  RCC_APB1Periph_DAC |
141  0, ENABLE);
142 
143  RCC_APB2PeriphClockCmd(
144  RCC_APB2Periph_TIM1 |
145  RCC_APB2Periph_TIM8 |
146  RCC_APB2Periph_USART1 |
147  RCC_APB2Periph_USART6 |
148  RCC_APB2Periph_ADC |
149  RCC_APB2Periph_ADC1 |
150  RCC_APB2Periph_ADC2 |
151  RCC_APB2Periph_ADC3 |
152  RCC_APB2Periph_SDIO |
153  RCC_APB2Periph_SPI1 |
154  RCC_APB2Periph_SYSCFG |
155  RCC_APB2Periph_TIM9 |
156  RCC_APB2Periph_TIM10 |
157  RCC_APB2Periph_TIM11 |
158  0, ENABLE);
159 
160  /*
161  * Configure all pins as input / pullup to avoid issues with
162  * uncommitted pins, excepting special-function pins that we need to
163  * remain as-is.
164  */
165  GPIO_InitTypeDef GPIO_InitStructure;
166  GPIO_StructInit(&GPIO_InitStructure);
167  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; // default is un-pulled input
168 
169  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_All;
170 #if (PIOS_USB_ENABLED)
171  GPIO_InitStructure.GPIO_Pin &= ~(GPIO_Pin_11 | GPIO_Pin_12); // leave USB D+/D- alone
172 #endif
173  GPIO_InitStructure.GPIO_Pin &= ~(GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15); // leave JTAG pins alone
174  GPIO_Init(GPIOA, &GPIO_InitStructure);
175 
176  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_All;
177  GPIO_Init(GPIOB, &GPIO_InitStructure);
178  GPIO_Init(GPIOC, &GPIO_InitStructure);
179  GPIO_Init(GPIOD, &GPIO_InitStructure);
180  GPIO_Init(GPIOE, &GPIO_InitStructure);
181  GPIO_Init(GPIOF, &GPIO_InitStructure);
182  GPIO_Init(GPIOG, &GPIO_InitStructure);
183 #if !defined(STM32F446xx)
184  GPIO_Init(GPIOH, &GPIO_InitStructure);
185  GPIO_Init(GPIOI, &GPIO_InitStructure);
186 #endif /* !defined(STM32F446xx) */
187 }
188 
199 int32_t PIOS_SYS_Reset(void)
200 {
201  // disable all interrupts
203 
204  // turn off all board LEDs
205 #ifdef PIOS_INCLUDE_ANNUNC
206 #if defined(PIOS_LED_HEARTBEAT)
208 #endif /* PIOS_LED_HEARTBEAT */
209 #if defined(PIOS_LED_ALARM)
211 #endif /* PIOS_LED_ALARM */
212 #endif
213 
214  /* XXX F10x port resets most (but not all) peripherals ... do we care? */
215 
216  /* Reset STM32 */
217  NVIC_SystemReset();
218 
219  while (1) ;
220 
221  /* We will never reach this point */
222  return -1;
223 }
224 
231 int32_t PIOS_SYS_SerialNumberGetBinary(uint8_t *array)
232 {
233  int i;
234 
235  /* Stored in the so called "electronic signature" */
236  for (i = 0; i < PIOS_SYS_SERIAL_NUM_BINARY_LEN; ++i) {
237  uint8_t b = MEM8(0x1fff7a10 + i);
238 
239  array[i] = b;
240  }
241 
242  /* No error */
243  return 0;
244 }
245 
252 int32_t PIOS_SYS_SerialNumberGet(char *str)
253 {
254  int i;
255 
256  /* Stored in the so called "electronic signature" */
257  for (i = 0; i < PIOS_SYS_SERIAL_NUM_ASCII_LEN; ++i) {
258  uint8_t b = MEM8(0x1fff7a10 + (i / 2));
259  if (!(i & 1))
260  b >>= 4;
261  b &= 0x0f;
262 
263  str[i] = ((b > 9) ? ('A' - 10) : '0') + b;
264  }
265  str[i] = '\0';
266 
267  /* No error */
268  return 0;
269 }
270 
271 static inline size_t unused_mem(uint32_t *top, uint32_t *bot, uint32_t pattern)
272 {
273  uint32_t *p = bot;
274  for (; p < top && *p == pattern; p++);
275  return (p - bot) * sizeof(uint32_t);
276 }
277 
278 #ifdef PIOS_INCLUDE_CHIBIOS
279 
280 #if !defined(CRT0_STACKS_FILL_PATTERN)
281 #define CRT0_STACKS_FILL_PATTERN 0x55555555 /* ChibiOS ResetHandler */
282 #endif
283 /* c.f. linker */
284 extern uint32_t __main_stack_base__;
285 extern uint32_t __main_stack_end__;
286 extern uint32_t __process_stack_base__;
287 extern uint32_t __process_stack_end__;
288 
289 size_t PIOS_SYS_IrqStackUnused(void)
290 {
291  return unused_mem(&__main_stack_end__, &__main_stack_base__,
292  CRT0_STACKS_FILL_PATTERN);
293 }
294 
295 size_t PIOS_SYS_OsStackUnused(void)
296 {
297  return unused_mem(&__process_stack_end__, &__process_stack_base__,
298  CRT0_STACKS_FILL_PATTERN);
299 }
300 
301 #else
302 
303 /* c.f. linker */
304 extern uint32_t _irq_stack_end;
305 extern uint32_t _irq_stack_top;
306 
307 size_t PIOS_SYS_IrqStackUnused(void)
308 {
309  return unused_mem(&_irq_stack_top, &_irq_stack_end, 0xa5a5a5a5);
310 }
311 
312 size_t PIOS_SYS_OsStackUnused(void)
313 {
314  return 0;
315 }
316 
317 #endif /* PIOS_INCLUDE_CHIBIOS */
318 
322 void NVIC_Configuration(void)
323 {
324  /* Set the Vector Table base address as specified in .ld file */
325  extern void *pios_isr_vector_table_base;
326  NVIC_SetVectorTable((uint32_t)&pios_isr_vector_table_base, 0x0);
327 
328  /* 4 bits for Interrupt priorities so no sub priorities */
329  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);
330 
331  /* Configure HCLK clock as SysTick clock source. */
332  SysTick_CLKSourceConfig(SysTick_CLKSource_HCLK);
333 }
334 
335 #ifdef USE_FULL_ASSERT
336 
343 void assert_failed(uint8_t * file, uint32_t line)
344 {
345  /* When serial debugging is implemented, use something like this. */
346  /* printf("Wrong parameters value: file %s on line %d\r\n", file, line); */
347 
348  /* Setup the LEDs to Alternate */
349 #if defined(PIOS_LED_HEARTBEAT)
351 #endif /* PIOS_LED_HEARTBEAT */
352 #if defined(PIOS_LED_ALARM)
354 #endif /* PIOS_LED_ALARM */
355 
356  /* Infinite loop */
357  while (1) {
358 #if defined(PIOS_LED_HEARTBEAT)
360 #endif /* PIOS_LED_HEARTBEAT */
361 #if defined(PIOS_LED_ALARM)
363 #endif /* PIOS_LED_ALARM */
364  for (int i = 0; i < 1000000; i++) ;
365  }
366 }
367 #endif
368 
369 #endif
370 
Main PiOS header to include all the compiled in PiOS options.
void SystemCoreClockUpdate(void)
Update SystemCoreClock variable according to Clock Register Values. The SystemCoreClock variable cont...
Definition: cmsis_system.c:289
#define PIOS_SYS_SERIAL_NUM_BINARY_LEN
Definition: pios_sys.h:36
void PIOS_SYS_Init(void)
int32_t PIOS_DELAY_Init(void)
Definition: pios_delay.c:98
void PIOS_ANNUNC_Off(uint32_t annunc_id)
void SystemInit(void)
Setup the microcontroller system Initialize the Embedded Flash Interface, the PLL and update the Syst...
Definition: cmsis_system.c:213
#define PIOS_LED_ALARM
Definition: pios_board.h:86
#define PIOS_SYS_SERIAL_NUM_ASCII_LEN
Definition: pios_sys.h:37
void PIOS_ANNUNC_On(uint32_t annunc_id)
uint8_t i
Definition: msp_messages.h:97
int32_t PIOS_SYS_Reset(void)
size_t PIOS_SYS_OsStackUnused(void)
int32_t PIOS_IRQ_Disable(void)
Definition: pios_irq.c:40
int32_t PIOS_SYS_SerialNumberGet(char str[PIOS_SYS_SERIAL_NUM_ASCII_LEN+1])
void PIOS_ANNUNC_Toggle(uint32_t annunc_id)
size_t PIOS_SYS_IrqStackUnused(void)
uint8_t p
Definition: msp_messages.h:96
#define PIOS_LED_HEARTBEAT
Definition: pios_board.h:85
int32_t PIOS_SYS_SerialNumberGetBinary(uint8_t array[PIOS_SYS_SERIAL_NUM_BINARY_LEN])