esphome 2025.7.4__py3-none-any.whl → 2025.8.0b1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- esphome/__main__.py +189 -82
- esphome/automation.py +2 -4
- esphome/build_gen/__init__.py +0 -0
- esphome/build_gen/platformio.py +102 -0
- esphome/components/a4988/a4988.cpp +0 -1
- esphome/components/absolute_humidity/absolute_humidity.cpp +0 -2
- esphome/components/absolute_humidity/sensor.py +2 -2
- esphome/components/adc/__init__.py +123 -85
- esphome/components/adc/adc_sensor.h +98 -35
- esphome/components/adc/adc_sensor_common.cpp +10 -4
- esphome/components/adc/adc_sensor_esp32.cpp +291 -123
- esphome/components/adc/adc_sensor_esp8266.cpp +1 -4
- esphome/components/adc/adc_sensor_libretiny.cpp +1 -2
- esphome/components/adc/adc_sensor_rp2040.cpp +1 -2
- esphome/components/adc/adc_sensor_zephyr.cpp +207 -0
- esphome/components/adc/sensor.py +61 -27
- esphome/components/adc128s102/adc128s102.cpp +1 -4
- esphome/components/ade7880/sensor.py +75 -49
- esphome/components/ads1115/ads1115.cpp +0 -1
- esphome/components/ads1118/ads1118.cpp +0 -1
- esphome/components/ags10/ags10.cpp +0 -4
- esphome/components/aht10/aht10.cpp +0 -4
- esphome/components/aic3204/aic3204.cpp +0 -2
- esphome/components/airthings_wave_plus/__init__.py +1 -1
- esphome/components/airthings_wave_plus/airthings_wave_plus.cpp +22 -4
- esphome/components/airthings_wave_plus/airthings_wave_plus.h +10 -1
- esphome/components/airthings_wave_plus/sensor.py +55 -28
- esphome/components/alarm_control_panel/__init__.py +4 -9
- esphome/components/am2315c/am2315c.cpp +0 -2
- esphome/components/am2320/am2320.cpp +0 -1
- esphome/components/animation/__init__.py +14 -11
- esphome/components/apds9306/apds9306.cpp +0 -4
- esphome/components/apds9960/apds9960.cpp +0 -1
- esphome/components/api/__init__.py +29 -4
- esphome/components/api/api_connection.cpp +378 -401
- esphome/components/api/api_connection.h +112 -56
- esphome/components/api/api_frame_helper.cpp +69 -896
- esphome/components/api/api_frame_helper.h +31 -126
- esphome/components/api/api_frame_helper_noise.cpp +583 -0
- esphome/components/api/api_frame_helper_noise.h +68 -0
- esphome/components/api/api_frame_helper_plaintext.cpp +290 -0
- esphome/components/api/api_frame_helper_plaintext.h +53 -0
- esphome/components/api/api_noise_context.h +2 -4
- esphome/components/api/api_pb2.cpp +1601 -1808
- esphome/components/api/api_pb2.h +367 -323
- esphome/components/api/api_pb2_dump.cpp +1137 -3466
- esphome/components/api/api_pb2_includes.h +34 -0
- esphome/components/api/api_pb2_service.cpp +94 -105
- esphome/components/api/api_pb2_service.h +27 -16
- esphome/components/api/api_server.cpp +18 -17
- esphome/components/api/api_server.h +8 -5
- esphome/components/api/client.py +16 -8
- esphome/components/api/custom_api_device.h +68 -14
- esphome/components/api/homeassistant_service.h +24 -19
- esphome/components/api/list_entities.cpp +3 -5
- esphome/components/api/list_entities.h +2 -4
- esphome/components/api/proto.cpp +3 -5
- esphome/components/api/proto.h +239 -274
- esphome/components/api/subscribe_state.cpp +2 -4
- esphome/components/api/subscribe_state.h +2 -4
- esphome/components/api/user_services.cpp +2 -4
- esphome/components/api/user_services.h +8 -8
- esphome/components/as3935/as3935.cpp +0 -2
- esphome/components/as3935_spi/as3935_spi.cpp +0 -2
- esphome/components/as5600/__init__.py +1 -1
- esphome/components/as5600/as5600.cpp +0 -2
- esphome/components/as5600/sensor/__init__.py +0 -1
- esphome/components/as7341/as7341.cpp +0 -1
- esphome/components/async_tcp/__init__.py +1 -1
- esphome/components/at581x/at581x.cpp +1 -1
- esphome/components/atm90e26/atm90e26.cpp +0 -1
- esphome/components/atm90e32/atm90e32.cpp +488 -118
- esphome/components/atm90e32/atm90e32.h +44 -5
- esphome/components/audio/audio.h +2 -2
- esphome/components/axs15231/touchscreen/axs15231_touchscreen.cpp +0 -2
- esphome/components/beken_spi_led_strip/led_strip.cpp +0 -2
- esphome/components/bh1750/bh1750.cpp +0 -1
- esphome/components/binary_sensor/__init__.py +14 -12
- esphome/components/ble_client/__init__.py +4 -7
- esphome/components/bluetooth_proxy/__init__.py +40 -3
- esphome/components/bluetooth_proxy/bluetooth_connection.cpp +387 -82
- esphome/components/bluetooth_proxy/bluetooth_connection.h +16 -5
- esphome/components/bluetooth_proxy/bluetooth_proxy.cpp +102 -311
- esphome/components/bluetooth_proxy/bluetooth_proxy.h +30 -14
- esphome/components/bme280_base/bme280_base.cpp +15 -16
- esphome/components/bme680/bme680.cpp +2 -3
- esphome/components/bme680_bsec/bme680_bsec.cpp +0 -2
- esphome/components/bme68x_bsec2/bme68x_bsec2.cpp +0 -2
- esphome/components/bmi160/bmi160.cpp +0 -1
- esphome/components/bmp085/bmp085.cpp +0 -1
- esphome/components/bmp280_base/bmp280_base.cpp +13 -14
- esphome/components/bmp3xx_base/bmp3xx_base.cpp +0 -1
- esphome/components/bmp581/bmp581.cpp +0 -2
- esphome/components/bp1658cj/bp1658cj.cpp +0 -1
- esphome/components/bp5758d/bp5758d.cpp +0 -1
- esphome/components/button/__init__.py +0 -1
- esphome/components/canbus/__init__.py +2 -3
- esphome/components/canbus/canbus.cpp +0 -1
- esphome/components/cap1188/cap1188.cpp +0 -2
- esphome/components/captive_portal/__init__.py +1 -1
- esphome/components/cd74hc4067/cd74hc4067.cpp +0 -2
- esphome/components/ch422g/ch422g.cpp +0 -1
- esphome/components/chsc6x/chsc6x_touchscreen.cpp +0 -3
- esphome/components/climate/__init__.py +0 -1
- esphome/components/climate/climate_traits.h +24 -0
- esphome/components/cm1106/cm1106.cpp +0 -1
- esphome/components/const/__init__.py +6 -0
- esphome/components/cover/__init__.py +0 -1
- esphome/components/cover/cover.cpp +9 -13
- esphome/components/cs5460a/cs5460a.cpp +0 -2
- esphome/components/cse7761/cse7761.cpp +0 -1
- esphome/components/cst226/touchscreen/cst226_touchscreen.cpp +0 -2
- esphome/components/cst816/touchscreen/cst816_touchscreen.cpp +0 -2
- esphome/components/dac7678/dac7678_output.cpp +0 -2
- esphome/components/dallas_temp/dallas_temp.cpp +0 -1
- esphome/components/datetime/__init__.py +0 -2
- esphome/components/debug/__init__.py +15 -1
- esphome/components/debug/debug_zephyr.cpp +281 -0
- esphome/components/debug/sensor.py +2 -1
- esphome/components/deep_sleep/deep_sleep_component.cpp +0 -1
- esphome/components/deep_sleep/deep_sleep_esp32.cpp +20 -1
- esphome/components/dfrobot_sen0395/__init__.py +1 -2
- esphome/components/dht/dht.cpp +0 -1
- esphome/components/dht12/dht12.cpp +0 -1
- esphome/components/display/__init__.py +16 -3
- esphome/components/display_menu_base/__init__.py +1 -1
- esphome/components/dps310/dps310.cpp +0 -2
- esphome/components/ds1307/ds1307.cpp +0 -1
- esphome/components/ds2484/ds2484.cpp +0 -1
- esphome/components/duty_cycle/duty_cycle_sensor.cpp +0 -1
- esphome/components/ee895/ee895.cpp +0 -1
- esphome/components/ektf2232/touchscreen/ektf2232.cpp +0 -1
- esphome/components/emc2101/emc2101.cpp +0 -2
- esphome/components/ens160_base/ens160_base.cpp +0 -2
- esphome/components/ens210/ens210.cpp +0 -1
- esphome/components/es7210/es7210.cpp +0 -2
- esphome/components/es7243e/es7243e.cpp +0 -2
- esphome/components/es8156/es8156.cpp +0 -2
- esphome/components/es8311/es8311.cpp +0 -2
- esphome/components/es8388/es8388.cpp +0 -2
- esphome/components/esp32/__init__.py +199 -58
- esphome/components/esp32/boards.py +17 -0
- esphome/components/esp32/gpio.cpp +0 -1
- esphome/components/esp32/gpio.py +1 -2
- esphome/components/esp32/gpio_esp32_h2.py +2 -7
- esphome/components/esp32/gpio_esp32_p4.py +2 -7
- esphome/components/esp32/post_build.py.script +112 -61
- esphome/components/esp32_ble/__init__.py +40 -2
- esphome/components/esp32_ble/ble.cpp +12 -8
- esphome/components/esp32_ble/ble.h +18 -18
- esphome/components/esp32_ble/ble_advertising.cpp +5 -5
- esphome/components/esp32_ble/ble_advertising.h +7 -5
- esphome/components/esp32_ble/ble_event.h +2 -4
- esphome/components/esp32_ble/ble_scan_result.h +2 -4
- esphome/components/esp32_ble/ble_uuid.cpp +5 -5
- esphome/components/esp32_ble/ble_uuid.h +6 -5
- esphome/components/esp32_ble_beacon/__init__.py +4 -0
- esphome/components/esp32_ble_client/__init__.py +1 -1
- esphome/components/esp32_ble_client/ble_characteristic.cpp +4 -4
- esphome/components/esp32_ble_client/ble_characteristic.h +6 -4
- esphome/components/esp32_ble_client/ble_client_base.cpp +155 -104
- esphome/components/esp32_ble_client/ble_client_base.h +17 -6
- esphome/components/esp32_ble_client/ble_descriptor.h +6 -4
- esphome/components/esp32_ble_client/ble_service.cpp +4 -4
- esphome/components/esp32_ble_client/ble_service.h +6 -4
- esphome/components/esp32_ble_server/__init__.py +15 -12
- esphome/components/esp32_ble_tracker/__init__.py +79 -11
- esphome/components/esp32_ble_tracker/automation.h +4 -4
- esphome/components/esp32_ble_tracker/esp32_ble_tracker.cpp +264 -261
- esphome/components/esp32_ble_tracker/esp32_ble_tracker.h +103 -37
- esphome/components/esp32_camera/__init__.py +13 -1
- esphome/components/esp32_camera/esp32_camera.cpp +7 -2
- esphome/components/esp32_camera/esp32_camera.h +1 -0
- esphome/components/esp32_dac/esp32_dac.cpp +3 -19
- esphome/components/esp32_dac/esp32_dac.h +4 -8
- esphome/components/esp32_rmt_led_strip/led_strip.cpp +1 -6
- esphome/components/esp32_rmt_led_strip/light.py +1 -1
- esphome/components/esp32_touch/__init__.py +2 -3
- esphome/components/esp32_touch/esp32_touch.h +9 -6
- esphome/components/esp32_touch/esp32_touch_common.cpp +2 -0
- esphome/components/esp32_touch/esp32_touch_v1.cpp +7 -9
- esphome/components/esp32_touch/esp32_touch_v2.cpp +10 -6
- esphome/components/esp8266/__init__.py +3 -1
- esphome/components/esp8266_pwm/esp8266_pwm.cpp +0 -1
- esphome/components/esphome/ota/__init__.py +1 -2
- esphome/components/esphome/ota/ota_esphome.cpp +150 -77
- esphome/components/esphome/ota/ota_esphome.h +8 -1
- esphome/components/espnow/__init__.py +309 -0
- esphome/components/espnow/automation.h +175 -0
- esphome/components/espnow/espnow_component.cpp +468 -0
- esphome/components/espnow/espnow_component.h +183 -0
- esphome/components/espnow/espnow_err.h +19 -0
- esphome/components/espnow/espnow_packet.h +166 -0
- esphome/components/ethernet/__init__.py +7 -1
- esphome/components/ethernet/esp_eth_phy_jl1101.c +5 -0
- esphome/components/ethernet/ethernet_component.cpp +0 -1
- esphome/components/ethernet/ethernet_component.h +4 -0
- esphome/components/ethernet_info/ethernet_info_text_sensor.h +0 -3
- esphome/components/event/__init__.py +0 -1
- esphome/components/factory_reset/__init__.py +92 -0
- esphome/components/factory_reset/factory_reset.cpp +76 -0
- esphome/components/factory_reset/factory_reset.h +43 -0
- esphome/components/fan/__init__.py +0 -1
- esphome/components/fan/fan_traits.h +16 -0
- esphome/components/fastled_base/fastled_light.cpp +0 -1
- esphome/components/fastled_spi/light.py +1 -3
- esphome/components/fingerprint_grow/fingerprint_grow.cpp +0 -2
- esphome/components/font/__init__.py +9 -1
- esphome/components/fs3000/fs3000.cpp +0 -2
- esphome/components/ft5x06/touchscreen/ft5x06_touchscreen.cpp +0 -2
- esphome/components/ft63x6/ft63x6.cpp +0 -1
- esphome/components/gdk101/gdk101.cpp +0 -1
- esphome/components/gl_r01_i2c/gl_r01_i2c.cpp +0 -1
- esphome/components/gl_r01_i2c/sensor.py +1 -1
- esphome/components/gpio/one_wire/gpio_one_wire.cpp +0 -1
- esphome/components/gpio/switch/gpio_switch.cpp +0 -2
- esphome/components/gpio_expander/cached_gpio.h +24 -15
- esphome/components/gps/__init__.py +6 -2
- esphome/components/gps/gps.cpp +50 -49
- esphome/components/gps/gps.h +4 -8
- esphome/components/gps/time/gps_time.cpp +3 -9
- esphome/components/gps/time/gps_time.h +4 -7
- esphome/components/graph/__init__.py +1 -1
- esphome/components/grove_gas_mc_v2/grove_gas_mc_v2.cpp +0 -1
- esphome/components/grove_tb6612fng/grove_tb6612fng.cpp +0 -1
- esphome/components/gt911/touchscreen/gt911_touchscreen.cpp +21 -12
- esphome/components/gt911/touchscreen/gt911_touchscreen.h +26 -2
- esphome/components/haier/climate.py +5 -10
- esphome/components/haier/haier_base.cpp +0 -1
- esphome/components/hbridge/switch/hbridge_switch.cpp +0 -2
- esphome/components/hdc1080/hdc1080.cpp +0 -2
- esphome/components/heatpumpir/climate.py +2 -2
- esphome/components/hlw8012/hlw8012.cpp +0 -1
- esphome/components/hm3301/hm3301.cpp +0 -1
- esphome/components/hmc5883l/hmc5883l.cpp +0 -1
- esphome/components/homeassistant/__init__.py +1 -0
- esphome/components/homeassistant/number/__init__.py +1 -0
- esphome/components/homeassistant/number/homeassistant_number.cpp +11 -7
- esphome/components/homeassistant/switch/__init__.py +1 -0
- esphome/components/homeassistant/switch/homeassistant_switch.cpp +9 -5
- esphome/components/honeywellabp/honeywellabp.cpp +1 -4
- esphome/components/host/__init__.py +2 -0
- esphome/components/hte501/hte501.cpp +0 -1
- esphome/components/http_request/__init__.py +2 -3
- esphome/components/http_request/http_request_idf.cpp +2 -2
- esphome/components/htu21d/htu21d.cpp +0 -2
- esphome/components/htu31d/htu31d.cpp +0 -2
- esphome/components/hx711/hx711.cpp +0 -1
- esphome/components/hydreon_rgxx/hydreon_rgxx.cpp +0 -1
- esphome/components/hydreon_rgxx/sensor.py +4 -5
- esphome/components/i2c/i2c_bus.h +1 -1
- esphome/components/i2c/i2c_bus_arduino.cpp +1 -2
- esphome/components/i2c/i2c_bus_esp_idf.cpp +192 -17
- esphome/components/i2c/i2c_bus_esp_idf.h +11 -1
- esphome/components/i2s_audio/__init__.py +6 -5
- esphome/components/i2s_audio/i2s_audio.cpp +0 -2
- esphome/components/i2s_audio/media_player/i2s_audio_media_player.cpp +1 -4
- esphome/components/i2s_audio/microphone/__init__.py +4 -6
- esphome/components/i2s_audio/microphone/i2s_audio_microphone.cpp +46 -19
- esphome/components/i2s_audio/microphone/i2s_audio_microphone.h +4 -3
- esphome/components/i2s_audio/speaker/i2s_audio_speaker.cpp +273 -269
- esphome/components/i2s_audio/speaker/i2s_audio_speaker.h +19 -34
- esphome/components/ili9xxx/display.py +4 -3
- esphome/components/ili9xxx/ili9xxx_display.cpp +0 -2
- esphome/components/image/__init__.py +123 -92
- esphome/components/improv_serial/__init__.py +7 -8
- esphome/components/ina219/ina219.cpp +0 -1
- esphome/components/ina226/ina226.cpp +0 -2
- esphome/components/ina260/ina260.cpp +0 -2
- esphome/components/ina2xx_base/__init__.py +2 -5
- esphome/components/ina2xx_base/ina2xx_base.cpp +0 -2
- esphome/components/ina3221/ina3221.cpp +0 -1
- esphome/components/internal_temperature/internal_temperature.cpp +0 -2
- esphome/components/interval/interval.h +5 -9
- esphome/components/json/__init__.py +1 -1
- esphome/components/kmeteriso/kmeteriso.cpp +0 -2
- esphome/components/lc709203f/lc709203f.cpp +0 -2
- esphome/components/lcd_gpio/display.py +1 -3
- esphome/components/lcd_gpio/gpio_lcd_display.cpp +0 -1
- esphome/components/lcd_pcf8574/pcf8574_display.cpp +0 -1
- esphome/components/ld2410/__init__.py +4 -6
- esphome/components/ld2410/binary_sensor.py +4 -0
- esphome/components/ld2410/ld2410.cpp +56 -100
- esphome/components/ld2410/ld2410.h +17 -15
- esphome/components/ld2410/sensor.py +24 -10
- esphome/components/ld2412/__init__.py +46 -0
- esphome/components/ld2412/binary_sensor.py +70 -0
- esphome/components/ld2412/button/__init__.py +74 -0
- esphome/components/ld2412/button/factory_reset_button.cpp +9 -0
- esphome/components/ld2412/button/factory_reset_button.h +18 -0
- esphome/components/ld2412/button/query_button.cpp +9 -0
- esphome/components/ld2412/button/query_button.h +18 -0
- esphome/components/ld2412/button/restart_button.cpp +9 -0
- esphome/components/ld2412/button/restart_button.h +18 -0
- esphome/components/ld2412/button/start_dynamic_background_correction_button.cpp +11 -0
- esphome/components/ld2412/button/start_dynamic_background_correction_button.h +18 -0
- esphome/components/ld2412/ld2412.cpp +861 -0
- esphome/components/ld2412/ld2412.h +141 -0
- esphome/components/ld2412/number/__init__.py +126 -0
- esphome/components/ld2412/number/gate_threshold_number.cpp +14 -0
- esphome/components/ld2412/number/gate_threshold_number.h +19 -0
- esphome/components/ld2412/number/light_threshold_number.cpp +12 -0
- esphome/components/ld2412/number/light_threshold_number.h +18 -0
- esphome/components/ld2412/number/max_distance_timeout_number.cpp +12 -0
- esphome/components/ld2412/number/max_distance_timeout_number.h +18 -0
- esphome/components/ld2412/select/__init__.py +82 -0
- esphome/components/ld2412/select/baud_rate_select.cpp +12 -0
- esphome/components/ld2412/select/baud_rate_select.h +18 -0
- esphome/components/ld2412/select/distance_resolution_select.cpp +12 -0
- esphome/components/ld2412/select/distance_resolution_select.h +18 -0
- esphome/components/ld2412/select/light_out_control_select.cpp +12 -0
- esphome/components/ld2412/select/light_out_control_select.h +18 -0
- esphome/components/ld2412/sensor.py +124 -0
- esphome/components/ld2412/switch/__init__.py +45 -0
- esphome/components/ld2412/switch/bluetooth_switch.cpp +12 -0
- esphome/components/ld2412/switch/bluetooth_switch.h +18 -0
- esphome/components/ld2412/switch/engineering_mode_switch.cpp +12 -0
- esphome/components/ld2412/switch/engineering_mode_switch.h +18 -0
- esphome/components/ld2412/text_sensor.py +34 -0
- esphome/components/ld2420/ld2420.cpp +0 -1
- esphome/components/ld2450/__init__.py +3 -4
- esphome/components/ld2450/binary_sensor.py +3 -0
- esphome/components/ld2450/ld2450.cpp +77 -165
- esphome/components/ld2450/ld2450.h +26 -54
- esphome/components/ld2450/sensor.py +120 -6
- esphome/components/ld2450/text_sensor.py +5 -4
- esphome/components/ld24xx/__init__.py +1 -0
- esphome/components/ld24xx/ld24xx.h +65 -0
- esphome/components/ledc/ledc_output.cpp +0 -1
- esphome/components/libretiny/__init__.py +2 -0
- esphome/components/light/__init__.py +0 -1
- esphome/components/light/effects.py +70 -45
- esphome/components/light/light_call.cpp +101 -66
- esphome/components/light/light_color_values.h +16 -11
- esphome/components/light/light_json_schema.cpp +46 -44
- esphome/components/light/light_state.cpp +8 -11
- esphome/components/light/light_traits.h +17 -0
- esphome/components/lightwaverf/lightwaverf.cpp +0 -2
- esphome/components/lilygo_t5_47/touchscreen/lilygo_t5_47_touchscreen.cpp +0 -1
- esphome/components/lock/__init__.py +0 -1
- esphome/components/logger/__init__.py +31 -9
- esphome/components/logger/logger.cpp +12 -7
- esphome/components/logger/logger.h +25 -14
- esphome/components/logger/logger_esp32.cpp +2 -7
- esphome/components/logger/logger_esp8266.cpp +2 -4
- esphome/components/logger/logger_host.cpp +2 -4
- esphome/components/logger/logger_libretiny.cpp +2 -4
- esphome/components/logger/logger_rp2040.cpp +2 -4
- esphome/components/logger/logger_zephyr.cpp +86 -0
- esphome/components/logger/select/logger_level_select.cpp +2 -4
- esphome/components/logger/select/logger_level_select.h +2 -4
- esphome/components/logger/task_log_buffer.cpp +2 -4
- esphome/components/logger/task_log_buffer.h +2 -4
- esphome/components/lps22/sensor.py +5 -5
- esphome/components/ltr390/ltr390.cpp +0 -2
- esphome/components/ltr501/ltr501.cpp +0 -1
- esphome/components/ltr_als_ps/ltr_als_ps.cpp +0 -1
- esphome/components/lvgl/__init__.py +14 -13
- esphome/components/lvgl/automation.py +2 -4
- esphome/components/lvgl/defines.py +0 -2
- esphome/components/lvgl/helpers.py +1 -1
- esphome/components/lvgl/lv_validation.py +7 -4
- esphome/components/lvgl/lvgl_esphome.cpp +2 -3
- esphome/components/lvgl/styles.py +2 -2
- esphome/components/lvgl/types.py +1 -1
- esphome/components/lvgl/widgets/__init__.py +2 -2
- esphome/components/lvgl/widgets/arc.py +14 -11
- esphome/components/lvgl/widgets/buttonmatrix.py +1 -1
- esphome/components/lvgl/widgets/qrcode.py +7 -7
- esphome/components/lvgl/widgets/spinner.py +6 -6
- esphome/components/lvgl/widgets/switch.py +2 -2
- esphome/components/lvgl/widgets/tabview.py +3 -3
- esphome/components/lvgl/widgets/tileview.py +15 -7
- esphome/components/m5stack_8angle/m5stack_8angle.cpp +0 -1
- esphome/components/matrix_keypad/__init__.py +4 -3
- esphome/components/max17043/max17043.cpp +0 -2
- esphome/components/max31855/max31855.cpp +1 -4
- esphome/components/max31856/max31856.cpp +0 -4
- esphome/components/max31865/max31865.cpp +0 -1
- esphome/components/max44009/max44009.cpp +0 -1
- esphome/components/max6675/max6675.cpp +1 -4
- esphome/components/max6956/max6956.cpp +0 -1
- esphome/components/max7219/max7219.cpp +0 -1
- esphome/components/max7219digit/display.py +1 -1
- esphome/components/max7219digit/max7219digit.cpp +0 -1
- esphome/components/max9611/max9611.cpp +0 -1
- esphome/components/mcp23008/__init__.py +1 -1
- esphome/components/mcp23008/mcp23008.cpp +0 -1
- esphome/components/mcp23016/mcp23016.cpp +0 -1
- esphome/components/mcp23017/__init__.py +1 -1
- esphome/components/mcp23017/mcp23017.cpp +0 -1
- esphome/components/mcp23s08/__init__.py +1 -1
- esphome/components/mcp23s08/mcp23s08.cpp +0 -1
- esphome/components/mcp23s17/__init__.py +1 -1
- esphome/components/mcp23s17/mcp23s17.cpp +0 -1
- esphome/components/mcp23x08_base/__init__.py +2 -0
- esphome/components/mcp23x08_base/mcp23x08_base.cpp +9 -7
- esphome/components/mcp23x08_base/mcp23x08_base.h +9 -4
- esphome/components/mcp23x17_base/__init__.py +2 -0
- esphome/components/mcp23x17_base/mcp23x17_base.cpp +20 -7
- esphome/components/mcp23x17_base/mcp23x17_base.h +9 -4
- esphome/components/mcp23xxx_base/__init__.py +11 -5
- esphome/components/mcp23xxx_base/mcp23xxx_base.cpp +15 -12
- esphome/components/mcp23xxx_base/mcp23xxx_base.h +8 -7
- esphome/components/mcp3008/mcp3008.cpp +1 -4
- esphome/components/mcp3204/mcp3204.cpp +1 -4
- esphome/components/mcp4461/mcp4461.cpp +0 -1
- esphome/components/mcp4725/mcp4725.cpp +0 -1
- esphome/components/mcp4728/mcp4728.cpp +0 -1
- esphome/components/mcp9600/mcp9600.cpp +0 -2
- esphome/components/mcp9808/mcp9808.cpp +0 -2
- esphome/components/mdns/__init__.py +3 -0
- esphome/components/mdns/mdns_component.cpp +2 -0
- esphome/components/mdns/mdns_component.h +4 -0
- esphome/components/media_player/__init__.py +40 -0
- esphome/components/media_player/automation.h +16 -0
- esphome/components/media_player/media_player.cpp +13 -0
- esphome/components/media_player/media_player.h +50 -3
- esphome/components/micro_wake_word/micro_wake_word.cpp +0 -3
- esphome/components/mics_4514/mics_4514.cpp +1 -6
- esphome/components/midea/ir_transmitter.h +4 -4
- esphome/components/mipi/__init__.py +416 -0
- esphome/components/mipi_dsi/__init__.py +5 -0
- esphome/components/mipi_dsi/display.py +233 -0
- esphome/components/mipi_dsi/mipi_dsi.cpp +379 -0
- esphome/components/mipi_dsi/mipi_dsi.h +123 -0
- esphome/components/mipi_dsi/models/__init__.py +0 -0
- esphome/components/mipi_dsi/models/guition.py +38 -0
- esphome/components/mipi_dsi/models/m5stack.py +57 -0
- esphome/components/mipi_dsi/models/waveshare.py +105 -0
- esphome/components/mipi_rgb/models/lilygo.py +0 -0
- esphome/components/mipi_spi/__init__.py +0 -9
- esphome/components/mipi_spi/display.py +220 -256
- esphome/components/mipi_spi/mipi_spi.cpp +1 -485
- esphome/components/mipi_spi/mipi_spi.h +556 -108
- esphome/components/mipi_spi/models/__init__.py +0 -65
- esphome/components/mipi_spi/models/adafruit.py +30 -0
- esphome/components/mipi_spi/models/amoled.py +41 -5
- esphome/components/mipi_spi/models/ili.py +5 -5
- esphome/components/mipi_spi/models/jc.py +1 -3
- esphome/components/mipi_spi/models/lilygo.py +1 -1
- esphome/components/mipi_spi/models/waveshare.py +16 -1
- esphome/components/mixer/speaker/__init__.py +4 -5
- esphome/components/mlx90393/sensor.py +7 -5
- esphome/components/mlx90393/sensor_mlx90393.cpp +0 -1
- esphome/components/mlx90614/mlx90614.cpp +0 -1
- esphome/components/mmc5603/mmc5603.cpp +0 -1
- esphome/components/mmc5983/mmc5983.cpp +0 -2
- esphome/components/mpl3115a2/mpl3115a2.cpp +0 -2
- esphome/components/mpr121/__init__.py +7 -6
- esphome/components/mpr121/mpr121.cpp +0 -1
- esphome/components/mpu6050/mpu6050.cpp +0 -1
- esphome/components/mpu6886/mpu6886.cpp +0 -1
- esphome/components/mqtt/__init__.py +1 -2
- esphome/components/mqtt/mqtt_button.cpp +1 -1
- esphome/components/mqtt/mqtt_client.cpp +0 -1
- esphome/components/mqtt/mqtt_component.cpp +8 -14
- esphome/components/mqtt/mqtt_component.h +0 -7
- esphome/components/mqtt/mqtt_sensor.cpp +0 -1
- esphome/components/mqtt/mqtt_sensor.h +0 -1
- esphome/components/mqtt/mqtt_text_sensor.cpp +0 -1
- esphome/components/mqtt/mqtt_text_sensor.h +0 -1
- esphome/components/ms5611/ms5611.cpp +0 -1
- esphome/components/ms8607/ms8607.cpp +0 -1
- esphome/components/msa3xx/msa3xx.cpp +0 -2
- esphome/components/my9231/my9231.cpp +0 -2
- esphome/components/nau7802/nau7802.cpp +0 -1
- esphome/components/neopixelbus/light.py +3 -0
- esphome/components/network/util.cpp +29 -0
- esphome/components/nextion/nextion.cpp +0 -1
- esphome/components/nfc/binary_sensor/{binary_sensor.cpp → nfc_binary_sensor.cpp} +1 -1
- esphome/components/npi19/npi19.cpp +0 -2
- esphome/components/nrf52/__init__.py +223 -0
- esphome/components/nrf52/boards.py +34 -0
- esphome/components/nrf52/const.py +18 -0
- esphome/components/nrf52/gpio.py +79 -0
- esphome/components/number/__init__.py +2 -1
- esphome/components/one_wire/__init__.py +1 -2
- esphome/components/one_wire/one_wire.cpp +0 -2
- esphome/components/one_wire/one_wire.h +0 -2
- esphome/components/opentherm/hub.cpp +0 -1
- esphome/components/opentherm/number/__init__.py +2 -2
- esphome/components/openthread/__init__.py +2 -3
- esphome/components/openthread/openthread.cpp +30 -13
- esphome/components/openthread/openthread.h +3 -0
- esphome/components/openthread/openthread_esp.cpp +3 -1
- esphome/components/opt3001/sensor.py +2 -6
- esphome/components/output/__init__.py +38 -0
- esphome/components/output/automation.h +24 -0
- esphome/components/output/switch/output_switch.cpp +0 -2
- esphome/components/packages/__init__.py +1 -2
- esphome/components/packet_transport/__init__.py +4 -3
- esphome/components/pca6416a/pca6416a.cpp +0 -1
- esphome/components/pca9554/pca9554.cpp +0 -1
- esphome/components/pca9685/pca9685_output.cpp +0 -2
- esphome/components/pcf85063/pcf85063.cpp +0 -1
- esphome/components/pcf8563/pcf8563.cpp +0 -1
- esphome/components/pcf8574/pcf8574.cpp +0 -1
- esphome/components/pi4ioe5v6408/pi4ioe5v6408.cpp +0 -1
- esphome/components/pipsolar/sensor/__init__.py +1 -1
- esphome/components/pm2005/pm2005.cpp +0 -1
- esphome/components/pmsa003i/pmsa003i.cpp +0 -2
- esphome/components/pmwcs3/sensor.py +1 -2
- esphome/components/pn532/pn532.cpp +0 -2
- esphome/components/pn532_spi/pn532_spi.cpp +0 -2
- esphome/components/power_supply/power_supply.cpp +7 -10
- esphome/components/power_supply/power_supply.h +1 -1
- esphome/components/psram/__init__.py +2 -1
- esphome/components/pulse_counter/pulse_counter_sensor.cpp +0 -1
- esphome/components/pulse_counter/sensor.py +9 -6
- esphome/components/pylontech/pylontech.cpp +0 -1
- esphome/components/qmc5883l/qmc5883l.cpp +0 -1
- esphome/components/qmp6988/qmp6988.cpp +0 -2
- esphome/components/qspi_dbi/display.py +2 -3
- esphome/components/qspi_dbi/qspi_dbi.cpp +0 -2
- esphome/components/qwiic_pir/binary_sensor.py +2 -3
- esphome/components/qwiic_pir/qwiic_pir.cpp +0 -2
- esphome/components/rc522/rc522.cpp +9 -31
- esphome/components/rc522_spi/rc522_spi.cpp +0 -1
- esphome/components/remote_base/__init__.py +5 -6
- esphome/components/remote_receiver/remote_receiver_esp32.cpp +0 -1
- esphome/components/remote_receiver/remote_receiver_esp8266.cpp +0 -1
- esphome/components/remote_receiver/remote_receiver_libretiny.cpp +0 -1
- esphome/components/remote_transmitter/__init__.py +26 -0
- esphome/components/remote_transmitter/automation.h +18 -0
- esphome/components/remote_transmitter/remote_transmitter.h +2 -1
- esphome/components/remote_transmitter/remote_transmitter_esp32.cpp +0 -1
- esphome/components/remote_transmitter/remote_transmitter_esp8266.cpp +2 -0
- esphome/components/remote_transmitter/remote_transmitter_libretiny.cpp +2 -0
- esphome/components/resampler/speaker/__init__.py +4 -5
- esphome/components/rf_bridge/__init__.py +4 -8
- esphome/components/rotary_encoder/rotary_encoder.cpp +0 -2
- esphome/components/rp2040/__init__.py +3 -1
- esphome/components/rp2040_pio_led_strip/led_strip.cpp +0 -2
- esphome/components/rp2040_pio_led_strip/light.py +1 -2
- esphome/components/rp2040_pwm/rp2040_pwm.cpp +1 -5
- esphome/components/rpi_dpi_rgb/display.py +13 -15
- esphome/components/rpi_dpi_rgb/rpi_dpi_rgb.cpp +0 -3
- esphome/components/runtime_stats/__init__.py +34 -0
- esphome/components/runtime_stats/runtime_stats.cpp +102 -0
- esphome/components/runtime_stats/runtime_stats.h +132 -0
- esphome/components/scd30/scd30.cpp +0 -2
- esphome/components/scd30/sensor.py +1 -2
- esphome/components/scd4x/scd4x.cpp +0 -1
- esphome/components/scd4x/sensor.py +1 -3
- esphome/components/sdl/display.py +3 -1
- esphome/components/sdl/sdl_esphome.cpp +0 -2
- esphome/components/sdp3x/sdp3x.cpp +0 -2
- esphome/components/seeed_mr24hpc1/seeed_mr24hpc1.cpp +0 -2
- esphome/components/seeed_mr60fda2/seeed_mr60fda2.cpp +0 -3
- esphome/components/select/__init__.py +2 -3
- esphome/components/select/select_traits.cpp +1 -1
- esphome/components/select/select_traits.h +1 -1
- esphome/components/sen0321/sen0321.cpp +0 -1
- esphome/components/sen5x/sen5x.cpp +0 -2
- esphome/components/sensor/__init__.py +36 -4
- esphome/components/sensor/filter.cpp +49 -10
- esphome/components/sensor/filter.h +22 -7
- esphome/components/sensor/sensor.cpp +0 -1
- esphome/components/sensor/sensor.h +0 -9
- esphome/components/sfa30/sfa30.cpp +0 -4
- esphome/components/sgp30/sgp30.cpp +0 -2
- esphome/components/sgp4x/sensor.py +1 -1
- esphome/components/sgp4x/sgp4x.cpp +0 -2
- esphome/components/shelly_dimmer/shelly_dimmer.cpp +0 -2
- esphome/components/sht3xd/sht3xd.cpp +0 -2
- esphome/components/sht4x/sht4x.cpp +0 -2
- esphome/components/shtcx/shtcx.cpp +0 -1
- esphome/components/sim800l/__init__.py +2 -4
- esphome/components/sm16716/sm16716.cpp +0 -1
- esphome/components/sm2135/sm2135.cpp +0 -1
- esphome/components/sm2235/sm2235.cpp +0 -1
- esphome/components/sm2335/sm2335.cpp +0 -1
- esphome/components/sn74hc165/sn74hc165.cpp +0 -1
- esphome/components/sn74hc595/sn74hc595.cpp +0 -1
- esphome/components/sntp/sntp_component.cpp +0 -1
- esphome/components/sound_level/sensor.py +1 -1
- esphome/components/speaker/media_player/__init__.py +21 -33
- esphome/components/speaker/media_player/audio_pipeline.cpp +4 -7
- esphome/components/spi/__init__.py +29 -13
- esphome/components/spi/spi.cpp +0 -2
- esphome/components/spi_device/spi_device.cpp +1 -4
- esphome/components/sprinkler/__init__.py +4 -4
- esphome/components/sps30/sps30.cpp +0 -1
- esphome/components/ssd1306_base/__init__.py +11 -11
- esphome/components/ssd1306_base/ssd1306_base.cpp +1 -1
- esphome/components/ssd1306_i2c/ssd1306_i2c.cpp +0 -1
- esphome/components/ssd1306_spi/ssd1306_spi.cpp +0 -1
- esphome/components/ssd1322_spi/ssd1322_spi.cpp +0 -1
- esphome/components/ssd1325_spi/ssd1325_spi.cpp +0 -1
- esphome/components/ssd1327_i2c/ssd1327_i2c.cpp +0 -1
- esphome/components/ssd1327_spi/ssd1327_spi.cpp +0 -1
- esphome/components/ssd1331_spi/ssd1331_spi.cpp +0 -1
- esphome/components/ssd1351_spi/ssd1351_spi.cpp +0 -1
- esphome/components/st7567_i2c/st7567_i2c.cpp +0 -1
- esphome/components/st7567_spi/st7567_spi.cpp +0 -1
- esphome/components/st7701s/display.py +10 -14
- esphome/components/st7701s/st7701s.cpp +0 -3
- esphome/components/st7735/st7735.cpp +0 -1
- esphome/components/st7789v/st7789v.cpp +0 -1
- esphome/components/st7920/st7920.cpp +0 -1
- esphome/components/status_led/light/status_led_light.cpp +0 -2
- esphome/components/status_led/status_led.cpp +0 -1
- esphome/components/stepper/__init__.py +2 -4
- esphome/components/sts3x/sts3x.cpp +0 -1
- esphome/components/substitutions/__init__.py +10 -16
- esphome/components/substitutions/jinja.py +24 -1
- esphome/components/sun/__init__.py +2 -3
- esphome/components/switch/__init__.py +31 -1
- esphome/components/switch/automation.h +24 -0
- esphome/components/switch/switch.cpp +8 -0
- esphome/components/switch/switch.h +8 -0
- esphome/components/sx126x/sx126x.cpp +0 -2
- esphome/components/sx127x/sx127x.cpp +0 -2
- esphome/components/sx1509/__init__.py +7 -5
- esphome/components/sx1509/output/sx1509_float_output.cpp +1 -1
- esphome/components/sx1509/sx1509.cpp +0 -2
- esphome/components/syslog/esphome_syslog.cpp +1 -1
- esphome/components/tc74/tc74.cpp +0 -1
- esphome/components/tca9548a/tca9548a.cpp +0 -1
- esphome/components/tca9555/tca9555.cpp +0 -1
- esphome/components/tcs34725/tcs34725.cpp +0 -1
- esphome/components/tee501/tee501.cpp +0 -1
- esphome/components/tem3200/tem3200.cpp +0 -2
- esphome/components/template/alarm_control_panel/template_alarm_control_panel.cpp +0 -1
- esphome/components/template/cover/template_cover.cpp +0 -1
- esphome/components/template/select/template_select.cpp +0 -1
- esphome/components/template/text/template_text.cpp +0 -2
- esphome/components/template/valve/template_valve.cpp +0 -1
- esphome/components/text/__init__.py +0 -1
- esphome/components/text/text_traits.h +2 -0
- esphome/components/text_sensor/__init__.py +2 -1
- esphome/components/text_sensor/text_sensor.cpp +0 -2
- esphome/components/text_sensor/text_sensor.h +0 -8
- esphome/components/thermostat/climate.py +4 -4
- esphome/components/time/__init__.py +7 -4
- esphome/components/time/real_time_clock.cpp +16 -3
- esphome/components/tlc59208f/tlc59208f_output.cpp +0 -2
- esphome/components/tlc5947/tlc5947.cpp +0 -2
- esphome/components/tlc5971/tlc5971.cpp +0 -2
- esphome/components/tm1621/tm1621.cpp +0 -2
- esphome/components/tm1637/tm1637.cpp +0 -2
- esphome/components/tm1638/tm1638.cpp +0 -2
- esphome/components/tm1651/__init__.py +45 -48
- esphome/components/tm1651/tm1651.cpp +213 -47
- esphome/components/tm1651/tm1651.h +37 -32
- esphome/components/tmp117/tmp117.cpp +0 -2
- esphome/components/tsl2561/tsl2561.cpp +0 -1
- esphome/components/tsl2591/tsl2591.cpp +0 -1
- esphome/components/tt21100/touchscreen/tt21100.cpp +0 -2
- esphome/components/ttp229_bsf/ttp229_bsf.cpp +0 -1
- esphome/components/ttp229_lsf/ttp229_lsf.cpp +0 -1
- esphome/components/tuya/climate/__init__.py +9 -10
- esphome/components/tuya/number/__init__.py +8 -6
- esphome/components/tx20/tx20.cpp +0 -1
- esphome/components/uart/uart_component_esp32_arduino.cpp +0 -1
- esphome/components/uart/uart_component_esp8266.cpp +0 -1
- esphome/components/uart/uart_component_esp_idf.cpp +0 -2
- esphome/components/uart/uart_component_libretiny.cpp +0 -2
- esphome/components/uart/uart_component_rp2040.cpp +0 -2
- esphome/components/udp/__init__.py +1 -1
- esphome/components/ufire_ec/sensor.py +1 -2
- esphome/components/ufire_ec/ufire_ec.cpp +0 -2
- esphome/components/ufire_ise/sensor.py +1 -2
- esphome/components/ufire_ise/ufire_ise.cpp +0 -2
- esphome/components/ultrasonic/ultrasonic_sensor.cpp +0 -1
- esphome/components/update/__init__.py +0 -1
- esphome/components/uptime/sensor/uptime_seconds_sensor.cpp +0 -1
- esphome/components/uptime/sensor/uptime_seconds_sensor.h +0 -2
- esphome/components/usb_host/usb_host_client.cpp +0 -1
- esphome/components/usb_host/usb_host_component.cpp +0 -1
- esphome/components/valve/__init__.py +0 -1
- esphome/components/veml3235/veml3235.cpp +0 -3
- esphome/components/veml7700/veml7700.cpp +0 -2
- esphome/components/version/version_text_sensor.cpp +0 -1
- esphome/components/version/version_text_sensor.h +0 -1
- esphome/components/vl53l0x/vl53l0x_sensor.cpp +0 -4
- esphome/components/voice_assistant/voice_assistant.cpp +9 -8
- esphome/components/web_server/__init__.py +13 -0
- esphome/components/web_server/web_server.cpp +187 -352
- esphome/components/web_server/web_server.h +61 -1
- esphome/components/web_server_base/__init__.py +1 -1
- esphome/components/web_server_base/web_server_base.cpp +2 -0
- esphome/components/web_server_base/web_server_base.h +6 -0
- esphome/components/web_server_idf/web_server_idf.cpp +10 -8
- esphome/components/web_server_idf/web_server_idf.h +2 -0
- esphome/components/weikai_i2c/weikai_i2c.cpp +1 -2
- esphome/components/weikai_spi/weikai_spi.cpp +1 -1
- esphome/components/wifi/__init__.py +8 -43
- esphome/components/wifi/wifi_component.cpp +100 -36
- esphome/components/wifi/wifi_component.h +5 -1
- esphome/components/wifi/wifi_component_esp32_arduino.cpp +30 -0
- esphome/components/wifi/wifi_component_esp_idf.cpp +30 -0
- esphome/components/wifi_info/wifi_info_text_sensor.h +0 -6
- esphome/components/wifi_signal/wifi_signal_sensor.h +0 -1
- esphome/components/wireguard/wireguard.cpp +0 -2
- esphome/components/x9c/x9c.cpp +0 -2
- esphome/components/xgzp68xx/xgzp68xx.cpp +0 -1
- esphome/components/xl9535/xl9535.cpp +0 -2
- esphome/components/zephyr/__init__.py +252 -0
- esphome/components/zephyr/const.py +16 -0
- esphome/components/zephyr/core.cpp +90 -0
- esphome/components/zephyr/gpio.cpp +120 -0
- esphome/components/zephyr/gpio.h +38 -0
- esphome/components/zephyr/pre_build.py.script +4 -0
- esphome/components/zephyr/preferences.cpp +156 -0
- esphome/components/zephyr/preferences.h +13 -0
- esphome/config.py +38 -16
- esphome/config_helpers.py +1 -2
- esphome/config_validation.py +8 -15
- esphome/const.py +26 -1
- esphome/core/__init__.py +88 -51
- esphome/core/application.cpp +75 -21
- esphome/core/application.h +106 -171
- esphome/core/color.h +10 -0
- esphome/core/component.cpp +41 -25
- esphome/core/component.h +9 -6
- esphome/core/component_iterator.cpp +61 -261
- esphome/core/component_iterator.h +15 -0
- esphome/core/config.py +26 -11
- esphome/core/defines.h +40 -2
- esphome/core/entity_base.h +18 -0
- esphome/core/entity_helpers.py +41 -6
- esphome/core/helpers.cpp +8 -15
- esphome/core/helpers.h +60 -6
- esphome/core/lock_free_queue.h +1 -1
- esphome/core/scheduler.cpp +277 -74
- esphome/core/scheduler.h +89 -27
- esphome/cpp_generator.py +2 -6
- esphome/cpp_helpers.py +1 -1
- esphome/dashboard/dashboard.py +2 -3
- esphome/dashboard/dns.py +2 -8
- esphome/dashboard/web_server.py +34 -19
- esphome/espota2.py +1 -4
- esphome/git.py +3 -1
- esphome/helpers.py +23 -4
- esphome/log.py +3 -1
- esphome/mqtt.py +3 -5
- esphome/platformio_api.py +7 -4
- esphome/types.py +12 -0
- esphome/util.py +20 -8
- esphome/voluptuous_schema.py +4 -3
- esphome/vscode.py +1 -2
- esphome/wizard.py +1 -4
- esphome/writer.py +5 -107
- esphome/yaml_util.py +7 -5
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/METADATA +12 -13
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/RECORD +753 -673
- esphome/components/mipi_spi/models/commands.py +0 -82
- /esphome/components/nfc/binary_sensor/{binary_sensor.h → nfc_binary_sensor.h} +0 -0
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/WHEEL +0 -0
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/entry_points.txt +0 -0
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/licenses/LICENSE +0 -0
- {esphome-2025.7.4.dist-info → esphome-2025.8.0b1.dist-info}/top_level.txt +0 -0
|
@@ -8,16 +8,369 @@
|
|
|
8
8
|
|
|
9
9
|
#include "bluetooth_proxy.h"
|
|
10
10
|
|
|
11
|
-
namespace esphome {
|
|
12
|
-
namespace bluetooth_proxy {
|
|
11
|
+
namespace esphome::bluetooth_proxy {
|
|
13
12
|
|
|
14
13
|
static const char *const TAG = "bluetooth_proxy.connection";
|
|
15
14
|
|
|
15
|
+
// This function is allocation-free and directly packs UUIDs into the output array
|
|
16
|
+
// using precalculated constants for the Bluetooth base UUID
|
|
17
|
+
static void fill_128bit_uuid_array(std::array<uint64_t, 2> &out, esp_bt_uuid_t uuid_source) {
|
|
18
|
+
// Bluetooth base UUID: 00000000-0000-1000-8000-00805F9B34FB
|
|
19
|
+
// out[0] = bytes 8-15 (big-endian)
|
|
20
|
+
// - For 128-bit UUIDs: use bytes 8-15 as-is
|
|
21
|
+
// - For 16/32-bit UUIDs: insert into bytes 12-15, use 0x00001000 for bytes 8-11
|
|
22
|
+
out[0] = uuid_source.len == ESP_UUID_LEN_128
|
|
23
|
+
? (((uint64_t) uuid_source.uuid.uuid128[15] << 56) | ((uint64_t) uuid_source.uuid.uuid128[14] << 48) |
|
|
24
|
+
((uint64_t) uuid_source.uuid.uuid128[13] << 40) | ((uint64_t) uuid_source.uuid.uuid128[12] << 32) |
|
|
25
|
+
((uint64_t) uuid_source.uuid.uuid128[11] << 24) | ((uint64_t) uuid_source.uuid.uuid128[10] << 16) |
|
|
26
|
+
((uint64_t) uuid_source.uuid.uuid128[9] << 8) | ((uint64_t) uuid_source.uuid.uuid128[8]))
|
|
27
|
+
: (((uint64_t) (uuid_source.len == ESP_UUID_LEN_16 ? uuid_source.uuid.uuid16 : uuid_source.uuid.uuid32)
|
|
28
|
+
<< 32) |
|
|
29
|
+
0x00001000ULL); // Base UUID bytes 8-11
|
|
30
|
+
// out[1] = bytes 0-7 (big-endian)
|
|
31
|
+
// - For 128-bit UUIDs: use bytes 0-7 as-is
|
|
32
|
+
// - For 16/32-bit UUIDs: use precalculated base UUID constant
|
|
33
|
+
out[1] = uuid_source.len == ESP_UUID_LEN_128
|
|
34
|
+
? ((uint64_t) uuid_source.uuid.uuid128[7] << 56) | ((uint64_t) uuid_source.uuid.uuid128[6] << 48) |
|
|
35
|
+
((uint64_t) uuid_source.uuid.uuid128[5] << 40) | ((uint64_t) uuid_source.uuid.uuid128[4] << 32) |
|
|
36
|
+
((uint64_t) uuid_source.uuid.uuid128[3] << 24) | ((uint64_t) uuid_source.uuid.uuid128[2] << 16) |
|
|
37
|
+
((uint64_t) uuid_source.uuid.uuid128[1] << 8) | ((uint64_t) uuid_source.uuid.uuid128[0])
|
|
38
|
+
: 0x800000805F9B34FBULL; // Base UUID bytes 0-7: 80-00-00-80-5F-9B-34-FB
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// Helper to fill UUID in the appropriate format based on client support and UUID type
|
|
42
|
+
static void fill_gatt_uuid(std::array<uint64_t, 2> &uuid_128, uint32_t &short_uuid, const esp_bt_uuid_t &uuid,
|
|
43
|
+
bool use_efficient_uuids) {
|
|
44
|
+
if (!use_efficient_uuids || uuid.len == ESP_UUID_LEN_128) {
|
|
45
|
+
// Use 128-bit format for old clients or when UUID is already 128-bit
|
|
46
|
+
fill_128bit_uuid_array(uuid_128, uuid);
|
|
47
|
+
} else if (uuid.len == ESP_UUID_LEN_16) {
|
|
48
|
+
short_uuid = uuid.uuid.uuid16;
|
|
49
|
+
} else if (uuid.len == ESP_UUID_LEN_32) {
|
|
50
|
+
short_uuid = uuid.uuid.uuid32;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
// Constants for size estimation
|
|
55
|
+
static constexpr uint8_t SERVICE_OVERHEAD_LEGACY = 25; // UUID(20) + handle(4) + overhead(1)
|
|
56
|
+
static constexpr uint8_t SERVICE_OVERHEAD_EFFICIENT = 10; // UUID(6) + handle(4)
|
|
57
|
+
static constexpr uint8_t CHAR_SIZE_128BIT = 35; // UUID(20) + handle(4) + props(4) + overhead(7)
|
|
58
|
+
static constexpr uint8_t DESC_SIZE_128BIT = 25; // UUID(20) + handle(4) + overhead(1)
|
|
59
|
+
static constexpr uint8_t DESC_SIZE_16BIT = 10; // UUID(6) + handle(4)
|
|
60
|
+
static constexpr uint8_t DESC_PER_CHAR = 1; // Assume 1 descriptor per characteristic
|
|
61
|
+
|
|
62
|
+
// Helper to estimate service size before fetching all data
|
|
63
|
+
/**
|
|
64
|
+
* Estimate the size of a Bluetooth service based on the number of characteristics and UUID format.
|
|
65
|
+
*
|
|
66
|
+
* @param char_count The number of characteristics in the service.
|
|
67
|
+
* @param use_efficient_uuids Whether to use efficient UUIDs (16-bit or 32-bit) for newer APIVersions.
|
|
68
|
+
* @return The estimated size of the service in bytes.
|
|
69
|
+
*
|
|
70
|
+
* This function calculates the size of a Bluetooth service by considering:
|
|
71
|
+
* - A service overhead, which depends on whether efficient UUIDs are used.
|
|
72
|
+
* - The size of each characteristic, assuming 128-bit UUIDs for safety.
|
|
73
|
+
* - The size of descriptors, assuming one 128-bit descriptor per characteristic.
|
|
74
|
+
*/
|
|
75
|
+
static size_t estimate_service_size(uint16_t char_count, bool use_efficient_uuids) {
|
|
76
|
+
size_t service_overhead = use_efficient_uuids ? SERVICE_OVERHEAD_EFFICIENT : SERVICE_OVERHEAD_LEGACY;
|
|
77
|
+
// Always assume 128-bit UUIDs for characteristics to be safe
|
|
78
|
+
size_t char_size = CHAR_SIZE_128BIT;
|
|
79
|
+
// Assume one 128-bit descriptor per characteristic
|
|
80
|
+
size_t desc_size = DESC_SIZE_128BIT * DESC_PER_CHAR;
|
|
81
|
+
|
|
82
|
+
return service_overhead + (char_size + desc_size) * char_count;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
bool BluetoothConnection::supports_efficient_uuids_() const {
|
|
86
|
+
auto *api_conn = this->proxy_->get_api_connection();
|
|
87
|
+
return api_conn && api_conn->client_supports_api_version(1, 12);
|
|
88
|
+
}
|
|
89
|
+
|
|
16
90
|
void BluetoothConnection::dump_config() {
|
|
17
91
|
ESP_LOGCONFIG(TAG, "BLE Connection:");
|
|
18
92
|
BLEClientBase::dump_config();
|
|
19
93
|
}
|
|
20
94
|
|
|
95
|
+
void BluetoothConnection::update_allocated_slot_(uint64_t find_value, uint64_t set_value) {
|
|
96
|
+
auto &allocated = this->proxy_->connections_free_response_.allocated;
|
|
97
|
+
for (auto &slot : allocated) {
|
|
98
|
+
if (slot == find_value) {
|
|
99
|
+
slot = set_value;
|
|
100
|
+
return;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
void BluetoothConnection::set_address(uint64_t address) {
|
|
106
|
+
// If we're clearing an address (disconnecting), update the pre-allocated message
|
|
107
|
+
if (address == 0 && this->address_ != 0) {
|
|
108
|
+
this->proxy_->connections_free_response_.free++;
|
|
109
|
+
this->update_allocated_slot_(this->address_, 0);
|
|
110
|
+
}
|
|
111
|
+
// If we're setting a new address (connecting), update the pre-allocated message
|
|
112
|
+
else if (address != 0 && this->address_ == 0) {
|
|
113
|
+
this->proxy_->connections_free_response_.free--;
|
|
114
|
+
this->update_allocated_slot_(0, address);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// Call parent implementation to actually set the address
|
|
118
|
+
BLEClientBase::set_address(address);
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
void BluetoothConnection::loop() {
|
|
122
|
+
BLEClientBase::loop();
|
|
123
|
+
|
|
124
|
+
// Early return if no active connection
|
|
125
|
+
if (this->address_ == 0) {
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// Handle service discovery if in valid range
|
|
130
|
+
if (this->send_service_ >= 0 && this->send_service_ <= this->service_count_) {
|
|
131
|
+
this->send_service_for_discovery_();
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
// Check if we should disable the loop
|
|
135
|
+
// - For V3_WITH_CACHE: Services are never sent, disable after INIT state
|
|
136
|
+
// - For other connections: Disable only after service discovery is complete
|
|
137
|
+
// (send_service_ == DONE_SENDING_SERVICES, which is only set after services are sent)
|
|
138
|
+
if (this->state_ != espbt::ClientState::INIT && (this->connection_type_ == espbt::ConnectionType::V3_WITH_CACHE ||
|
|
139
|
+
this->send_service_ == DONE_SENDING_SERVICES)) {
|
|
140
|
+
this->disable_loop();
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
void BluetoothConnection::reset_connection_(esp_err_t reason) {
|
|
145
|
+
// Send disconnection notification
|
|
146
|
+
this->proxy_->send_device_connection(this->address_, false, 0, reason);
|
|
147
|
+
|
|
148
|
+
// Important: If we were in the middle of sending services, we do NOT send
|
|
149
|
+
// send_gatt_services_done() here. This ensures the client knows that
|
|
150
|
+
// the service discovery was interrupted and can retry. The client
|
|
151
|
+
// (aioesphomeapi) implements a 30-second timeout (DEFAULT_BLE_TIMEOUT)
|
|
152
|
+
// to detect incomplete service discovery rather than relying on us to
|
|
153
|
+
// tell them about a partial list.
|
|
154
|
+
this->set_address(0);
|
|
155
|
+
this->send_service_ = INIT_SENDING_SERVICES;
|
|
156
|
+
this->proxy_->send_connections_free();
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
void BluetoothConnection::send_service_for_discovery_() {
|
|
160
|
+
if (this->send_service_ >= this->service_count_) {
|
|
161
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
162
|
+
this->proxy_->send_gatt_services_done(this->address_);
|
|
163
|
+
if (this->connection_type_ == espbt::ConnectionType::V3_WITH_CACHE ||
|
|
164
|
+
this->connection_type_ == espbt::ConnectionType::V3_WITHOUT_CACHE) {
|
|
165
|
+
this->release_services();
|
|
166
|
+
}
|
|
167
|
+
return;
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
// Early return if no API connection
|
|
171
|
+
auto *api_conn = this->proxy_->get_api_connection();
|
|
172
|
+
if (api_conn == nullptr) {
|
|
173
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
174
|
+
return;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
// Check if client supports efficient UUIDs
|
|
178
|
+
bool use_efficient_uuids = this->supports_efficient_uuids_();
|
|
179
|
+
|
|
180
|
+
// Prepare response
|
|
181
|
+
api::BluetoothGATTGetServicesResponse resp;
|
|
182
|
+
resp.address = this->address_;
|
|
183
|
+
|
|
184
|
+
// Dynamic batching based on actual size
|
|
185
|
+
// Conservative MTU limit for API messages (accounts for WPA3 overhead)
|
|
186
|
+
static constexpr size_t MAX_PACKET_SIZE = 1360;
|
|
187
|
+
|
|
188
|
+
// Keep running total of actual message size
|
|
189
|
+
size_t current_size = 0;
|
|
190
|
+
api::ProtoSize size;
|
|
191
|
+
resp.calculate_size(size);
|
|
192
|
+
current_size = size.get_size();
|
|
193
|
+
|
|
194
|
+
while (this->send_service_ < this->service_count_) {
|
|
195
|
+
esp_gattc_service_elem_t service_result;
|
|
196
|
+
uint16_t service_count = 1;
|
|
197
|
+
esp_gatt_status_t service_status = esp_ble_gattc_get_service(this->gattc_if_, this->conn_id_, nullptr,
|
|
198
|
+
&service_result, &service_count, this->send_service_);
|
|
199
|
+
|
|
200
|
+
if (service_status != ESP_GATT_OK || service_count == 0) {
|
|
201
|
+
ESP_LOGE(TAG, "[%d] [%s] esp_ble_gattc_get_service %s, status=%d, service_count=%d, offset=%d",
|
|
202
|
+
this->connection_index_, this->address_str().c_str(),
|
|
203
|
+
service_status != ESP_GATT_OK ? "error" : "missing", service_status, service_count, this->send_service_);
|
|
204
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
205
|
+
return;
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
// Get the number of characteristics BEFORE adding to response
|
|
209
|
+
uint16_t total_char_count = 0;
|
|
210
|
+
esp_gatt_status_t char_count_status =
|
|
211
|
+
esp_ble_gattc_get_attr_count(this->gattc_if_, this->conn_id_, ESP_GATT_DB_CHARACTERISTIC,
|
|
212
|
+
service_result.start_handle, service_result.end_handle, 0, &total_char_count);
|
|
213
|
+
|
|
214
|
+
if (char_count_status != ESP_GATT_OK) {
|
|
215
|
+
this->log_connection_error_("esp_ble_gattc_get_attr_count", char_count_status);
|
|
216
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
217
|
+
return;
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
// If this service likely won't fit, send current batch (unless it's the first)
|
|
221
|
+
size_t estimated_size = estimate_service_size(total_char_count, use_efficient_uuids);
|
|
222
|
+
if (!resp.services.empty() && (current_size + estimated_size > MAX_PACKET_SIZE)) {
|
|
223
|
+
// This service likely won't fit, send current batch
|
|
224
|
+
break;
|
|
225
|
+
}
|
|
226
|
+
|
|
227
|
+
// Now add the service since we know it will likely fit
|
|
228
|
+
resp.services.emplace_back();
|
|
229
|
+
auto &service_resp = resp.services.back();
|
|
230
|
+
|
|
231
|
+
fill_gatt_uuid(service_resp.uuid, service_resp.short_uuid, service_result.uuid, use_efficient_uuids);
|
|
232
|
+
|
|
233
|
+
service_resp.handle = service_result.start_handle;
|
|
234
|
+
|
|
235
|
+
if (total_char_count > 0) {
|
|
236
|
+
// Reserve space and process characteristics
|
|
237
|
+
service_resp.characteristics.reserve(total_char_count);
|
|
238
|
+
uint16_t char_offset = 0;
|
|
239
|
+
esp_gattc_char_elem_t char_result;
|
|
240
|
+
while (true) { // characteristics
|
|
241
|
+
uint16_t char_count = 1;
|
|
242
|
+
esp_gatt_status_t char_status =
|
|
243
|
+
esp_ble_gattc_get_all_char(this->gattc_if_, this->conn_id_, service_result.start_handle,
|
|
244
|
+
service_result.end_handle, &char_result, &char_count, char_offset);
|
|
245
|
+
if (char_status == ESP_GATT_INVALID_OFFSET || char_status == ESP_GATT_NOT_FOUND) {
|
|
246
|
+
break;
|
|
247
|
+
}
|
|
248
|
+
if (char_status != ESP_GATT_OK) {
|
|
249
|
+
this->log_connection_error_("esp_ble_gattc_get_all_char", char_status);
|
|
250
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
251
|
+
return;
|
|
252
|
+
}
|
|
253
|
+
if (char_count == 0) {
|
|
254
|
+
break;
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
service_resp.characteristics.emplace_back();
|
|
258
|
+
auto &characteristic_resp = service_resp.characteristics.back();
|
|
259
|
+
|
|
260
|
+
fill_gatt_uuid(characteristic_resp.uuid, characteristic_resp.short_uuid, char_result.uuid, use_efficient_uuids);
|
|
261
|
+
|
|
262
|
+
characteristic_resp.handle = char_result.char_handle;
|
|
263
|
+
characteristic_resp.properties = char_result.properties;
|
|
264
|
+
char_offset++;
|
|
265
|
+
|
|
266
|
+
// Get the number of descriptors directly with one call
|
|
267
|
+
uint16_t total_desc_count = 0;
|
|
268
|
+
esp_gatt_status_t desc_count_status = esp_ble_gattc_get_attr_count(
|
|
269
|
+
this->gattc_if_, this->conn_id_, ESP_GATT_DB_DESCRIPTOR, 0, 0, char_result.char_handle, &total_desc_count);
|
|
270
|
+
|
|
271
|
+
if (desc_count_status != ESP_GATT_OK) {
|
|
272
|
+
this->log_connection_error_("esp_ble_gattc_get_attr_count", desc_count_status);
|
|
273
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
274
|
+
return;
|
|
275
|
+
}
|
|
276
|
+
if (total_desc_count == 0) {
|
|
277
|
+
// No descriptors, continue to next characteristic
|
|
278
|
+
continue;
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
// Reserve space and process descriptors
|
|
282
|
+
characteristic_resp.descriptors.reserve(total_desc_count);
|
|
283
|
+
uint16_t desc_offset = 0;
|
|
284
|
+
esp_gattc_descr_elem_t desc_result;
|
|
285
|
+
while (true) { // descriptors
|
|
286
|
+
uint16_t desc_count = 1;
|
|
287
|
+
esp_gatt_status_t desc_status = esp_ble_gattc_get_all_descr(
|
|
288
|
+
this->gattc_if_, this->conn_id_, char_result.char_handle, &desc_result, &desc_count, desc_offset);
|
|
289
|
+
if (desc_status == ESP_GATT_INVALID_OFFSET || desc_status == ESP_GATT_NOT_FOUND) {
|
|
290
|
+
break;
|
|
291
|
+
}
|
|
292
|
+
if (desc_status != ESP_GATT_OK) {
|
|
293
|
+
this->log_connection_error_("esp_ble_gattc_get_all_descr", desc_status);
|
|
294
|
+
this->send_service_ = DONE_SENDING_SERVICES;
|
|
295
|
+
return;
|
|
296
|
+
}
|
|
297
|
+
if (desc_count == 0) {
|
|
298
|
+
break; // No more descriptors
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
characteristic_resp.descriptors.emplace_back();
|
|
302
|
+
auto &descriptor_resp = characteristic_resp.descriptors.back();
|
|
303
|
+
|
|
304
|
+
fill_gatt_uuid(descriptor_resp.uuid, descriptor_resp.short_uuid, desc_result.uuid, use_efficient_uuids);
|
|
305
|
+
|
|
306
|
+
descriptor_resp.handle = desc_result.handle;
|
|
307
|
+
desc_offset++;
|
|
308
|
+
}
|
|
309
|
+
}
|
|
310
|
+
} // end if (total_char_count > 0)
|
|
311
|
+
|
|
312
|
+
// Calculate the actual size of just this service
|
|
313
|
+
api::ProtoSize service_sizer;
|
|
314
|
+
service_resp.calculate_size(service_sizer);
|
|
315
|
+
size_t service_size = service_sizer.get_size() + 1; // +1 for field tag
|
|
316
|
+
|
|
317
|
+
// Check if adding this service would exceed the limit
|
|
318
|
+
if (current_size + service_size > MAX_PACKET_SIZE) {
|
|
319
|
+
// We would go over - pop the last service if we have more than one
|
|
320
|
+
if (resp.services.size() > 1) {
|
|
321
|
+
resp.services.pop_back();
|
|
322
|
+
ESP_LOGD(TAG, "[%d] [%s] Service %d would exceed limit (current: %d + service: %d > %d), sending current batch",
|
|
323
|
+
this->connection_index_, this->address_str().c_str(), this->send_service_, current_size, service_size,
|
|
324
|
+
MAX_PACKET_SIZE);
|
|
325
|
+
// Don't increment send_service_ - we'll retry this service in next batch
|
|
326
|
+
} else {
|
|
327
|
+
// This single service is too large, but we have to send it anyway
|
|
328
|
+
ESP_LOGV(TAG, "[%d] [%s] Service %d is too large (%d bytes) but sending anyway", this->connection_index_,
|
|
329
|
+
this->address_str().c_str(), this->send_service_, service_size);
|
|
330
|
+
// Increment so we don't get stuck
|
|
331
|
+
this->send_service_++;
|
|
332
|
+
}
|
|
333
|
+
// Send what we have
|
|
334
|
+
break;
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
// Now we know we're keeping this service, add its size
|
|
338
|
+
current_size += service_size;
|
|
339
|
+
// Successfully added this service, increment counter
|
|
340
|
+
this->send_service_++;
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
// Send the message with dynamically batched services
|
|
344
|
+
api_conn->send_message(resp, api::BluetoothGATTGetServicesResponse::MESSAGE_TYPE);
|
|
345
|
+
}
|
|
346
|
+
|
|
347
|
+
void BluetoothConnection::log_connection_error_(const char *operation, esp_gatt_status_t status) {
|
|
348
|
+
ESP_LOGE(TAG, "[%d] [%s] %s error, status=%d", this->connection_index_, this->address_str().c_str(), operation,
|
|
349
|
+
status);
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
void BluetoothConnection::log_connection_warning_(const char *operation, esp_err_t err) {
|
|
353
|
+
ESP_LOGW(TAG, "[%d] [%s] %s failed, err=%d", this->connection_index_, this->address_str().c_str(), operation, err);
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
void BluetoothConnection::log_gatt_not_connected_(const char *action, const char *type) {
|
|
357
|
+
ESP_LOGW(TAG, "[%d] [%s] Cannot %s GATT %s, not connected.", this->connection_index_, this->address_str().c_str(),
|
|
358
|
+
action, type);
|
|
359
|
+
}
|
|
360
|
+
|
|
361
|
+
void BluetoothConnection::log_gatt_operation_error_(const char *operation, uint16_t handle, esp_gatt_status_t status) {
|
|
362
|
+
ESP_LOGW(TAG, "[%d] [%s] Error %s for handle 0x%2X, status=%d", this->connection_index_, this->address_str().c_str(),
|
|
363
|
+
operation, handle, status);
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
esp_err_t BluetoothConnection::check_and_log_error_(const char *operation, esp_err_t err) {
|
|
367
|
+
if (err != ESP_OK) {
|
|
368
|
+
this->log_connection_warning_(operation, err);
|
|
369
|
+
return err;
|
|
370
|
+
}
|
|
371
|
+
return ESP_OK;
|
|
372
|
+
}
|
|
373
|
+
|
|
21
374
|
bool BluetoothConnection::gattc_event_handler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if,
|
|
22
375
|
esp_ble_gattc_cb_param_t *param) {
|
|
23
376
|
if (!BLEClientBase::gattc_event_handler(event, gattc_if, param))
|
|
@@ -25,22 +378,16 @@ bool BluetoothConnection::gattc_event_handler(esp_gattc_cb_event_t event, esp_ga
|
|
|
25
378
|
|
|
26
379
|
switch (event) {
|
|
27
380
|
case ESP_GATTC_DISCONNECT_EVT: {
|
|
28
|
-
this->
|
|
29
|
-
this->set_address(0);
|
|
30
|
-
this->proxy_->send_connections_free();
|
|
381
|
+
this->reset_connection_(param->disconnect.reason);
|
|
31
382
|
break;
|
|
32
383
|
}
|
|
33
384
|
case ESP_GATTC_CLOSE_EVT: {
|
|
34
|
-
this->
|
|
35
|
-
this->set_address(0);
|
|
36
|
-
this->proxy_->send_connections_free();
|
|
385
|
+
this->reset_connection_(param->close.reason);
|
|
37
386
|
break;
|
|
38
387
|
}
|
|
39
388
|
case ESP_GATTC_OPEN_EVT: {
|
|
40
389
|
if (param->open.status != ESP_GATT_OK && param->open.status != ESP_GATT_ALREADY_OPEN) {
|
|
41
|
-
this->
|
|
42
|
-
this->set_address(0);
|
|
43
|
-
this->proxy_->send_connections_free();
|
|
390
|
+
this->reset_connection_(param->open.status);
|
|
44
391
|
} else if (this->connection_type_ == espbt::ConnectionType::V3_WITH_CACHE) {
|
|
45
392
|
this->proxy_->send_device_connection(this->address_, true, this->mtu_);
|
|
46
393
|
this->proxy_->send_connections_free();
|
|
@@ -64,59 +411,54 @@ bool BluetoothConnection::gattc_event_handler(esp_gattc_cb_event_t event, esp_ga
|
|
|
64
411
|
case ESP_GATTC_READ_DESCR_EVT:
|
|
65
412
|
case ESP_GATTC_READ_CHAR_EVT: {
|
|
66
413
|
if (param->read.status != ESP_GATT_OK) {
|
|
67
|
-
|
|
68
|
-
this->address_str_.c_str(), param->read.handle, param->read.status);
|
|
414
|
+
this->log_gatt_operation_error_("reading char/descriptor", param->read.handle, param->read.status);
|
|
69
415
|
this->proxy_->send_gatt_error(this->address_, param->read.handle, param->read.status);
|
|
70
416
|
break;
|
|
71
417
|
}
|
|
72
418
|
api::BluetoothGATTReadResponse resp;
|
|
73
419
|
resp.address = this->address_;
|
|
74
420
|
resp.handle = param->read.handle;
|
|
75
|
-
resp.
|
|
76
|
-
|
|
77
|
-
resp.data.insert(resp.data.end(), param->read.value, param->read.value + param->read.value_len);
|
|
78
|
-
this->proxy_->get_api_connection()->send_message(resp);
|
|
421
|
+
resp.set_data(param->read.value, param->read.value_len);
|
|
422
|
+
this->proxy_->get_api_connection()->send_message(resp, api::BluetoothGATTReadResponse::MESSAGE_TYPE);
|
|
79
423
|
break;
|
|
80
424
|
}
|
|
81
425
|
case ESP_GATTC_WRITE_CHAR_EVT:
|
|
82
426
|
case ESP_GATTC_WRITE_DESCR_EVT: {
|
|
83
427
|
if (param->write.status != ESP_GATT_OK) {
|
|
84
|
-
|
|
85
|
-
this->address_str_.c_str(), param->write.handle, param->write.status);
|
|
428
|
+
this->log_gatt_operation_error_("writing char/descriptor", param->write.handle, param->write.status);
|
|
86
429
|
this->proxy_->send_gatt_error(this->address_, param->write.handle, param->write.status);
|
|
87
430
|
break;
|
|
88
431
|
}
|
|
89
432
|
api::BluetoothGATTWriteResponse resp;
|
|
90
433
|
resp.address = this->address_;
|
|
91
434
|
resp.handle = param->write.handle;
|
|
92
|
-
this->proxy_->get_api_connection()->send_message(resp);
|
|
435
|
+
this->proxy_->get_api_connection()->send_message(resp, api::BluetoothGATTWriteResponse::MESSAGE_TYPE);
|
|
93
436
|
break;
|
|
94
437
|
}
|
|
95
438
|
case ESP_GATTC_UNREG_FOR_NOTIFY_EVT: {
|
|
96
439
|
if (param->unreg_for_notify.status != ESP_GATT_OK) {
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
param->unreg_for_notify.status);
|
|
440
|
+
this->log_gatt_operation_error_("unregistering notifications", param->unreg_for_notify.handle,
|
|
441
|
+
param->unreg_for_notify.status);
|
|
100
442
|
this->proxy_->send_gatt_error(this->address_, param->unreg_for_notify.handle, param->unreg_for_notify.status);
|
|
101
443
|
break;
|
|
102
444
|
}
|
|
103
445
|
api::BluetoothGATTNotifyResponse resp;
|
|
104
446
|
resp.address = this->address_;
|
|
105
447
|
resp.handle = param->unreg_for_notify.handle;
|
|
106
|
-
this->proxy_->get_api_connection()->send_message(resp);
|
|
448
|
+
this->proxy_->get_api_connection()->send_message(resp, api::BluetoothGATTNotifyResponse::MESSAGE_TYPE);
|
|
107
449
|
break;
|
|
108
450
|
}
|
|
109
451
|
case ESP_GATTC_REG_FOR_NOTIFY_EVT: {
|
|
110
452
|
if (param->reg_for_notify.status != ESP_GATT_OK) {
|
|
111
|
-
|
|
112
|
-
|
|
453
|
+
this->log_gatt_operation_error_("registering notifications", param->reg_for_notify.handle,
|
|
454
|
+
param->reg_for_notify.status);
|
|
113
455
|
this->proxy_->send_gatt_error(this->address_, param->reg_for_notify.handle, param->reg_for_notify.status);
|
|
114
456
|
break;
|
|
115
457
|
}
|
|
116
458
|
api::BluetoothGATTNotifyResponse resp;
|
|
117
459
|
resp.address = this->address_;
|
|
118
460
|
resp.handle = param->reg_for_notify.handle;
|
|
119
|
-
this->proxy_->get_api_connection()->send_message(resp);
|
|
461
|
+
this->proxy_->get_api_connection()->send_message(resp, api::BluetoothGATTNotifyResponse::MESSAGE_TYPE);
|
|
120
462
|
break;
|
|
121
463
|
}
|
|
122
464
|
case ESP_GATTC_NOTIFY_EVT: {
|
|
@@ -125,10 +467,8 @@ bool BluetoothConnection::gattc_event_handler(esp_gattc_cb_event_t event, esp_ga
|
|
|
125
467
|
api::BluetoothGATTNotifyDataResponse resp;
|
|
126
468
|
resp.address = this->address_;
|
|
127
469
|
resp.handle = param->notify.handle;
|
|
128
|
-
resp.
|
|
129
|
-
|
|
130
|
-
resp.data.insert(resp.data.end(), param->notify.value, param->notify.value + param->notify.value_len);
|
|
131
|
-
this->proxy_->get_api_connection()->send_message(resp);
|
|
470
|
+
resp.set_data(param->notify.value, param->notify.value_len);
|
|
471
|
+
this->proxy_->get_api_connection()->send_message(resp, api::BluetoothGATTNotifyDataResponse::MESSAGE_TYPE);
|
|
132
472
|
break;
|
|
133
473
|
}
|
|
134
474
|
default:
|
|
@@ -157,8 +497,7 @@ void BluetoothConnection::gap_event_handler(esp_gap_ble_cb_event_t event, esp_bl
|
|
|
157
497
|
|
|
158
498
|
esp_err_t BluetoothConnection::read_characteristic(uint16_t handle) {
|
|
159
499
|
if (!this->connected()) {
|
|
160
|
-
|
|
161
|
-
this->address_str_.c_str());
|
|
500
|
+
this->log_gatt_not_connected_("read", "characteristic");
|
|
162
501
|
return ESP_GATT_NOT_CONNECTED;
|
|
163
502
|
}
|
|
164
503
|
|
|
@@ -166,18 +505,12 @@ esp_err_t BluetoothConnection::read_characteristic(uint16_t handle) {
|
|
|
166
505
|
handle);
|
|
167
506
|
|
|
168
507
|
esp_err_t err = esp_ble_gattc_read_char(this->gattc_if_, this->conn_id_, handle, ESP_GATT_AUTH_REQ_NONE);
|
|
169
|
-
|
|
170
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_read_char error, err=%d", this->connection_index_,
|
|
171
|
-
this->address_str_.c_str(), err);
|
|
172
|
-
return err;
|
|
173
|
-
}
|
|
174
|
-
return ESP_OK;
|
|
508
|
+
return this->check_and_log_error_("esp_ble_gattc_read_char", err);
|
|
175
509
|
}
|
|
176
510
|
|
|
177
511
|
esp_err_t BluetoothConnection::write_characteristic(uint16_t handle, const std::string &data, bool response) {
|
|
178
512
|
if (!this->connected()) {
|
|
179
|
-
|
|
180
|
-
this->address_str_.c_str());
|
|
513
|
+
this->log_gatt_not_connected_("write", "characteristic");
|
|
181
514
|
return ESP_GATT_NOT_CONNECTED;
|
|
182
515
|
}
|
|
183
516
|
ESP_LOGV(TAG, "[%d] [%s] Writing GATT characteristic handle %d", this->connection_index_, this->address_str_.c_str(),
|
|
@@ -186,36 +519,24 @@ esp_err_t BluetoothConnection::write_characteristic(uint16_t handle, const std::
|
|
|
186
519
|
esp_err_t err =
|
|
187
520
|
esp_ble_gattc_write_char(this->gattc_if_, this->conn_id_, handle, data.size(), (uint8_t *) data.data(),
|
|
188
521
|
response ? ESP_GATT_WRITE_TYPE_RSP : ESP_GATT_WRITE_TYPE_NO_RSP, ESP_GATT_AUTH_REQ_NONE);
|
|
189
|
-
|
|
190
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_write_char error, err=%d", this->connection_index_,
|
|
191
|
-
this->address_str_.c_str(), err);
|
|
192
|
-
return err;
|
|
193
|
-
}
|
|
194
|
-
return ESP_OK;
|
|
522
|
+
return this->check_and_log_error_("esp_ble_gattc_write_char", err);
|
|
195
523
|
}
|
|
196
524
|
|
|
197
525
|
esp_err_t BluetoothConnection::read_descriptor(uint16_t handle) {
|
|
198
526
|
if (!this->connected()) {
|
|
199
|
-
|
|
200
|
-
this->address_str_.c_str());
|
|
527
|
+
this->log_gatt_not_connected_("read", "descriptor");
|
|
201
528
|
return ESP_GATT_NOT_CONNECTED;
|
|
202
529
|
}
|
|
203
530
|
ESP_LOGV(TAG, "[%d] [%s] Reading GATT descriptor handle %d", this->connection_index_, this->address_str_.c_str(),
|
|
204
531
|
handle);
|
|
205
532
|
|
|
206
533
|
esp_err_t err = esp_ble_gattc_read_char_descr(this->gattc_if_, this->conn_id_, handle, ESP_GATT_AUTH_REQ_NONE);
|
|
207
|
-
|
|
208
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_read_char_descr error, err=%d", this->connection_index_,
|
|
209
|
-
this->address_str_.c_str(), err);
|
|
210
|
-
return err;
|
|
211
|
-
}
|
|
212
|
-
return ESP_OK;
|
|
534
|
+
return this->check_and_log_error_("esp_ble_gattc_read_char_descr", err);
|
|
213
535
|
}
|
|
214
536
|
|
|
215
537
|
esp_err_t BluetoothConnection::write_descriptor(uint16_t handle, const std::string &data, bool response) {
|
|
216
538
|
if (!this->connected()) {
|
|
217
|
-
|
|
218
|
-
this->address_str_.c_str());
|
|
539
|
+
this->log_gatt_not_connected_("write", "descriptor");
|
|
219
540
|
return ESP_GATT_NOT_CONNECTED;
|
|
220
541
|
}
|
|
221
542
|
ESP_LOGV(TAG, "[%d] [%s] Writing GATT descriptor handle %d", this->connection_index_, this->address_str_.c_str(),
|
|
@@ -224,18 +545,12 @@ esp_err_t BluetoothConnection::write_descriptor(uint16_t handle, const std::stri
|
|
|
224
545
|
esp_err_t err = esp_ble_gattc_write_char_descr(
|
|
225
546
|
this->gattc_if_, this->conn_id_, handle, data.size(), (uint8_t *) data.data(),
|
|
226
547
|
response ? ESP_GATT_WRITE_TYPE_RSP : ESP_GATT_WRITE_TYPE_NO_RSP, ESP_GATT_AUTH_REQ_NONE);
|
|
227
|
-
|
|
228
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_write_char_descr error, err=%d", this->connection_index_,
|
|
229
|
-
this->address_str_.c_str(), err);
|
|
230
|
-
return err;
|
|
231
|
-
}
|
|
232
|
-
return ESP_OK;
|
|
548
|
+
return this->check_and_log_error_("esp_ble_gattc_write_char_descr", err);
|
|
233
549
|
}
|
|
234
550
|
|
|
235
551
|
esp_err_t BluetoothConnection::notify_characteristic(uint16_t handle, bool enable) {
|
|
236
552
|
if (!this->connected()) {
|
|
237
|
-
|
|
238
|
-
this->address_str_.c_str());
|
|
553
|
+
this->log_gatt_not_connected_("notify", "characteristic");
|
|
239
554
|
return ESP_GATT_NOT_CONNECTED;
|
|
240
555
|
}
|
|
241
556
|
|
|
@@ -243,29 +558,19 @@ esp_err_t BluetoothConnection::notify_characteristic(uint16_t handle, bool enabl
|
|
|
243
558
|
ESP_LOGV(TAG, "[%d] [%s] Registering for GATT characteristic notifications handle %d", this->connection_index_,
|
|
244
559
|
this->address_str_.c_str(), handle);
|
|
245
560
|
esp_err_t err = esp_ble_gattc_register_for_notify(this->gattc_if_, this->remote_bda_, handle);
|
|
246
|
-
|
|
247
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_register_for_notify failed, err=%d", this->connection_index_,
|
|
248
|
-
this->address_str_.c_str(), err);
|
|
249
|
-
return err;
|
|
250
|
-
}
|
|
251
|
-
} else {
|
|
252
|
-
ESP_LOGV(TAG, "[%d] [%s] Unregistering for GATT characteristic notifications handle %d", this->connection_index_,
|
|
253
|
-
this->address_str_.c_str(), handle);
|
|
254
|
-
esp_err_t err = esp_ble_gattc_unregister_for_notify(this->gattc_if_, this->remote_bda_, handle);
|
|
255
|
-
if (err != ESP_OK) {
|
|
256
|
-
ESP_LOGW(TAG, "[%d] [%s] esp_ble_gattc_unregister_for_notify failed, err=%d", this->connection_index_,
|
|
257
|
-
this->address_str_.c_str(), err);
|
|
258
|
-
return err;
|
|
259
|
-
}
|
|
561
|
+
return this->check_and_log_error_("esp_ble_gattc_register_for_notify", err);
|
|
260
562
|
}
|
|
261
|
-
|
|
563
|
+
|
|
564
|
+
ESP_LOGV(TAG, "[%d] [%s] Unregistering for GATT characteristic notifications handle %d", this->connection_index_,
|
|
565
|
+
this->address_str_.c_str(), handle);
|
|
566
|
+
esp_err_t err = esp_ble_gattc_unregister_for_notify(this->gattc_if_, this->remote_bda_, handle);
|
|
567
|
+
return this->check_and_log_error_("esp_ble_gattc_unregister_for_notify", err);
|
|
262
568
|
}
|
|
263
569
|
|
|
264
570
|
esp32_ble_tracker::AdvertisementParserType BluetoothConnection::get_advertisement_parser_type() {
|
|
265
571
|
return this->proxy_->get_advertisement_parser_type();
|
|
266
572
|
}
|
|
267
573
|
|
|
268
|
-
} // namespace bluetooth_proxy
|
|
269
|
-
} // namespace esphome
|
|
574
|
+
} // namespace esphome::bluetooth_proxy
|
|
270
575
|
|
|
271
576
|
#endif // USE_ESP32
|
|
@@ -4,14 +4,14 @@
|
|
|
4
4
|
|
|
5
5
|
#include "esphome/components/esp32_ble_client/ble_client_base.h"
|
|
6
6
|
|
|
7
|
-
namespace esphome {
|
|
8
|
-
namespace bluetooth_proxy {
|
|
7
|
+
namespace esphome::bluetooth_proxy {
|
|
9
8
|
|
|
10
9
|
class BluetoothProxy;
|
|
11
10
|
|
|
12
11
|
class BluetoothConnection : public esp32_ble_client::BLEClientBase {
|
|
13
12
|
public:
|
|
14
13
|
void dump_config() override;
|
|
14
|
+
void loop() override;
|
|
15
15
|
bool gattc_event_handler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if,
|
|
16
16
|
esp_ble_gattc_cb_param_t *param) override;
|
|
17
17
|
void gap_event_handler(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t *param) override;
|
|
@@ -24,22 +24,33 @@ class BluetoothConnection : public esp32_ble_client::BLEClientBase {
|
|
|
24
24
|
|
|
25
25
|
esp_err_t notify_characteristic(uint16_t handle, bool enable);
|
|
26
26
|
|
|
27
|
+
void set_address(uint64_t address) override;
|
|
28
|
+
|
|
27
29
|
protected:
|
|
28
30
|
friend class BluetoothProxy;
|
|
29
31
|
|
|
32
|
+
bool supports_efficient_uuids_() const;
|
|
33
|
+
void send_service_for_discovery_();
|
|
34
|
+
void reset_connection_(esp_err_t reason);
|
|
35
|
+
void update_allocated_slot_(uint64_t find_value, uint64_t set_value);
|
|
36
|
+
void log_connection_error_(const char *operation, esp_gatt_status_t status);
|
|
37
|
+
void log_connection_warning_(const char *operation, esp_err_t err);
|
|
38
|
+
void log_gatt_not_connected_(const char *action, const char *type);
|
|
39
|
+
void log_gatt_operation_error_(const char *operation, uint16_t handle, esp_gatt_status_t status);
|
|
40
|
+
esp_err_t check_and_log_error_(const char *operation, esp_err_t err);
|
|
41
|
+
|
|
30
42
|
// Memory optimized layout for 32-bit systems
|
|
31
43
|
// Group 1: Pointers (4 bytes each, naturally aligned)
|
|
32
44
|
BluetoothProxy *proxy_;
|
|
33
45
|
|
|
34
46
|
// Group 2: 2-byte types
|
|
35
|
-
int16_t send_service_{-
|
|
47
|
+
int16_t send_service_{-3}; // -3 = INIT_SENDING_SERVICES, -2 = DONE_SENDING_SERVICES, >=0 = service index
|
|
36
48
|
|
|
37
49
|
// Group 3: 1-byte types
|
|
38
50
|
bool seen_mtu_or_services_{false};
|
|
39
51
|
// 1 byte used, 1 byte padding
|
|
40
52
|
};
|
|
41
53
|
|
|
42
|
-
} // namespace bluetooth_proxy
|
|
43
|
-
} // namespace esphome
|
|
54
|
+
} // namespace esphome::bluetooth_proxy
|
|
44
55
|
|
|
45
56
|
#endif // USE_ESP32
|