@@ -46,42 +46,58 @@ float common_hal_mcu_processor_get_voltage(void) {
46
46
}
47
47
48
48
uint32_t common_hal_mcu_processor_get_frequency (void ) {
49
+ #if CIRCUITPY_SETTABLE_PROCESSOR_FREQUENCY
49
50
esp_pm_config_t pm ;
50
51
CHECK_ESP_RESULT (esp_pm_get_configuration (& pm ));
51
52
return pm .min_freq_mhz * 1000000 ;
53
+ #else
54
+ return CONFIG_ESP_DEFAULT_CPU_FREQ_MHZ * 1000000 ;
55
+ #endif
52
56
}
53
57
54
- #if defined(CIRCUITPY_SETTABLE_PROCESSOR_FREQUENCY ) // Don't need a NotImplementedError here if this is false, as that is handled in shared-bindings
55
- static void validate_cpu_frequency (uint32_t freq_mhz ) {
58
+ #if CIRCUITPY_SETTABLE_PROCESSOR_FREQUENCY // Don't need a NotImplementedError here if this is false, as that is handled in shared-bindings
59
+ // If the requested frequency is not supported by the hardware, return the next lower supported frequency
60
+ static uint32_t get_valid_cpu_frequency (uint32_t requested_freq_mhz ) {
61
+
56
62
#if defined(CONFIG_IDF_TARGET_ESP32C3 ) || defined(CONFIG_IDF_TARGET_ESP32C6 )
57
- if (freq_mhz != 20 && freq_mhz != 40 && freq_mhz != 80 && freq_mhz != 160 ) {
58
- mp_raise_ValueError (MP_ERROR_TEXT ("Frequency must be 20, 40, 80 or 160MHz" ));
59
- }
63
+ uint32_t valid_cpu_frequencies [] = {20 , 40 , 80 , 160 };
60
64
#elif defined(CONFIG_IDF_TARGET_ESP32C2 )
61
- if (freq_mhz != 20 && freq_mhz != 40 && freq_mhz != 80 && freq_mhz != 120 ) {
62
- mp_raise_ValueError (MP_ERROR_TEXT ("Frequency must be 20, 40, 80 or 120MHz" ));
63
- }
65
+ uint32_t valid_cpu_frequencies [] = {20 , 40 , 80 , 120 };
64
66
#elif defined(CONFIG_IDF_TARGET_ESP32H2 )
65
- if (freq_mhz != 32 && freq_mhz != 48 && freq_mhz != 64 && freq_mhz != 96 ) {
66
- mp_raise_ValueError (MP_ERROR_TEXT ("Frequency must be 32, 48, 64 or 96MHz" ));
67
- }
67
+ uint32_t valid_cpu_frequencies [] = {32 , 48 , 64 , 96 };
68
68
#else
69
- if (freq_mhz != 20 && freq_mhz != 40 && freq_mhz != 80 && freq_mhz != 160 && freq_mhz != 240 ) {
70
- mp_raise_ValueError (MP_ERROR_TEXT ("Frequency must be 20, 40, 80, 160 or 240MHz" ));
71
- }
69
+ uint32_t valid_cpu_frequencies [] = {20 , 40 , 80 , 160 , 240 };
72
70
#endif
71
+
72
+ if (requested_freq_mhz < valid_cpu_frequencies [0 ]) {
73
+ // Don't round to the lowest valid frequency automatically here because the lowest valid frequency
74
+ // can break UART/USB connection on some boards and it's very easy to trigger this case accidentally
75
+ // (e.g. accidentally setting the frequency to 16000000 instead of 160000000,
76
+ // or setting the frequency to 160 instead of 160000000). So trigger an exception instead.
77
+ mp_raise_ValueError_varg (MP_ERROR_TEXT ("Invalid %q" ), MP_QSTR_frequency );
78
+ }
79
+
80
+ const size_t num_valid_frequencies = MP_ARRAY_SIZE (valid_cpu_frequencies );
81
+
82
+ for (size_t i = 1 ; i < num_valid_frequencies ; i ++ ) {
83
+ if (requested_freq_mhz < valid_cpu_frequencies [i ]) {
84
+ return valid_cpu_frequencies [i - 1 ];
85
+ }
86
+ }
87
+
88
+ return valid_cpu_frequencies [num_valid_frequencies - 1 ];
73
89
}
74
90
75
91
void common_hal_mcu_processor_set_frequency (mcu_processor_obj_t * self , uint32_t frequency ) {
76
- // Without this check, everything would compile without error , but silently fail at runtime if
92
+ // Without this check, everything would compile without errors , but silently fail at runtime if
77
93
// CONFIG_PM_ENABLE is ever accidentally disabled
78
94
#if !defined(CONFIG_PM_ENABLE )
79
95
#error "common_hal_mcu_processor_set_frequency needs CONFIG_PM_ENABLE to be defined."
80
96
#endif
81
97
82
98
frequency /= 1000000 ;
83
99
84
- validate_cpu_frequency (frequency );
100
+ frequency = get_valid_cpu_frequency (frequency );
85
101
86
102
esp_pm_config_t pm ;
87
103
pm .max_freq_mhz = frequency ;
0 commit comments