8000
Skip to content

[kuntze] Use stack buffer for hex formatting in verbose logging - #12775

Merged
bdraco merged 4 commits into
devfrom
kuntze
Jan 3, 2026
Merged

[kuntze] Use stack buffer for hex formatting in verbose logging#12775
bdraco merged 4 commits into
devfrom
kuntze

Conversation

@bdraco
@bdraco bdraco commented Jan 1, 2026
Copy link
Copy Markdown
Member

What does this implement/fix?

Replace heap-allocating format_hex_pretty(...).c_str() with stack-based format_hex_pretty_to() in the kuntze component's verbose logging.

This eliminates a std::string heap allocation in the LOGV path. The buffer is wrapped in a compile guard to avoid stack allocation when verbose logging is disabled.

Buffer size is 24 bytes (format_hex_pretty_size(8)) based on typical Modbus response size (2 registers = 4 bytes data, plus overhead).

Types of changes

  • Bugfix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Developer breaking change (an API change that could break external components)
  • Code quality improvements to existing code or addition of tests
  • Other

Related issue or feature (if applicable):

  • n/a

Pull request in esphome-docs with documentation (if applicable):

  • n/a

Test Environment

  • ESP32
  • ESP32 IDF
  • ESP8266
  • RP2040
  • BK72xx
  • RTL87xx
  • nRF52840

Example entry for config.yaml:

# Standard kuntze configuration - no changes needed
uart:
  tx_pin: GPIO17
  rx_pin: GPIO16
  baud_rate: 19200

modbus:
  uart_id: modbus_uart

sensor:
  - platform: kuntze
    ph:
      name: "pH"

Checklist:

  • The code change is tested and works locally.
  • Tests have been added to verify that the new code works (under tests/ folder).

If user exposed functionality or configuration variables are added/changed:

@github-actions
github-actions Bot commented Jan 1, 2026
Copy link
Copy Markdown
Contributor

To use the changes from this PR as an external component, add the following to your ESPHome configuration YAML file:

external_components:
  - source: github://pr#12775
    components: [kuntze]
    refresh: 1h

(Added by the PR bot)

@codecov-commenter
codecov-commenter commented Jan 1, 2026
Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 73.31%. Comparing base (4e8c02b) to head (0393c31).

Additional details and impacted files
@@            Coverage Diff             @@
##              dev   #12775      +/-   ##
==========================================
- Coverage   73.34%   73.31%   -0.03%     
==========================================
  Files          53       53              
  Lines       11284    11284              
  Branches     1531     1531              
==========================================
- Hits         8276     8273       -3     
- Misses       2608     2610       +2     
- Partials      400      401       +1     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@github-actions
github-actions Bot commented Jan 1, 2026
Copy link
Copy Markdown
Contributor

Memory Impact Analysis

Components: kuntze
Platform: esp8266-ard

Metric Target Branch This PR Change
RAM 29,488 bytes 29,216 bytes 📉 ✅ -272 bytes (-0.92%)
Flash 285,995 bytes 284,035 bytes 📉 ✅ -1,960 bytes (-0.69%)
📊 Component Memory Breakdown
Component Target Flash PR Flash Change
cpp_runtime 1,705 bytes 383 bytes 📉 -1,322 bytes (-77.54%)
[esphome]core 8,871 bytes 8,591 bytes 📉 🎉 -280 bytes (-3.16%)
cpp_stdlib 266 bytes 65 bytes 📉 -201 bytes (-75.56%)
[esphome]kuntze 1,005 bytes 997 bytes 📉 ✅ -8 bytes (-0.80%)
🔍 Symbol-Level Changes (click to expand)

Changed Symbols

Symbol Target Size PR Size Change
esphome::kuntze::Kuntze::on_modbus_data(std::vector<unsigned char, std::allocator ...esphome::kuntze::Kuntze::on_modbus_data(std::vector<unsigned char, std::allocator > const&)
443 bytes 435 bytes 📉 -8 bytes (-1.81%)

Removed Symbols (top 15)

Symbol Size
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_replace(unsig...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_replace(unsigned int, unsigned int, char const*, unsigned int)
280 bytes
std::__cxx11::to_string(unsigned int) 279 bytes
esphome::format_hex_pretty_uint8(unsigned char const*, unsigned int, char, bool) 237 bytes
std::__detail::__to_chars_10_impl<unsigned int>(char*, unsigned int, unsigned int)::__digits 201 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_mutate(unsign...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_mutate(unsigned int, unsigned int, char const*, unsigned int)
139 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::resize(unsigned ...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::resize(unsigned int)
117 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::basic_string(std...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::basic_string(std::__cxx11::basic_string<char, std::char_traits, std::allocator > const&)
98 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator > std::operator+<ch...std::__cxx11::basic_string<char, std::char_traits, std::allocator > std::operator+<char, std::char_traits, std::allocator >(std::__cxx11::basic_string<char, std::char_traits, std::allocator >&&, std::__cxx11::basic_string<char, std::char_traits, std::allocator >&&)
87 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_append(char c...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_M_append(char const*, unsigned int)
84 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::basic_string(std...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::basic_string(std::__cxx11::basic_string<char, std::char_traits, std::allocator >&&)
72 bytes
std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >::append(char const*) 57 bytes
esphome::format_hex_pretty[abi:cxx11](std::vector<unsigned char, std::allocator > ...esphome::format_hex_pretty[abi:cxx11](std::vector<unsigned char, std::allocator > const&, char, bool)
43 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_S_assign(char*,...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_S_assign(char*, unsigned int, char)
26 bytes
std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_S_move(char*, c...std::__cxx11::basic_string<char, std::char_traits, std::allocator >::_S_move(char*, char const*, unsigned int)
22 bytes

Note: This analysis measures static RAM and Flash usage only (compile-time allocation).
Dynamic memory (heap) cannot be measured automatically.
⚠️ You must test this PR on a real device to measure free heap and ensure no runtime memory issues.

This analysis runs automatically when components change. Memory usage is measured from a representative test configuration.

Comment thread esphome/components/kuntze/kuntze.cpp Outdated
@bdraco
bdraco marked this pull request as ready for review January 1, 2026 02:20
@bdraco
bdraco requested a review from ssieb as a code owner January 1, 2026 02:20
Copilot AI review requested due to automatic review settings January 1, 2026 02:20
@github-actions
github-actions Bot commented Jan 1, 2026
Copy link
Copy Markdown
Contributor

👋 Hi there! I've automatically requested reviews from codeowners based on the files changed in this PR.

@ssieb - You've been requested to review this PR as codeowner(s) of 1 file(s) that were modified. Thanks for your time! 🙏

Comment thread esphome/components/kuntze/kuntze.cpp Outdated
Copilot AI left a comment
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR optimizes the kuntze component's verbose logging by replacing heap-allocating format_hex_pretty(...).c_str() with stack-based format_hex_pretty_to(). This eliminates a std::string heap allocation in the logging path.

Key Changes:

  • Added include for esphome/core/helpers.h to access the stack-based formatting function
  • Introduced KUNTZE_MAX_LOG_BYTES constant (8 bytes) and allocated a 24-byte stack buffer for hex formatting
  • Replaced format_hex_pretty(data).c_str() with format_hex_pretty_to(hex_buf, data.data(), data.size())

Comment thread esphome/components/kuntze/kuntze.cpp
Comment thread esphome/components/kuntze/kuntze.cpp
@bdraco
bdraco commented Jan 3, 2026
Copy link
Copy Markdown
Member Author

Thanks

@bdraco
bdraco merged commit a57011b into dev Jan 3, 2026
24 checks passed
@bdraco
bdraco deleted the kuntze branch January 3, 2026 02:36
@github-actions github-actions Bot locked and limited conversation to collaborators Jan 5, 2026
B5C8
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

0