blob: 7a1de5b71d4399743d53a14b39fd03d7b79207b4 [file] [log] [blame]
"""Functions related to hardware topology.
See proto definitions for descriptions of arguments.
"""
# Needed to load from @proto. Add @unused to silence lint.
load("//config/util/bindings/proto.star", "protos")
load(
"@proto//chromiumos/config/api/topology.proto",
topo_pb = "chromiumos.config.api",
)
load(
"@proto//chromiumos/config/api/hardware_topology.proto",
hw_topo_pb = "chromiumos.config.api",
)
load(
"@proto//chromiumos/config/api/component.proto",
comp_pb = "chromiumos.config.api",
)
_PRESENT = struct(
UNKNOWN = topo_pb.HardwareFeatures.PRESENT_UNKNOWN,
PRESENT = topo_pb.HardwareFeatures.PRESENT,
NOT_PRESENT = topo_pb.HardwareFeatures.NOT_PRESENT,
)
_FF = struct(
CLAMSHELL = topo_pb.HardwareFeatures.FormFactor.CLAMSHELL,
CONVERTIBLE = topo_pb.HardwareFeatures.FormFactor.CONVERTIBLE,
DETACHABLE = topo_pb.HardwareFeatures.FormFactor.DETACHABLE,
CHROMEBASE = topo_pb.HardwareFeatures.FormFactor.CHROMEBASE,
CHROMEBOX = topo_pb.HardwareFeatures.FormFactor.CHROMEBOX,
CHROMEBIT = topo_pb.HardwareFeatures.FormFactor.CHROMEBIT,
CHROMESLATE = topo_pb.HardwareFeatures.FormFactor.CHROMESLATE,
)
_AUDIO_CODEC = struct(
RT5682 = topo_pb.HardwareFeatures.Audio.RT5682,
ALC5682I = topo_pb.HardwareFeatures.Audio.ALC5682I,
ALC5682 = topo_pb.HardwareFeatures.Audio.ALC5682,
MAX98357 = topo_pb.HardwareFeatures.Audio.MAX98357,
MAX98373 = topo_pb.HardwareFeatures.Audio.MAX98373,
MAX98360 = topo_pb.HardwareFeatures.Audio.MAX98360,
RT1015 = topo_pb.HardwareFeatures.Audio.RT1015,
DA7219 = topo_pb.HardwareFeatures.Audio.DA7219,
ALC1011 = topo_pb.HardwareFeatures.Audio.ALC1011,
)
_FP_LOC = struct(
NOT_PRESENT = topo_pb.HardwareFeatures.Fingerprint.NOT_PRESENT,
POWER_BUTTON_TOP_LEFT = topo_pb.HardwareFeatures.Fingerprint.POWER_BUTTON_TOP_LEFT,
KEYBOARD_BOTTOM_LEFT = topo_pb.HardwareFeatures.Fingerprint.KEYBOARD_BOTTOM_LEFT,
KEYBOARD_BOTTOM_RIGHT = topo_pb.HardwareFeatures.Fingerprint.KEYBOARD_BOTTOM_RIGHT,
KEYBOARD_TOP_RIGHT = topo_pb.HardwareFeatures.Fingerprint.KEYBOARD_TOP_RIGHT,
POWER_BUTTON_SIDE_RIGHT = topo_pb.HardwareFeatures.Fingerprint.POWER_BUTTON_SIDE_RIGHT,
)
_STORAGE = struct(
EMMC = comp_pb.Component.Storage.EMMC,
NVME = comp_pb.Component.Storage.NVME,
SATA = comp_pb.Component.Storage.SATA,
)
_KB_TYPE = struct(
NONE = topo_pb.HardwareFeatures.Keyboard.NONE,
INTERNAL = topo_pb.HardwareFeatures.Keyboard.INTERNAL,
DETACHABLE = topo_pb.HardwareFeatures.Keyboard.DETACHABLE,
)
_STYLUS = struct(
NONE = topo_pb.HardwareFeatures.Stylus.NONE,
INTERNAL = topo_pb.HardwareFeatures.Stylus.INTERNAL,
EXTERNAL = topo_pb.HardwareFeatures.Stylus.EXTERNAL,
)
_REGION = struct(
SCREEN = topo_pb.HardwareFeatures.Button.SCREEN,
KEYBOARD = topo_pb.HardwareFeatures.Button.KEYBOARD,
)
_EDGE = struct(
LEFT = topo_pb.HardwareFeatures.Button.LEFT,
RIGHT = topo_pb.HardwareFeatures.Button.RIGHT,
TOP = topo_pb.HardwareFeatures.Button.TOP,
BOTTOM = topo_pb.HardwareFeatures.Button.BOTTOM,
)
_CAMERA_FLAGS = struct(
SUPPORT_1080P = topo_pb.HardwareFeatures.Camera.FLAGS_SUPPORT_1080P,
SUPPORT_AUTOFOCUS = topo_pb.HardwareFeatures.Camera.FLAGS_SUPPORT_AUTOFOCUS,
)
_EC_TYPE = struct(
UNKNOWN = topo_pb.HardwareFeatures.EmbeddedController.EC_TYPE_UNKNOWN,
CHROME = topo_pb.HardwareFeatures.EmbeddedController.EC_CHROME,
WILCO = topo_pb.HardwareFeatures.EmbeddedController.EC_WILCO,
)
# Starlark doesn't support converting enums to their names. Add helper fns. to
# do so.
def _button_region_to_str(region):
return {
_REGION.SCREEN: "SCREEN",
_REGION.KEYBOARD: "KEYBOARD",
}.get(region, "UNKNOWN")
def _button_edge_to_str(edge):
return {
_EDGE.LEFT: "LEFT",
_EDGE.RIGHT: "RIGHT",
_EDGE.TOP: "TOP",
_EDGE.BOTTOM: "BOTTOM",
}.get(edge, "UNKNOWN")
def _make_fw_config(mask, id):
"""Builds a HardwareFeatures.FirmwareConfiguration proto.
Takes a 32-bit mask for the field and an id. Shifts the id
into the mask region and checks that the value fits within the bit mask.
"""
lsb_bit_set = (~mask + 1) & mask
shifted_id = id * lsb_bit_set
if shifted_id & mask != shifted_id:
fail("Specified id %d out of range [0, %d]" % (id, mask // lsb_bit_set))
return topo_pb.HardwareFeatures.FirmwareConfiguration(
value = shifted_id,
mask = mask,
)
def _accumulate_fw_config(existing_fw_config, new_fw_config):
"""Adds fw config to existing fw config."""
if existing_fw_config.mask & new_fw_config.mask:
fail("FW_CONFIG masks cannot overlap! 0x%x and 0x%x" %
(existing_fw_config.mask, new_fw_config.mask))
existing_fw_config.value += new_fw_config.value
existing_fw_config.mask += new_fw_config.mask
def _accumulate_fw_configs(result_hw_features, fw_configs):
for fw_config in fw_configs:
_accumulate_fw_config(result_hw_features.fw_config, fw_config)
def _create_design_features(form_factor = _FF.CLAMSHELL):
"""Builds a HardwareFeatures proto with form_factor."""
return topo_pb.HardwareFeatures(
form_factor = topo_pb.HardwareFeatures.FormFactor(
form_factor = form_factor,
),
)
def _create_features(form_factors = [_FF.CLAMSHELL, _FF.CONVERTIBLE]):
"""Builds a HardwareFeatures proto for each of form_factors."""
return [_create_design_features(ff) for ff in form_factors]
def _bool_to_present(value):
"""Returns correct value of present enum depending on value"""
if value == None:
return _PRESENT.UNKNOWN
elif value:
return _PRESENT.PRESENT
else:
return _PRESENT.NOT_PRESENT
def _create_screen(
id = None,
description = None,
inches = 0,
width_px = None,
height_px = None,
pixels_per_in = None,
touch = False,
fw_configs = []):
"""Builds a Topology proto for a screen."""
hw_features = topo_pb.HardwareFeatures()
hw_features.screen.panel_properties = comp_pb.Component.DisplayPanel.Properties(
diagonal_milliinch = inches * 1000,
width_px = width_px,
height_px = height_px,
pixels_per_in = pixels_per_in,
)
hw_features.screen.touch_support = _bool_to_present(touch)
_accumulate_fw_configs(hw_features, fw_configs)
if touch:
screen_id = id if id else "TOUCHSCREEN"
screen_desc = description if description else "Touchscreen"
else:
screen_id = id if id else "SCREEN"
screen_desc = description if description else "Default screen"
return topo_pb.Topology(
id = screen_id,
type = topo_pb.Topology.SCREEN,
description = {"EN": screen_desc},
hardware_feature = hw_features,
)
def _create_form_factor(form_factor, fw_configs = [], id = None, description = None):
"""Builds a Topology proto for a form factor.
Args:
form_factor: A FormFactorType enum. Required.
fw_configs: A list of FirmwareConfiguration protos for the form factor.
id: A string identifier for the Topology. If not passed, a default is
provided based on form_factor.
description: An English description for the Topology. If not passed, a
default is provided based on form_factor.
"""
if not id:
id = {
_FF.CLAMSHELL: "CLAMSHELL",
_FF.CONVERTIBLE: "CONVERTIBLE",
_FF.CHROMEBOX: "CHROMEBOX",
}[form_factor]
if not description:
description = {
_FF.CLAMSHELL: "Device cannot rotate past 180 degrees",
_FF.CONVERTIBLE: "Device can rotate 360 degrees",
_FF.CHROMEBOX: "Desktop chrome device.",
}[form_factor]
hw_features = topo_pb.HardwareFeatures()
hw_features.form_factor.form_factor = form_factor
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.FORM_FACTOR,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_audio(id, description, codec = None, speaker_amp = None, headphone_codec = None, fw_configs = []):
"""Builds a Topology proto for audio."""
hw_features = topo_pb.HardwareFeatures()
if codec:
hw_features.audio.audio_codec = codec
if speaker_amp:
hw_features.audio.speaker_amp = speaker_amp
if headphone_codec:
hw_features.audio.headphone_codec = headphone_codec
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.AUDIO,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_stylus(id, description, stylus_type, fw_configs = []):
"""Builds a Topology proto for a stylus."""
hw_features = topo_pb.HardwareFeatures()
hw_features.stylus.stylus = stylus_type
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.STYLUS,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_keyboard(backlight, pwr_btn_present, kb_type, fw_configs = [], id = None, description = None):
"""Builds a Topology proto for a keyboard.
Args:
backlight: True if a backlight is present. Required.
pwr_btn_present: True if a power button is present. Required.
kb_type: A KeyboardType enum. Required.
fw_configs: A list of FirmwareConfiguration protos for the form factor.
id: A string identifier for the Topology. If not passed, a default is
provided.
description: An English description for the Topology. If not passed, a
default is provided.
"""
if not id:
id = "KB_{backlight}".format(
backlight = "BL" if backlight else "NO_BL",
)
if not description:
# Starlark doesn't seem to have a way to find the enum name with
# reflection.
if kb_type == topo_pb.HardwareFeatures.Keyboard.INTERNAL:
type_str = "Internal"
elif kb_type == topo_pb.HardwareFeatures.Keyboard.DETACHABLE:
type_str = "Detachable"
else:
type_str = "Unknown type"
description = "{type} keyboard {backlight} backlight".format(
type = type_str,
backlight = "with" if backlight else "without",
)
hw_features = topo_pb.HardwareFeatures()
hw_features.keyboard.keyboard_type = kb_type
hw_features.keyboard.backlight = _bool_to_present(backlight)
hw_features.keyboard.power_button = _bool_to_present(pwr_btn_present)
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.KEYBOARD,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_thermal(id, description, fw_configs = []):
"""Builds a Topology proto for thermal."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.THERMAL,
description = {"EN": description},
hardware_feature = hw_features,
)
def _make_camera_device(interface, facing, orientation, flags, ids):
"""Builds a HardwareFeatures.Camera.Device proto."""
camera_pb = topo_pb.HardwareFeatures.Camera
device = camera_pb.Device()
device.interface = {
"usb": camera_pb.INTERFACE_USB,
"mipi": camera_pb.INTERFACE_MIPI,
}[interface]
device.facing = {
"back": camera_pb.FACING_BACK,
"front": camera_pb.FACING_FRONT,
}[facing]
device.orientation = {
0: camera_pb.ORIENTATION_0,
90: camera_pb.ORIENTATION_90,
180: camera_pb.ORIENTATION_180,
270: camera_pb.ORIENTATION_270,
}[orientation]
device.flags = flags
device.ids = ids
return device
def _create_camera(
id,
description,
fw_configs = [],
camera_devices = []):
"""Builds a Topology proto for cameras.
Args:
id: A string identifier for the Topology.
description: An English description for the Topology.
fw_configs: A list of FirmwareConfiguration protos for the form factor.
camera_devices: A list of HardwareFeatures.Camera.Device protos.
"""
hw_features = topo_pb.HardwareFeatures()
camera = hw_features.camera
camera.devices = camera_devices
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.CAMERA,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_sensor(
id,
description,
fw_configs = [],
lid_accel_present = None,
base_accel_present = None,
lid_gyro_present = None,
base_gyro_present = None,
lid_magno_present = None,
base_magno_present = None,
lid_light_present = None,
base_light_present = None):
"""Builds a Topology proto for accelerometer/gyroscrope/magnometer sensors."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
if lid_accel_present:
hw_features.accelerometer.lid_accelerometer = _bool_to_present(lid_accel_present)
if base_accel_present:
hw_features.accelerometer.base_accelerometer = _bool_to_present(base_accel_present)
if lid_gyro_present:
hw_features.gyroscope.lid_gyroscope = _bool_to_present(lid_gyro_present)
if base_gyro_present:
hw_features.gyroscope.base_gyroscope = _bool_to_present(base_gyro_present)
if lid_magno_present:
hw_features.magnetometer.lid_magnetometer = _bool_to_present(lid_magno_present)
if base_magno_present:
hw_features.magnetometer.base_magnetometer = _bool_to_present(base_magno_present)
if lid_light_present:
hw_features.light_sensor.lid_lightsensor = _bool_to_present(lid_light_present)
if base_light_present:
hw_features.light_sensor.base_lightsensor = _bool_to_present(base_light_present)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.ACCELEROMETER_GYROSCOPE_MAGNETOMETER,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_fingerprint(id, description, location, board = None, fw_configs = []):
"""Builds a Topology proto for a fingerprint reader."""
hw_features = topo_pb.HardwareFeatures()
hw_features.fingerprint.location = location
if board:
hw_features.fingerprint.board = board
if board == "bloonchipper":
hw_features.fingerprint.ro_version = "bloonchipper_v2.0.5938-197506c1"
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.FINGERPRINT,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_proximity_sensor(id, description, fw_configs = []):
"""Builds a Topology proto for a proximity sensor."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.PROXIMITY_SENSOR,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_daughter_board(
id,
description,
fw_configs = [],
usbc_count = 0,
usba_count = 0,
lte_support = False,
hdmi_support = False):
"""Builds a Topology proto for a daughter board."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
hw_features.usb_c.count.value = usbc_count
hw_features.usb_a.count.value = usba_count
hw_features.lte.present = _bool_to_present(lte_support)
hw_features.hdmi.present = _bool_to_present(hdmi_support)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.DAUGHTER_BOARD,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_non_volatile_storage(id, description, storage_type, fw_configs = []):
"""Builds a Topology proto for non-volatile storage."""
hw_features = topo_pb.HardwareFeatures()
hw_features.storage.storage_type = storage_type
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.NON_VOLATILE_STORAGE,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_wifi(id, description, fw_configs = []):
"""Builds a Topology proto for a WiFi chip."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.WIFI,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_lte_board(id, description, lte_present, fw_configs = []):
"""Builds a Topology proto for a LTE board."""
hw_features = topo_pb.HardwareFeatures()
hw_features.lte.present = _bool_to_present(lte_present)
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.LTE_BOARD,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_sd_reader(id, description, fw_configs = []):
"""Builds a Topology proto for a SD reader."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.SD_READER,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_motherboard_usb(
id,
description,
fw_configs = [],
usbc_count = 0,
usba_count = 0):
"""Builds a Topology proto for a motherboard."""
hw_features = topo_pb.HardwareFeatures()
_accumulate_fw_configs(hw_features, fw_configs)
hw_features.usb_c.count.value = usbc_count
hw_features.usb_a.count.value = usba_count
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.MOTHERBOARD_USB,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_bluetooth(id, description, bt_component, fw_configs = []):
"""Builds a Topology proto for bluetooth."""
hw_features = topo_pb.HardwareFeatures()
hw_features.bluetooth.component = bt_component
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.BLUETOOTH,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_barreljack(id, description, bj_present, fw_configs = []):
"""Builds a Topology proto for barreljack."""
hw_features = topo_pb.HardwareFeatures()
hw_features.barreljack.present = _bool_to_present(bj_present)
_accumulate_fw_configs(hw_features, fw_configs)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.BARRELJACK,
description = {"EN": description},
hardware_feature = hw_features,
)
def _create_power_button(region, edge, position, id = None, description = None):
"""Builds a Topology proto for a power button.
Args:
region: A HardwareFeatures.Button.Region enum. Required.
edge: A HardwareFeatures.Button.Edge enum. Required.
position: The percentage for button center position to the display's
width/height in primary landscape screen orientation. If edge is
LEFT or RIGHT, specifies the button's center position as a fraction
of region's height relative to the top of region. For TOP and
BOTTOM, specifies the position as a fraction of region width
relative to the left side of region. Must be in the range
[0.0, 1.0]. Required.
id: A string identifier for the Topology. If not passed, a default is
provided.
description: An English description for the Topology. If not passed, a
default is provided.
"""
if not id:
id = "{region}_{edge}_POWER_BUTTON".format(
region = _button_region_to_str(region),
edge = _button_edge_to_str(edge),
)
if not description:
description = "Power button on the {edge} edge of the {region}".format(
region = _button_region_to_str(region).lower(),
edge = _button_edge_to_str(edge).lower(),
)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.POWER_BUTTON,
description = {"EN": description},
hardware_feature = topo_pb.HardwareFeatures(
power_button = topo_pb.HardwareFeatures.Button(
region = region,
edge = edge,
position = position,
),
),
)
def _create_volume_button(region, edge, position, id = None, description = None):
"""Builds a Topology proto for a volume button.
Args:
region: A HardwareFeatures.Button.Region enum. Required.
edge: A HardwareFeatures.Button.Edge enum. Required.
position: The percentage for button center position to the display's
width/height in primary landscape screen orientation. If edge is
LEFT or RIGHT, specifies the button's center position as a fraction
of region's height relative to the top of region. For TOP and
BOTTOM, specifies the position as a fraction of region width
relative to the left side of region. Must be in the range
[0.0, 1.0]. Required.
id: A string identifier for the Topology. If not passed, a default is
provided.
description: An English description for the Topology. If not passed, a
default is provided.
"""
if not id:
id = "{region}_{edge}_VOLUME_BUTTON".format(
region = _button_region_to_str(region),
edge = _button_edge_to_str(edge),
)
if not description:
description = "Volume button on the {edge} edge of the {region}".format(
region = _button_region_to_str(region).lower(),
edge = _button_edge_to_str(edge).lower(),
)
return topo_pb.Topology(
id = id,
type = topo_pb.Topology.POWER_BUTTON,
description = {"EN": description},
hardware_feature = topo_pb.HardwareFeatures(
volume_button = topo_pb.HardwareFeatures.Button(
region = region,
edge = edge,
position = position,
),
),
)
def _create_ec(present = True, ec_type = _EC_TYPE.CHROME, id = None):
"""Builds a Topology proto for an embedded controller.
Args:
present: flag indicating whether the device has an EC at all
ec_type: An EmbeddedControllerType enum
id: A string identifier for the Topology. If not passed, a default is
provided.
"""
hw_features = topo_pb.HardwareFeatures()
hw_features.embedded_controller.ec_type = ec_type
hw_features.embedded_controller.present = _bool_to_present(present)
return topo_pb.Topology(
id = id or "ec",
type = topo_pb.Topology.EC,
hardware_feature = hw_features,
)
# enumerate the common cases
_EC_NONE = _create_ec(present = False, ec_type = _EC_TYPE.UNKNOWN)
_EC_CHROME = _create_ec(ec_type = _EC_TYPE.CHROME)
_EC_WILCO = _create_ec(ec_type = _EC_TYPE.WILCO)
def _create_hardware_topology(
screen = None,
form_factor = None,
audio = None,
stylus = None,
keyboard = None,
thermal = None,
camera = None,
accelerometer_gyroscope_magnetometer = None,
fingerprint = None,
proximity_sensor = None,
daughter_board = None,
non_volatile_storage = None,
wifi = None,
lte_board = None,
sd_reader = None,
motherboard_usb = None,
bluetooth = None,
barreljack = None,
power_button = None,
volume_button = None,
ec = None):
"""Builds a HardwareTopology proto from Topology protos."""
# Only allow form_factor topologies for form factors
if screen and screen.type != topo_pb.Topology.SCREEN:
fail("Invalid screen topology")
if form_factor and form_factor.type != topo_pb.Topology.FORM_FACTOR:
fail("Invalid form factor topology")
if audio and audio.type != topo_pb.Topology.AUDIO:
fail("Invalid audio topology")
if stylus and stylus.type != topo_pb.Topology.STYLUS:
fail("Invalid stylus topology")
if keyboard and keyboard.type != topo_pb.Topology.KEYBOARD:
fail("Invalid keyboard topology")
if thermal and thermal.type != topo_pb.Topology.THERMAL:
fail("Invalid thermal topology")
if camera and camera.type != topo_pb.Topology.CAMERA:
fail("Invalid camera topology")
if accelerometer_gyroscope_magnetometer and accelerometer_gyroscope_magnetometer.type != topo_pb.Topology.ACCELEROMETER_GYROSCOPE_MAGNETOMETER:
fail("Invalid accelerometer/gyroscope/magnetometer topology")
if fingerprint and fingerprint.type != topo_pb.Topology.FINGERPRINT:
fail("Invalid fingerprint topology")
if proximity_sensor and proximity_sensor.type != topo_pb.Topology.PROXIMITY_SENSOR:
fail("Invalid proximity sensor topology")
if daughter_board and daughter_board.type != topo_pb.Topology.DAUGHTER_BOARD:
fail("Invalid daughter board topology")
if non_volatile_storage and non_volatile_storage.type != topo_pb.Topology.NON_VOLATILE_STORAGE:
fail("Invalid non-volatile storage topology")
if wifi and wifi.type != topo_pb.Topology.WIFI:
fail("Invalid wifi topology")
if lte_board and lte_board.type != topo_pb.Topology.LTE_BOARD:
fail("Invalid lte board topology")
if sd_reader and sd_reader.type != topo_pb.Topology.SD_READER:
fail("Invalid lte board topology")
if motherboard_usb and motherboard_usb.type != topo_pb.Topology.MOTHERBOARD_USB:
fail("Invalid motherboard usb board topology")
if bluetooth and bluetooth.type != topo_pb.Topology.BLUETOOTH:
fail("Invalid bluetooth topology")
if barreljack and barreljack.type != topo_pb.Topology.BARRELJACK:
fail("Invalid barreljack topology")
if power_button and power_button.type != topo_pb.Topology.POWER_BUTTON:
fail("Invalid power button topology")
if volume_button and volume_button.type != topo_pb.Topology.POWER_BUTTON:
fail("Invalid volume button topology")
if ec and ec.type != topo_pb.Topology.EC:
fail("Invalid ec type")
return hw_topo_pb.HardwareTopology(
screen = screen,
form_factor = form_factor,
audio = audio,
stylus = stylus,
keyboard = keyboard,
thermal = thermal,
camera = camera,
accelerometer_gyroscope_magnetometer = accelerometer_gyroscope_magnetometer,
fingerprint = fingerprint,
proximity_sensor = proximity_sensor,
daughter_board = daughter_board,
non_volatile_storage = non_volatile_storage,
wifi = wifi,
lte_board = lte_board,
sd_reader = sd_reader,
motherboard_usb = motherboard_usb,
bluetooth = bluetooth,
barreljack = barreljack,
power_button = power_button,
volume_button = volume_button,
ec = ec,
)
def _accumulate_presence(existing_present, new_present):
if existing_present == _PRESENT.PRESENT:
return existing_present
elif new_present != _PRESENT.UNKNOWN:
return new_present
else:
return existing_present
def _accumulate_usbc(existing_usbc, new_usbc):
existing_usbc.count.value += new_usbc.count.value
def _accumulate_usba(existing_usba, new_usba):
existing_usba.count.value += new_usba.count.value
def _accumulate_lte(existing_lte, new_lte):
existing_lte.present = _accumulate_presence(existing_lte.present, new_lte.present)
def _accumulate_hdmi(existing_hdmi, new_hdmi):
existing_hdmi.present = _accumulate_presence(existing_hdmi.present, new_hdmi.present)
def _convert_to_hw_features(hardware_topology):
"""Converts a HardwareTopology proto to a HardwareFeatures proto."""
result = topo_pb.HardwareFeatures()
# Need to make deep-copy otherwise we change the has_ message serialization
copy = proto.from_textpb(hw_topo_pb.HardwareTopology, proto.to_textpb(hardware_topology))
# Handle all possible screen hardware features attributes
_accumulate_fw_config(result.fw_config, copy.screen.hardware_feature.fw_config)
if copy.screen.hardware_feature.screen != topo_pb.HardwareFeatures.Screen():
result.screen = copy.screen.hardware_feature.screen
# Handle all possible form factor hardware features attributes
_accumulate_fw_config(result.fw_config, copy.form_factor.hardware_feature.fw_config)
if copy.form_factor.hardware_feature.form_factor != topo_pb.HardwareFeatures.FormFactor():
result.form_factor = copy.form_factor.hardware_feature.form_factor
# Handle all possible audio features attributes
_accumulate_fw_config(result.fw_config, copy.audio.hardware_feature.fw_config)
if copy.audio.hardware_feature.audio != topo_pb.HardwareFeatures.Audio():
result.audio = copy.audio.hardware_feature.audio
# Handle all possible stylus hardware features attributes
_accumulate_fw_config(result.fw_config, copy.stylus.hardware_feature.fw_config)
if copy.stylus.hardware_feature.stylus != topo_pb.HardwareFeatures.Stylus():
result.stylus = copy.stylus.hardware_feature.stylus
# Handle all possible keyboard hardware features attributes
_accumulate_fw_config(result.fw_config, copy.keyboard.hardware_feature.fw_config)
if copy.keyboard.hardware_feature.keyboard != topo_pb.HardwareFeatures.Keyboard():
result.keyboard = copy.keyboard.hardware_feature.keyboard
# Handle all possible thermal features attributes
_accumulate_fw_config(result.fw_config, copy.thermal.hardware_feature.fw_config)
# Handle all possible camera features attributes
_accumulate_fw_config(result.fw_config, copy.camera.hardware_feature.fw_config)
if copy.camera.hardware_feature.camera != topo_pb.HardwareFeatures.Camera():
result.camera = copy.camera.hardware_feature.camera
# Handle all possible sensor attributes
_accumulate_fw_config(result.fw_config, copy.accelerometer_gyroscope_magnetometer.hardware_feature.fw_config)
if copy.accelerometer_gyroscope_magnetometer.hardware_feature.accelerometer != topo_pb.HardwareFeatures.Accelerometer():
result.accelerometer = copy.accelerometer_gyroscope_magnetometer.hardware_feature.accelerometer
if copy.accelerometer_gyroscope_magnetometer.hardware_feature.gyroscope != topo_pb.HardwareFeatures.Gyroscope():
result.gyroscope = copy.accelerometer_gyroscope_magnetometer.hardware_feature.gyroscope
if copy.accelerometer_gyroscope_magnetometer.hardware_feature.magnetometer != topo_pb.HardwareFeatures.Magnetometer():
result.magnetometer = copy.accelerometer_gyroscope_magnetometer.hardware_feature.magnetometer
if copy.accelerometer_gyroscope_magnetometer.hardware_feature.light_sensor != topo_pb.HardwareFeatures.LightSensor():
result.light_sensor = copy.accelerometer_gyroscope_magnetometer.hardware_feature.light_sensor
# Handle all possible fingerprint hardware features attributes
_accumulate_fw_config(result.fw_config, copy.fingerprint.hardware_feature.fw_config)
if copy.fingerprint.hardware_feature.fingerprint != topo_pb.HardwareFeatures.Fingerprint():
result.fingerprint = copy.fingerprint.hardware_feature.fingerprint
# Handle all possible proximity sensor hardware features attributes
_accumulate_fw_config(result.fw_config, copy.proximity_sensor.hardware_feature.fw_config)
# Handle all possible daughter board hardware features attributes
_accumulate_fw_config(result.fw_config, copy.daughter_board.hardware_feature.fw_config)
if copy.daughter_board.hardware_feature.usb_c != topo_pb.HardwareFeatures.UsbC():
_accumulate_usbc(result.usb_c, copy.daughter_board.hardware_feature.usb_c)
if copy.daughter_board.hardware_feature.usb_a != topo_pb.HardwareFeatures.UsbA():
_accumulate_usba(result.usb_a, copy.daughter_board.hardware_feature.usb_a)
if copy.daughter_board.hardware_feature.lte != topo_pb.HardwareFeatures.Lte():
_accumulate_lte(result.lte, copy.daughter_board.hardware_feature.lte)
if copy.daughter_board.hardware_feature.hdmi != topo_pb.HardwareFeatures.Hdmi():
_accumulate_hdmi(result.hdmi, copy.daughter_board.hardware_feature.hdmi)
# Handle all possible non volatile storage hardware features attributes
_accumulate_fw_config(result.fw_config, copy.non_volatile_storage.hardware_feature.fw_config)
if copy.non_volatile_storage.hardware_feature.storage != topo_pb.HardwareFeatures.Storage():
result.storage = copy.non_volatile_storage.hardware_feature.storage
# Handle all possible wifi hardware features attributes
_accumulate_fw_config(result.fw_config, copy.wifi.hardware_feature.fw_config)
# Handle all possible lte board attributes
_accumulate_fw_config(result.fw_config, copy.lte_board.hardware_feature.fw_config)
if copy.lte_board.hardware_feature.lte != topo_pb.HardwareFeatures.Lte():
result.lte.present = _accumulate_presence(result.lte.present, copy.lte_board.hardware_feature.lte.present)
# Handle all possible sd reader hardware features attributes
_accumulate_fw_config(result.fw_config, copy.sd_reader.hardware_feature.fw_config)
# Handle all possible motherboard usb features attributes
_accumulate_fw_config(result.fw_config, copy.motherboard_usb.hardware_feature.fw_config)
if copy.motherboard_usb.hardware_feature.usb_c != topo_pb.HardwareFeatures.UsbC():
_accumulate_usbc(result.usb_c, copy.motherboard_usb.hardware_feature.usb_c)
if copy.motherboard_usb.hardware_feature.usb_a != topo_pb.HardwareFeatures.UsbA():
_accumulate_usba(result.usb_a, copy.motherboard_usb.hardware_feature.usb_a)
# Handle all possible bluetooth features attributes
_accumulate_fw_config(result.fw_config, copy.bluetooth.hardware_feature.fw_config)
if copy.bluetooth.hardware_feature.bluetooth != topo_pb.HardwareFeatures.Bluetooth():
result.bluetooth = copy.bluetooth.hardware_feature.bluetooth
# Handle all possible barreljack features
_accumulate_fw_config(result.fw_config, copy.barreljack.hardware_feature.fw_config)
if copy.barreljack.hardware_feature.barreljack != topo_pb.HardwareFeatures.BarrelJack():
result.barreljack = copy.barreljack.hardware_feature.barreljack
if copy.power_button.hardware_feature.power_button != topo_pb.HardwareFeatures.Button():
result.power_button = copy.power_button.hardware_feature.power_button
if copy.volume_button.hardware_feature.volume_button != topo_pb.HardwareFeatures.Button():
result.volume_button = copy.volume_button.hardware_feature.volume_button
return result
hw_topo = struct(
create_design_features = _create_design_features,
create_features = _create_features,
create_screen = _create_screen,
create_form_factor = _create_form_factor,
create_audio = _create_audio,
create_stylus = _create_stylus,
create_keyboard = _create_keyboard,
create_thermal = _create_thermal,
create_camera = _create_camera,
create_sensor = _create_sensor,
create_fingerprint = _create_fingerprint,
create_proximity_sensor = _create_proximity_sensor,
create_daughter_board = _create_daughter_board,
create_non_volatile_storage = _create_non_volatile_storage,
create_wifi = _create_wifi,
create_lte_board = _create_lte_board,
create_sd_reader = _create_sd_reader,
create_motherboard_usb = _create_motherboard_usb,
create_bluetooth = _create_bluetooth,
create_barreljack = _create_barreljack,
create_hardware_topology = _create_hardware_topology,
create_power_button = _create_power_button,
create_volume_button = _create_volume_button,
convert_to_hw_features = _convert_to_hw_features,
make_camera_device = _make_camera_device,
make_fw_config = _make_fw_config,
ff = _FF,
audio_codec = _AUDIO_CODEC,
fp_loc = _FP_LOC,
storage = _STORAGE,
kb_type = _KB_TYPE,
stylus = _STYLUS,
region = _REGION,
edge = _EDGE,
camera_flags = _CAMERA_FLAGS,
present = _PRESENT,
# embedded controller exports
ec_type = _EC_TYPE,
create_ec = _create_ec,
EC_NONE = _EC_NONE,
EC_CHROME = _EC_CHROME,
EC_WILCO = _EC_WILCO,
)