From 1d547642e34693cb30ffdbde73738f3149578c16 Mon Sep 17 00:00:00 2001 From: "J. Nick Koston" Date: Sat, 21 Feb 2026 01:11:06 -0600 Subject: [PATCH] Use uint8_t for lookup indices and escape strings in codegen - Change lookup function signatures from uint16_t to uint8_t since indices are stored in uint8_t fields (max 255 per category) - Use cpp_string_escape() for string table entries to prevent compilation errors from special characters in user-provided strings --- esphome/core/entity_base.cpp | 6 +++--- esphome/core/entity_base.h | 6 +++--- esphome/core/entity_helpers.py | 6 +++--- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/esphome/core/entity_base.cpp b/esphome/core/entity_base.cpp index a6c702448e..31e9618640 100644 --- a/esphome/core/entity_base.cpp +++ b/esphome/core/entity_base.cpp @@ -46,9 +46,9 @@ void EntityBase::set_name(const char *name, uint32_t object_id_hash) { } // Weak default lookup functions — overridden by generated code in main.cpp -__attribute__((weak)) const char *entity_device_class_lookup(uint16_t) { return ""; } -__attribute__((weak)) const char *entity_uom_lookup(uint16_t) { return ""; } -__attribute__((weak)) const char *entity_icon_lookup(uint16_t) { return ""; } +__attribute__((weak)) const char *entity_device_class_lookup(uint8_t) { return ""; } +__attribute__((weak)) const char *entity_uom_lookup(uint8_t) { return ""; } +__attribute__((weak)) const char *entity_icon_lookup(uint8_t) { return ""; } // Entity device class (from index) StringRef EntityBase::get_device_class_ref() const { diff --git a/esphome/core/entity_base.h b/esphome/core/entity_base.h index e381db2f1b..e67f16422a 100644 --- a/esphome/core/entity_base.h +++ b/esphome/core/entity_base.h @@ -16,9 +16,9 @@ namespace esphome { // Extern lookup functions for entity string tables. // Generated code provides strong definitions; weak defaults return "". -extern const char *entity_device_class_lookup(uint16_t index); -extern const char *entity_uom_lookup(uint16_t index); -extern const char *entity_icon_lookup(uint16_t index); +extern const char *entity_device_class_lookup(uint8_t index); +extern const char *entity_uom_lookup(uint8_t index); +extern const char *entity_icon_lookup(uint8_t index); // Maximum device name length - keep in sync with validate_hostname() in esphome/core/config.py static constexpr size_t ESPHOME_DEVICE_NAME_MAX_LEN = 31; diff --git a/esphome/core/entity_helpers.py b/esphome/core/entity_helpers.py index c0bb1b1c08..cc435e7c47 100644 --- a/esphome/core/entity_helpers.py +++ b/esphome/core/entity_helpers.py @@ -19,7 +19,7 @@ from esphome.const import ( from esphome.core import CORE, ID, CoroPriority, coroutine_with_priority from esphome.cpp_generator import MockObj, RawStatement, add, get_variable import esphome.final_validate as fv -from esphome.helpers import fnv1_hash_object_id, sanitize, snake_case +from esphome.helpers import cpp_string_escape, fnv1_hash_object_id, sanitize, snake_case from esphome.types import ConfigType, EntityMetadata _LOGGER = logging.getLogger(__name__) @@ -90,12 +90,12 @@ def _generate_category_code( return "" sorted_strings = sorted(strings.items(), key=lambda x: x[1]) - entries = ", ".join(f'"{s}"' for s, _ in sorted_strings) + entries = ", ".join(cpp_string_escape(s) for s, _ in sorted_strings) count = len(sorted_strings) return ( f"static const char *const {table_var}[] PROGMEM = {{{entries}}};\n" - f"const char *{lookup_fn}(uint16_t index) {{\n" + f"const char *{lookup_fn}(uint8_t index) {{\n" f' if (index == 0 || index > {count}) return "";\n' f" return progmem_read_ptr(&{table_var}[index - 1]);\n" f"}}\n"