mirror of
https://github.com/esphome/esphome.git
synced 2026-10-26 16:02:13 +00:00
Compare commits
6
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a17ddfec99 | ||
|
|
227097a36e | ||
|
|
d7472891f0 | ||
|
|
1080e9d285 | ||
|
|
a04e6a0508 | ||
|
|
8c242a46ee |
No files matched your search
@@ -642,7 +642,10 @@ def Pvariable(id_: ID, rhs: SafeExpType, type_: "MockObj" = None) -> "MockObj":
|
|||||||
MockObj(f"reinterpret_cast<{pointer_type} *>({storage_name})"),
|
MockObj(f"reinterpret_cast<{pointer_type} *>({storage_name})"),
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
placement_new = CallExpression(f"new({id_.id}) {actual_type}", *call_expr.args)
|
# No parens without args: `T()` value-initializes, zero-filling .bss that is already zero.
|
||||||
|
placement_new = RawExpression(f"new({id_.id}) {actual_type}")
|
||||||
|
if call_expr.args.args:
|
||||||
|
placement_new = CallExpression(placement_new, *call_expr.args)
|
||||||
CORE.add(ExpressionStatement(placement_new))
|
CORE.add(ExpressionStatement(placement_new))
|
||||||
else:
|
else:
|
||||||
decl = VariableDeclarationExpression(id_.type, "*", id_, static=True)
|
decl = VariableDeclarationExpression(id_.type, "*", id_, static=True)
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ def test_button_is_setup(generate_main):
|
|||||||
|
|
||||||
# Then
|
# Then
|
||||||
assert "static wake_on_lan::WakeOnLanButton *const" in main_cpp
|
assert "static wake_on_lan::WakeOnLanButton *const" in main_cpp
|
||||||
assert ") wake_on_lan::WakeOnLanButton();" in main_cpp
|
assert ") wake_on_lan::WakeOnLanButton;" in main_cpp
|
||||||
assert "App.register_button" in main_cpp
|
assert "App.register_button" in main_cpp
|
||||||
assert "App.register_component" in main_cpp
|
assert "App.register_component" in main_cpp
|
||||||
|
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ def test_deep_sleep_setup(generate_main):
|
|||||||
"static deep_sleep::DeepSleepComponent *const deepsleep = reinterpret_cast<deep_sleep::DeepSleepComponent *>(deep_sleep__deepsleep__pstorage);"
|
"static deep_sleep::DeepSleepComponent *const deepsleep = reinterpret_cast<deep_sleep::DeepSleepComponent *>(deep_sleep__deepsleep__pstorage);"
|
||||||
in main_cpp
|
in main_cpp
|
||||||
)
|
)
|
||||||
assert "new(deepsleep) deep_sleep::DeepSleepComponent();" in main_cpp
|
assert "new(deepsleep) deep_sleep::DeepSleepComponent;" in main_cpp
|
||||||
assert "App.register_component_(deepsleep, " in main_cpp
|
assert "App.register_component_(deepsleep, " in main_cpp
|
||||||
|
|
||||||
|
|
||||||
@@ -49,7 +49,7 @@ def test_deep_sleep_on_wake_trigger(generate_main):
|
|||||||
"""
|
"""
|
||||||
main_cpp = generate_main("tests/component_tests/deep_sleep/test_deep_sleep3.yaml")
|
main_cpp = generate_main("tests/component_tests/deep_sleep/test_deep_sleep3.yaml")
|
||||||
|
|
||||||
assert "deep_sleep::WakeTrigger();" in main_cpp
|
assert "deep_sleep::WakeTrigger;" in main_cpp
|
||||||
assert "Automation<deep_sleep::WakeupCause>" in main_cpp
|
assert "Automation<deep_sleep::WakeupCause>" in main_cpp
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ def test_gpio_binary_sensor_basic_setup(
|
|||||||
main_cpp = generate_main("tests/component_tests/gpio/test_gpio_binary_sensor.yaml")
|
main_cpp = generate_main("tests/component_tests/gpio/test_gpio_binary_sensor.yaml")
|
||||||
|
|
||||||
assert "static gpio::GPIOBinarySensor *const" in main_cpp
|
assert "static gpio::GPIOBinarySensor *const" in main_cpp
|
||||||
assert ") gpio::GPIOBinarySensor();" in main_cpp
|
assert ") gpio::GPIOBinarySensor;" in main_cpp
|
||||||
assert "App.register_binary_sensor" in main_cpp
|
assert "App.register_binary_sensor" in main_cpp
|
||||||
# set_use_interrupt(true) should NOT be generated (uses C++ default)
|
# set_use_interrupt(true) should NOT be generated (uses C++ default)
|
||||||
assert "bs_gpio->set_use_interrupt(true);" not in main_cpp
|
assert "bs_gpio->set_use_interrupt(true);" not in main_cpp
|
||||||
|
|||||||
@@ -26,6 +26,6 @@ def test_ili9xxx_placement_new_uses_model_subclass(
|
|||||||
# Pointer is declared as the base type for polymorphism.
|
# Pointer is declared as the base type for polymorphism.
|
||||||
assert "static ili9xxx::ILI9XXXDisplay *const tft_display" in main_cpp
|
assert "static ili9xxx::ILI9XXXDisplay *const tft_display" in main_cpp
|
||||||
# Placement new runs the subclass constructor — this is the actual regression fix.
|
# Placement new runs the subclass constructor — this is the actual regression fix.
|
||||||
assert "new(tft_display) ili9xxx::ILI9XXXST7789V()" in main_cpp
|
assert "new(tft_display) ili9xxx::ILI9XXXST7789V;" in main_cpp
|
||||||
# Base-class default constructor must NOT be used.
|
# Base-class default constructor must NOT be used.
|
||||||
assert "new(tft_display) ili9xxx::ILI9XXXDisplay()" not in main_cpp
|
assert "new(tft_display) ili9xxx::ILI9XXXDisplay;" not in main_cpp
|
||||||
@@ -358,7 +358,7 @@ def test_native_generation(
|
|||||||
|
|
||||||
main_cpp = generate_main(component_fixture_path("native.yaml"))
|
main_cpp = generate_main(component_fixture_path("native.yaml"))
|
||||||
assert (
|
assert (
|
||||||
"mipi_spi::MipiSpiBuffer<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_QUAD, 360, 360, 0, 1, 0, 0, 0, true, 1, 1>()"
|
"mipi_spi::MipiSpiBuffer<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_QUAD, 360, 360, 0, 1, 0, 0, 0, true, 1, 1>;"
|
||||||
in main_cpp
|
in main_cpp
|
||||||
)
|
)
|
||||||
# A 10ms post-reset delay ({10, 255}) is prepended ahead of the model commands.
|
# A 10ms post-reset delay ({10, 255}) is prepended ahead of the model commands.
|
||||||
@@ -375,7 +375,7 @@ def test_lvgl_generation(
|
|||||||
|
|
||||||
main_cpp = generate_main(component_fixture_path("lvgl.yaml"))
|
main_cpp = generate_main(component_fixture_path("lvgl.yaml"))
|
||||||
assert (
|
assert (
|
||||||
"mipi_spi::MipiSpi<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_SINGLE, 128, 160, 0, 0, 0, 0, 0, true>();"
|
"mipi_spi::MipiSpi<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_SINGLE, 128, 160, 0, 0, 0, 0, 0, true>;"
|
||||||
in main_cpp
|
in main_cpp
|
||||||
)
|
)
|
||||||
# A 10ms post-reset delay ({10, 255}) is prepended ahead of the model commands.
|
# A 10ms post-reset delay ({10, 255}) is prepended ahead of the model commands.
|
||||||
|
|||||||
@@ -314,7 +314,7 @@ class TestTemplateParameterPassing:
|
|||||||
# FRACTION, ROUNDING)
|
# FRACTION, ROUNDING)
|
||||||
# The instantiation should include padding values (0, 0 for default)
|
# The instantiation should include padding values (0, 0 for default)
|
||||||
assert (
|
assert (
|
||||||
"mipi_spi::MipiSpiBuffer<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_QUAD, 360, 360, 0, 1, 0, 0, 0, true, 1, 1>()"
|
"mipi_spi::MipiSpiBuffer<uint16_t, mipi_spi::PIXEL_MODE_16, true, mipi_spi::PIXEL_MODE_16, mipi_spi::BUS_TYPE_QUAD, 360, 360, 0, 1, 0, 0, 0, true, 1, 1>;"
|
||||||
in main_cpp
|
in main_cpp
|
||||||
), (
|
), (
|
||||||
"Padding parameters (0, 0) should be in the MipiSpiBuffer template instantiation"
|
"Padding parameters (0, 0) should be in the MipiSpiBuffer template instantiation"
|
||||||
|
|||||||
@@ -30,10 +30,10 @@ def test_template_text_saver_uses_placement_new_with_templated_subclass(
|
|||||||
in main_cpp
|
in main_cpp
|
||||||
)
|
)
|
||||||
# Placement new runs the templated subclass constructor.
|
# Placement new runs the templated subclass constructor.
|
||||||
assert "new(test_text_restore_value_saver) template_::TextSaver<10>()" in main_cpp
|
assert "new(test_text_restore_value_saver) template_::TextSaver<10>;" in main_cpp
|
||||||
# Base-class default ctor must NOT be used.
|
# Base-class default ctor must NOT be used.
|
||||||
assert (
|
assert (
|
||||||
"new(test_text_restore_value_saver) template_::TemplateTextSaverBase()"
|
"new(test_text_restore_value_saver) template_::TemplateTextSaverBase;"
|
||||||
not in main_cpp
|
not in main_cpp
|
||||||
)
|
)
|
||||||
# No heap `new TextSaver<...>()` left over — the pre-fix pattern.
|
# No heap `new TextSaver<...>()` left over — the pre-fix pattern.
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ def test_text_is_setup(generate_main):
|
|||||||
|
|
||||||
# Then
|
# Then
|
||||||
assert "static template_::TemplateText *const" in main_cpp
|
assert "static template_::TemplateText *const" in main_cpp
|
||||||
assert ") template_::TemplateText();" in main_cpp
|
assert ") template_::TemplateText;" in main_cpp
|
||||||
assert "App.register_text" in main_cpp
|
assert "App.register_text" in main_cpp
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ def test_text_sensor_is_setup(generate_main):
|
|||||||
|
|
||||||
# Then
|
# Then
|
||||||
assert "static template_::TemplateTextSensor *const" in main_cpp
|
assert "static template_::TemplateTextSensor *const" in main_cpp
|
||||||
assert ") template_::TemplateTextSensor();" in main_cpp
|
assert ") template_::TemplateTextSensor;" in main_cpp
|
||||||
assert "App.register_text_sensor" in main_cpp
|
assert "App.register_text_sensor" in main_cpp
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import math
|
|||||||
import pytest
|
import pytest
|
||||||
|
|
||||||
from esphome import cpp_generator as cg, cpp_types as ct
|
from esphome import cpp_generator as cg, cpp_types as ct
|
||||||
|
from esphome.core import CORE
|
||||||
|
|
||||||
|
|
||||||
class TestExpressions:
|
class TestExpressions:
|
||||||
@@ -790,3 +791,27 @@ async def test_templatable__lambda_with_std_string() -> None:
|
|||||||
result = await cg.templatable(lambda_obj, [], ct.std_string)
|
result = await cg.templatable(lambda_obj, [], ct.std_string)
|
||||||
|
|
||||||
assert isinstance(result, cg.LambdaExpression)
|
assert isinstance(result, cg.LambdaExpression)
|
||||||
|
|
||||||
|
|
||||||
|
class TestPvariablePlacementNew:
|
||||||
|
def _placement_new(self) -> str:
|
||||||
|
return next(
|
||||||
|
str(stmt) for stmt in CORE.main_statements if str(stmt).startswith("new(")
|
||||||
|
)
|
||||||
|
|
||||||
|
def test_no_args_uses_default_initialization(self) -> None:
|
||||||
|
"""`new(p) T` rather than `new(p) T()`: value initialization would zero-fill
|
||||||
|
storage that is already zero, costing a loop of flash at every site."""
|
||||||
|
id_ = cg.ID("my_id", is_declaration=True, type=ct.esphome_ns.class_("Foo"))
|
||||||
|
cg.new_Pvariable(id_)
|
||||||
|
assert self._placement_new() == "new(my_id) Foo;"
|
||||||
|
|
||||||
|
def test_with_args_calls_constructor(self) -> None:
|
||||||
|
id_ = cg.ID("my_id", is_declaration=True, type=ct.esphome_ns.class_("Foo"))
|
||||||
|
cg.new_Pvariable(id_, 1, 2)
|
||||||
|
assert self._placement_new() == "new(my_id) Foo(1, 2);"
|
||||||
|
|
||||||
|
def test_template_args_without_ctor_args(self) -> None:
|
||||||
|
id_ = cg.ID("my_id", is_declaration=True, type=ct.esphome_ns.class_("Foo"))
|
||||||
|
cg.new_Pvariable(id_, cg.TemplateArguments(ct.uint8))
|
||||||
|
assert self._placement_new() == "new(my_id) Foo<uint8_t>;"
|
||||||
Reference in new issue
Block a user