- hal.cpp: include esphome/core/helpers.h for the HOT macro (millis/delay
use it; without the include the TU fails to compile).
- hal_esp8266.h: drop the redundant arch_get_cpu_cycle_count() bare
declaration that came back via the merge from dev (the inline def
above already declares the function).
Followup #16111 dropped the cross-platform arch_get_cpu_cycle_count()
declaration from hal.h dispatcher and added bare decls to libretiny,
rp2040, host, and zephyr per-platform headers — but missed
hal_esp8266.h. ESP8266 callers (spi.h, uart_component_esp8266.cpp) now
fail clang-tidy with 'use of undeclared identifier'.
The body is still out-of-line in components/esp8266/core.cpp on this
PR; the inline def is added on the chained #16112 PR. Add a bare decl
here for now so #16111 builds in isolation.
crash_handler.h is itself guarded by #ifdef USE_ESP32_CRASH_HANDLER, so when
hal.cpp included it before defines.h, the namespace block was empty at parse
time and arch_init()'s USE_ESP32_CRASH_HANDLER branch failed with:
error: 'crash_handler_read_and_clear' is not a member of 'esphome::esp32'
Pull defines.h first so USE_ESP32_CRASH_HANDLER is defined before
crash_handler.h is parsed.
clang-tidy flagged the forward decl in hal_esp8266.h because <user_interface.h>
also declares the function (when included via SDK headers). Both decls are
identical `extern "C"` so the redundancy is harmless; suppress the warning
on the hal_esp8266.h side.
Both bodies are one-liners:
arch_get_cpu_cycle_count() -> esp_get_cycle_count()
arch_get_cpu_freq_hz() -> F_CPU
Move them inline in core/hal/hal_esp8266.h:
- esp_get_cycle_count() comes from <core_esp8266_features.h> (now
pulled into hal_esp8266.h, small ESP8266-only header).
- F_CPU is a -DF_CPU=80000000L compiler flag from the ESP8266 Arduino
board defs, available without any include.
Drop the cross-platform arch_get_cpu_freq_hz() declaration from the
dispatcher hal.h and add bare decls to hal_esp32.h / hal_libretiny.h /
hal_rp2040.h / hal_host.h / hal_zephyr.h so subsequent per-platform
follow-ups only touch their own platform header.
Per-platform follow-up to #15977, chained on top of #16111.
Move out-of-line HAL bodies (millis() fast accumulator, delay() poll,
arch_restart, arch_get_cpu_cycle_count, arch_get_cpu_freq_hz, plus the
__wrap_millis linker trampoline) from components/esp8266/core.cpp into
a new components/esp8266/hal.cpp. core.cpp keeps only the ESP8266
firmware bootstrap (Tasmota OTA magic bytes, optional GPIO pre-init
via resetPins) — single-purpose files.
arch_init() is empty on ESP8266 so it is now inlined directly in
core/hal/hal_esp8266.h alongside the other already-inlined wrappers
(yield, micros, millis_64, delayMicroseconds, arch_feed_wdt,
progmem_read_*).
The dispatcher hal.h drops the cross-platform arch_init() declaration
since at least one platform (ESP8266) inlines it now; bare declarations
are added to the other per-platform headers (hal_esp32.h, hal_libretiny.h,
hal_rp2040.h, hal_host.h, hal_zephyr.h) so future per-platform PRs only
touch their own file.
The previous commit placed the out-of-line ESP32 HAL bodies under
core/hal/hal_esp32.cpp and gated compilation via FILTER_SOURCE_FILES,
mirroring the wake/wake_<platform>.cpp pattern. Switch to the simpler
components/esp32/hal.cpp location instead:
- A component-internal .cpp only compiles when USE_<PLATFORM> is set,
so no FILTER_SOURCE_FILES entry is needed (revert that addition).
- The file can include the component's private crash_handler.h header
directly without a layering inversion or forward decl, so arch_init()
also moves into hal.cpp now (previously stuck in core.cpp because of
that header dependency).
- A future consolidation PR will move the existing core/wake/wake_*.cpp
files into components/<platform>/wake.cpp the same way and drop their
FILTER_SOURCE_FILES entries.
ci-custom's lint_namespace check is satisfied with an empty
namespace esphome::esp32 {} block at the top of the file — the HAL
functions themselves live in namespace esphome (root) since they are
not part of the esp32 component's API.
Per-platform follow-up to #15977.
Move out-of-line HAL bodies (millis(), arch_restart(), arch_get_cpu_freq_hz())
from components/esp32/core.cpp into a new esphome/core/hal/hal_esp32.cpp so
HAL implementation finally lives next to the HAL header.
Inline the trivial one-liners directly in hal_esp32.h:
delayMicroseconds(us) -> delay_microseconds_safe(us)
arch_feed_wdt() -> esp_task_wdt_reset()
arch_get_cpu_cycle_count() -> esp_cpu_get_cycle_count()
arch_init() stays in components/esp32/core.cpp because it uses
esp32::crash_handler_read_and_clear() from the component-private
crash_handler.h header — moving it would require an awkward layering
inversion of core/ -> components/esp32/.
config.py FILTER_SOURCE_FILES gains a hal/hal_esp32.cpp entry so only
ESP32 builds compile it (same pattern wake/wake_*.cpp uses).
Cross-platform decls of delayMicroseconds(), arch_feed_wdt(), and
arch_get_cpu_cycle_count() are dropped from the dispatcher hal.h and
moved into each per-platform header — that way subsequent per-platform
follow-up PRs (libretiny, rp2040, host, zephyr) only need to touch
their own platform header instead of accumulating gates in hal.h.
These wrappers were one-line forwarders to platform primitives:
delayMicroseconds(us) -> delay_microseconds_safe(us)
arch_feed_wdt() -> system_soft_wdt_feed()
progmem_read_byte(p) -> pgm_read_byte(p)
progmem_read_ptr(p) -> pgm_read_ptr(p) cast
progmem_read_uint16(p) -> pgm_read_word(p)
Mark them __attribute__((always_inline)) inline in hal_esp8266.h so the
wrapper call/return is eliminated at every call site, and remove the
out-of-line definitions from components/esp8266/core.cpp.
The IRAM_ATTR previously on delayMicroseconds() was decorative — its
body calls delay_microseconds_safe() which lives in flash, so an IRAM
ISR caller already jumped from SRAM into flash. Inlining is no worse
than the prior code (same reasoning as the libretiny IRAM_ATTR note in
the parent commit's PR description).
The dispatcher hal.h now gates its delayMicroseconds/arch_feed_wdt
declarations behind #ifndef USE_ESP8266 so clang-tidy does not flag
them as redundant on top of the inline definitions.
Mirror the wake.{h,cpp} → wake/wake_<platform>.{h,cpp} decomposition
that PR #15978 did. After this change esphome/core/hal.h is a thin
dispatcher and each platform's HAL bits (IRAM_ATTR / PROGMEM macros,
in_isr_context(), the inline yield/delay/micros/millis/millis_64
wrappers, plus ESP8266's progmem_read_*) live in their own header
under esphome/core/hal/.
Scope is headers only — there is no esphome/core/hal.cpp today (every
out-of-line implementation lives in esphome/components/<platform>/core.cpp
alongside platform-specific concerns) so no new .cpp files are added
and no FILTER_SOURCE_FILES entries are needed in core/config.py.
recursive_sources=True on the core manifest already picks up the new
.h files automatically.
No public API moves, no symbol renames, no behavior change. Pure code
motion. The only observable difference is the dispatcher #errors when
no USE_* is set (today an unknown platform silently fell through to
the else branch with empty IRAM_ATTR/PROGMEM); this matches wake.h's
behavior.