samples: boards: stm32 mco output control
This sample enables and configures the MCO1/2 output for stm32 target boards. MCO_PRE_DIV_n is defined by the stm32XX_clock.h Signed-off-by: Francois Ramu <francois.ramu@st.com>
This commit is contained in:
parent
a103d63b8f
commit
17fcb33eae
7 changed files with 86 additions and 24 deletions
|
@ -16,6 +16,13 @@ Requirements
|
|||
The SoC should support MCO functionality and use a pin that has the MCO alternate function.
|
||||
To support another board, add a dts overlay file in boards folder.
|
||||
Make sure that the output clock is enabled in dts overlay file.
|
||||
Depending on the stm32 serie, several clock source and prescaler are possible for each MCOx.
|
||||
The clock source is set by the DTS among the possible values for each stm32 serie.
|
||||
The prescaler is set by the DTS, through the property ``prescaler = <MCOx_PRE(MCO_PRE_DIV_n)>;``
|
||||
|
||||
See :zephyr_file:`dts/bindings/clock/st,stm32-clock-mco.yaml`
|
||||
|
||||
It is required to check the Reference Manual to configure the DTS correctly.
|
||||
|
||||
|
||||
Building and Running
|
||||
|
|
30
samples/boards/st/mco/boards/nucleo_f411re.overlay
Normal file
30
samples/boards/st/mco/boards/nucleo_f411re.overlay
Normal file
|
@ -0,0 +1,30 @@
|
|||
/* Enable the PLLI2s and set it as clock source for the MCO2 (with prescaler 5) */
|
||||
|
||||
&plli2s {
|
||||
div-m = <8>;
|
||||
mul-n = <100>;
|
||||
div-r = <2>;
|
||||
clocks = <&clk_hse>;
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
/* see RefMan RM0383 */
|
||||
&mco1 {
|
||||
/* Select One of the line below for clock source */
|
||||
clocks = <&rcc STM32_SRC_HSI MCO1_SEL(0)>;
|
||||
/* clocks = <&rcc STM32_SRC_LSE MCO1_SEL(1)>; */
|
||||
/* clocks = <&rcc STM32_SRC_HSE MCO1_SEL(2)>; */
|
||||
/* clocks = <&rcc STM32_SRC_PLL_P MCO1_SEL(3)>; */
|
||||
prescaler = <MCO1_PRE(MCO_PRE_DIV_2)>;
|
||||
pinctrl-0 = <&rcc_mco_1_pa8>;
|
||||
pinctrl-names = "default";
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&mco2 {
|
||||
clocks = <&rcc STM32_SRC_PLLI2S_R MCO2_SEL(1)>;
|
||||
prescaler = <MCO2_PRE(MCO_PRE_DIV_5)>;
|
||||
pinctrl-0 = <&rcc_mco_2_pc9>;
|
||||
pinctrl-names = "default";
|
||||
status = "okay";
|
||||
};
|
30
samples/boards/st/mco/boards/nucleo_f446ze.overlay
Normal file
30
samples/boards/st/mco/boards/nucleo_f446ze.overlay
Normal file
|
@ -0,0 +1,30 @@
|
|||
/* Enable the PLLI2s and set it as clock source for the MCO2 (with prescaler 2) : 25MHz */
|
||||
|
||||
&plli2s {
|
||||
div-m = <8>;
|
||||
mul-n = <100>;
|
||||
div-r = <2>;
|
||||
clocks = <&clk_hse>;
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
/* see RefMan RM0390 */
|
||||
&mco1 {
|
||||
/* Select One of the line below for clock source */
|
||||
/* clocks = <&rcc STM32_SRC_HSI MCO1_SEL(0)>; */
|
||||
/* clocks = <&rcc STM32_SRC_LSE MCO1_SEL(1)>; */
|
||||
clocks = <&rcc STM32_SRC_HSE MCO1_SEL(2)>;
|
||||
/* clocks = <&rcc STM32_SRC_PLL_P MCO1_SEL(3)>;*/
|
||||
prescaler = <MCO1_PRE(MCO_PRE_DIV_1)>;
|
||||
pinctrl-0 = <&rcc_mco_1_pa8>;
|
||||
pinctrl-names = "default";
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&mco2 {
|
||||
clocks = <&rcc STM32_SRC_PLLI2S_R MCO2_SEL(1)>;
|
||||
prescaler = <MCO2_PRE(MCO_PRE_DIV_2)>;
|
||||
pinctrl-0 = <&rcc_mco_2_pc9>;
|
||||
pinctrl-names = "default";
|
||||
status = "okay";
|
||||
};
|
|
@ -8,15 +8,10 @@
|
|||
*/
|
||||
#define MCO1_SEL_LSE 7
|
||||
|
||||
/* See reference manual (RM0456):
|
||||
* 0b001: MCO divided by 2
|
||||
*/
|
||||
#define MCO1_PRE_DIV_2 1
|
||||
|
||||
&mco1 {
|
||||
status = "okay";
|
||||
clocks = <&rcc STM32_SRC_LSE MCO1_SEL(MCO1_SEL_LSE)>;
|
||||
prescaler = <MCO1_PRE(MCO1_PRE_DIV_2)>;
|
||||
prescaler = <MCO1_PRE(MCO_PRE_DIV_2)>;
|
||||
pinctrl-0 = <&rcc_mco_pa8>;
|
||||
pinctrl-names = "default";
|
||||
};
|
||||
|
|
|
@ -12,15 +12,10 @@
|
|||
*/
|
||||
#define MCO1_SEL_LSE 1
|
||||
|
||||
/* See reference manual (RM0385):
|
||||
* 0b100: division by 2
|
||||
*/
|
||||
#define MCO1_PRE_DIV_2 4
|
||||
|
||||
&mco1 {
|
||||
status = "okay";
|
||||
clocks = <&rcc STM32_SRC_LSE MCO1_SEL(MCO1_SEL_LSE)>;
|
||||
prescaler = <MCO1_PRE(MCO1_PRE_DIV_2)>;
|
||||
prescaler = <MCO1_PRE(MCO_PRE_DIV_2)>;
|
||||
pinctrl-0 = <&rcc_mco_1_pa8>; /* D10 (CN7) */
|
||||
pinctrl-names = "default";
|
||||
};
|
||||
|
@ -30,15 +25,10 @@
|
|||
*/
|
||||
#define MCO2_SEL_HSE 2
|
||||
|
||||
/* See reference manual (RM0385):
|
||||
* 0b111: division by 5
|
||||
*/
|
||||
#define MCO2_PRE_DIV_5 7
|
||||
|
||||
&mco2 {
|
||||
status = "okay";
|
||||
clocks = <&rcc STM32_SRC_HSE MCO2_SEL(MCO2_SEL_HSE)>;
|
||||
prescaler = <MCO2_PRE(MCO2_PRE_DIV_5)>;
|
||||
prescaler = <MCO2_PRE(MCO_PRE_DIV_5)>;
|
||||
pinctrl-0 = <&rcc_mco_2_pc9>; /* uSD_D1 (CN3 pin 8) */
|
||||
pinctrl-names = "default";
|
||||
};
|
||||
|
|
|
@ -3,6 +3,10 @@ sample:
|
|||
tests:
|
||||
sample.board.stm32.mco:
|
||||
platform_allow:
|
||||
- nucleo_f411re
|
||||
- nucleo_f446ze
|
||||
- stm32f746g_disco
|
||||
- nucleo_u5a5zj_q
|
||||
integration_platforms:
|
||||
- stm32f746g_disco
|
||||
tags: board
|
||||
|
|
|
@ -9,7 +9,6 @@
|
|||
|
||||
int main(void)
|
||||
{
|
||||
const struct device *dev;
|
||||
|
||||
/* This sample demonstrates MCO usage via Device Tree.
|
||||
* MCO configuration is performed in the Device Tree overlay files.
|
||||
|
@ -17,23 +16,30 @@ int main(void)
|
|||
* initialization. This sample checks that all MCOs are ready - if so,
|
||||
* the selected clock should be visible on the chosen GPIO pin.
|
||||
*/
|
||||
dev = DEVICE_DT_GET(DT_NODELABEL(mco1));
|
||||
if (device_is_ready(dev)) {
|
||||
|
||||
#if DT_NODE_HAS_STATUS_OKAY(DT_NODELABEL(mco1))
|
||||
const struct device *dev1;
|
||||
|
||||
dev1 = DEVICE_DT_GET(DT_NODELABEL(mco1));
|
||||
if (device_is_ready(dev1)) {
|
||||
printk("MCO1 device successfully configured\n");
|
||||
} else {
|
||||
printk("MCO1 device not ready\n");
|
||||
return -1;
|
||||
}
|
||||
#endif /* mco1 */
|
||||
|
||||
#if DT_NODE_HAS_STATUS_OKAY(DT_NODELABEL(mco2))
|
||||
dev = DEVICE_DT_GET(DT_NODELABEL(mco2));
|
||||
if (device_is_ready(dev)) {
|
||||
const struct device *dev2;
|
||||
|
||||
dev2 = DEVICE_DT_GET(DT_NODELABEL(mco2));
|
||||
if (device_is_ready(dev2)) {
|
||||
printk("MCO2 device successfully configured\n");
|
||||
} else {
|
||||
printk("MCO2 device not ready\n");
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
#endif /* mco2 */
|
||||
|
||||
printk("\nDisplayed the status of all MCO devices - end of example.\n");
|
||||
return 0;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue