Device migrations, drivers and fixes (#571)
Device migrations: - cyd-4848S040c - guition-jc1060p470ciwy - guition-jc2432w328c - guition-jc3248w535c (known issue with display and touch, Shadowtrance will look into it) - guition-jc8048w550c - heltec-wifi-lora-32-v3 - lilygo-tdeck-max (excluding graphics) - lilygo-tdisplay - lilygo-tdisplay-s3 - lilygo-tdongle-s3 - lilygo-tlora-pager Driver migrations: - Implemented haptic driver interface in kernel - AXS15231b - BQ25896 - BQ27220 - CST328 - CST6xx - DRV2605 - JD9165 - Custom LilyGO driver for T-Lora Pager - SSD1306 - ST7701 - ST7735 - SY6970 - TCA8418 Fixes/improvements: - Boot app: support for multiple power devices, improved UI - lvgl_devices and related code: fixes for mapping - Support for arrays in dts parser
This commit is contained in:
committed by
GitHub
parent
3b5a401594
commit
d896657bf9
@@ -161,7 +161,7 @@ def resolve_parameters_from_bindings(device: Device, bindings: list[Binding], de
|
||||
|
||||
node_name = get_device_node_name_safe(device)
|
||||
result = []
|
||||
phandle_arrays = []
|
||||
array_decls = []
|
||||
for binding_property in binding_properties:
|
||||
device_property = find_device_property(device, binding_property.name)
|
||||
|
||||
@@ -172,7 +172,35 @@ def resolve_parameters_from_bindings(device: Device, bindings: list[Binding], de
|
||||
array_var = f"{node_name}_{prop_safe}"
|
||||
if device_property is not None:
|
||||
entries = resolve_phandle_array_entries(device_property, devices)
|
||||
phandle_arrays.append((array_var, binding_property.element_type, entries))
|
||||
array_decls.append((array_var, binding_property.element_type, entries))
|
||||
result.append(f"({binding_property.element_type}*){array_var}")
|
||||
result.append(str(len(entries)))
|
||||
elif binding_property.default is not None:
|
||||
result.append("NULL")
|
||||
result.append("0")
|
||||
elif binding_property.required:
|
||||
raise DevicetreeException(f"device {device.node_name} doesn't have property '{binding_property.name}'")
|
||||
else:
|
||||
result.append("NULL")
|
||||
result.append("0")
|
||||
continue
|
||||
|
||||
if binding_property.type == "array":
|
||||
# A flat literal array (DTS `[ ... ]` syntax, e.g. a byte blob), as opposed to
|
||||
# phandle-array's list of resolved device references. Emits the same
|
||||
# (pointer, length) parameter pair, backed by a plain data array instead of one
|
||||
# holding phandle-derived initializers.
|
||||
if binding_property.element_type is None:
|
||||
raise DevicetreeException(f"array property '{binding_property.name}' requires 'element-type' in binding")
|
||||
prop_safe = binding_property.name.replace("-", "_")
|
||||
array_var = f"{node_name}_{prop_safe}"
|
||||
if device_property is not None:
|
||||
if device_property.type != "array":
|
||||
raise DevicetreeException(
|
||||
f"Device '{device.node_name}' property '{binding_property.name}' must use '[ ... ]' array syntax"
|
||||
)
|
||||
entries = [str(value) for value in device_property.value]
|
||||
array_decls.append((array_var, binding_property.element_type, entries))
|
||||
result.append(f"({binding_property.element_type}*){array_var}")
|
||||
result.append(str(len(entries)))
|
||||
elif binding_property.default is not None:
|
||||
@@ -207,17 +235,17 @@ def resolve_parameters_from_bindings(device: Device, bindings: list[Binding], de
|
||||
validate_property_range(device, binding_property, device_property.value)
|
||||
result.append(property_to_string(device_property, devices))
|
||||
|
||||
return result, phandle_arrays
|
||||
return result, array_decls
|
||||
|
||||
def write_config(file, device: Device, bindings: list[Binding], devices: list[Device], type_name: str):
|
||||
node_name = get_device_node_name_safe(device)
|
||||
config_type = f"{type_name}_config_dt"
|
||||
config_variable_name = f"{node_name}_config"
|
||||
|
||||
config_params, phandle_arrays = resolve_parameters_from_bindings(device, bindings, devices)
|
||||
config_params, array_decls = resolve_parameters_from_bindings(device, bindings, devices)
|
||||
|
||||
# Write phandle-array variables before the config struct
|
||||
for array_var, element_type, entries in phandle_arrays:
|
||||
# Write phandle-array/array variables before the config struct
|
||||
for array_var, element_type, entries in array_decls:
|
||||
entries_str = ", ".join(entries)
|
||||
file.write(f"static {element_type} {array_var}[] = {{ {entries_str} }};\n")
|
||||
|
||||
|
||||
@@ -209,6 +209,92 @@ def test_minmax_symbolic_value_skips_validation():
|
||||
print("PASSED")
|
||||
return True
|
||||
|
||||
def write_array_config(tmp_dir, device_property_line):
|
||||
config_dir = os.path.join(tmp_dir, "array_data")
|
||||
bindings_dir = os.path.join(config_dir, "bindings")
|
||||
os.makedirs(bindings_dir)
|
||||
|
||||
with open(os.path.join(config_dir, "devicetree.yaml"), "w") as f:
|
||||
f.write("dts: test.dts\nbindings: bindings")
|
||||
|
||||
with open(os.path.join(config_dir, "test.dts"), "w") as f:
|
||||
f.write(f"""/dts-v1/;
|
||||
|
||||
/ {{
|
||||
compatible = "test,root";
|
||||
model = "Test Model";
|
||||
|
||||
test-device@0 {{
|
||||
compatible = "test,array-device";
|
||||
{device_property_line}
|
||||
}};
|
||||
}};
|
||||
""")
|
||||
|
||||
with open(os.path.join(bindings_dir, "test,root.yaml"), "w") as f:
|
||||
f.write("description: Test root binding\ncompatible: \"test,root\"\nproperties:\n model:\n type: string\n")
|
||||
|
||||
with open(os.path.join(bindings_dir, "test,array-device.yaml"), "w") as f:
|
||||
f.write("""description: Test array binding
|
||||
compatible: "test,array-device"
|
||||
properties:
|
||||
init-sequence:
|
||||
type: array
|
||||
element-type: uint8_t
|
||||
""")
|
||||
|
||||
return config_dir
|
||||
|
||||
def test_array_property_generates_static_array_and_length():
|
||||
print("Running test_array_property_generates_static_array_and_length...")
|
||||
with tempfile.TemporaryDirectory() as tmp_dir:
|
||||
config_dir = write_array_config(tmp_dir, "init-sequence = [0xFF 0x01 0x00 0x00 0x10 5 0];")
|
||||
output_dir = os.path.join(tmp_dir, "output")
|
||||
os.makedirs(output_dir)
|
||||
|
||||
result = run_compiler(config_dir, output_dir)
|
||||
|
||||
if result.returncode != 0:
|
||||
print(f"FAILED: Compilation should have succeeded: {result.stderr} {result.stdout}")
|
||||
return False
|
||||
|
||||
with open(os.path.join(output_dir, "devicetree.c")) as f:
|
||||
generated = f.read()
|
||||
|
||||
if "static uint8_t test_device_init_sequence[] = { 0xFF, 0x01, 0x00, 0x00, 0x10, 5, 0 };" not in generated:
|
||||
print(f"FAILED: Expected static array declaration not found:\n{generated}")
|
||||
return False
|
||||
|
||||
if "(uint8_t*)test_device_init_sequence" not in generated or "\t7\n" not in generated:
|
||||
print(f"FAILED: Expected (pointer, length) config params not found:\n{generated}")
|
||||
return False
|
||||
|
||||
print("PASSED")
|
||||
return True
|
||||
|
||||
def test_array_property_defaults_to_null_when_absent():
|
||||
print("Running test_array_property_defaults_to_null_when_absent...")
|
||||
with tempfile.TemporaryDirectory() as tmp_dir:
|
||||
config_dir = write_array_config(tmp_dir, "")
|
||||
output_dir = os.path.join(tmp_dir, "output")
|
||||
os.makedirs(output_dir)
|
||||
|
||||
result = run_compiler(config_dir, output_dir)
|
||||
|
||||
if result.returncode != 0:
|
||||
print(f"FAILED: Compilation should have succeeded: {result.stderr} {result.stdout}")
|
||||
return False
|
||||
|
||||
with open(os.path.join(output_dir, "devicetree.c")) as f:
|
||||
generated = f.read()
|
||||
|
||||
if "NULL,\n\t0" not in generated:
|
||||
print(f"FAILED: Expected NULL/0 defaults not found:\n{generated}")
|
||||
return False
|
||||
|
||||
print("PASSED")
|
||||
return True
|
||||
|
||||
def test_compile_missing_config():
|
||||
print("Running test_compile_missing_config...")
|
||||
with tempfile.TemporaryDirectory() as output_dir:
|
||||
@@ -234,7 +320,9 @@ if __name__ == "__main__":
|
||||
test_minmax_below_minimum_fails,
|
||||
test_minmax_above_maximum_fails,
|
||||
test_minmax_out_of_range_default_fails,
|
||||
test_minmax_symbolic_value_skips_validation
|
||||
test_minmax_symbolic_value_skips_validation,
|
||||
test_array_property_generates_static_array_and_length,
|
||||
test_array_property_defaults_to_null_when_absent
|
||||
]
|
||||
|
||||
failed = 0
|
||||
|
||||
Reference in New Issue
Block a user