summaryrefslogtreecommitdiff
path: root/tools/proxyclient/m1n1/fw/dcp/iboot.py
diff options
context:
space:
mode:
Diffstat (limited to 'tools/proxyclient/m1n1/fw/dcp/iboot.py')
-rw-r--r--tools/proxyclient/m1n1/fw/dcp/iboot.py215
1 files changed, 215 insertions, 0 deletions
diff --git a/tools/proxyclient/m1n1/fw/dcp/iboot.py b/tools/proxyclient/m1n1/fw/dcp/iboot.py
new file mode 100644
index 0000000..8124ca9
--- /dev/null
+++ b/tools/proxyclient/m1n1/fw/dcp/iboot.py
@@ -0,0 +1,215 @@
+# SPDX-License-Identifier: MIT
+from construct import *
+
+from ...utils import *
+from ..asc import StandardASC
+from ..afk.epic import *
+from .dcpav import *
+
+EOTF = "EOTF" / Enum(Int32ul,
+ GAMMA_SDR = 1,
+ GAMMA_HDR = 2,
+)
+
+Encoding = "Encoding" / Enum(Int32ul,
+ RGB = 1,
+ YCBCR_444 = 3,
+ YCBCR_422 = 4,
+ YCBCR_420 = 5,
+)
+
+Colorimetry = "Colorimetry" / Enum(Int32ul,
+ BT601_709 = 1,
+ BT2020 = 2,
+ DCIP3 = 3,
+)
+
+Colorspace = "Colorspace" / Enum(Int32ul,
+ SRGB = 1,
+ Native = 2,
+ BT2020 = 3,
+)
+
+SurfaceFormat = "SurfaceFormat" / Enum(Int32ul,
+ BGRA = 1,
+ BGRA2 = 2,
+ RGBA = 3,
+ w18p = 4,
+ BGRA3 = 5,
+ _444v = 6,
+ _422v = 7,
+ _420v = 8,
+ w30r = 9,
+ w40a = 10,
+)
+
+Transform = "Transform" / Enum(Int8ul,
+ NONE = 0,
+ XFLIP = 1,
+ YFLIP = 2,
+ ROT_90 = 3,
+ ROT_180 = 4,
+ ROT_270 = 5,
+)
+
+AddrFormat = "AddrFormat" / Enum(Int32ul,
+ PLANAR = 1,
+ TILED = 2,
+ AGX = 3
+)
+
+TimingMode = Struct(
+ "valid" / Bool(Int32ul),
+ "width" / Int32ul,
+ "height" / Int32ul,
+ "fps_frac" / Int16ul,
+ "fps_int" / Int16ul,
+ Padding(8),
+)
+
+TimingModeList = Struct(
+ "count" / Int32ul,
+ "list" / GreedyRange(TimingMode),
+)
+
+ColorMode = Struct(
+ "valid" / Bool(Int32ul),
+ "colorimetry" / Colorimetry,
+ "eotf" / EOTF,
+ "encoding" / Encoding,
+ "bpp" / Int32ul,
+ "unk" / Int32ul,
+)
+
+ColorModeList = Struct(
+ "count" / Int32ul,
+ "list" / GreedyRange(ColorMode),
+)
+
+SwapInfo = Struct(
+ "unk1" / Int32ul,
+ "unk2" / Int32ul,
+ "unk3" / Int32ul,
+ "swap_id" / Int32ul,
+ "unk5" / Int32ul,
+)
+
+IBootPlaneInfo = Struct(
+ "unk1" / Default(Int32ul, 0),
+ "addr" / Default(Int64ul, 0),
+ "tile_size" / Default(Int32ul, 0),
+ "stride" / Default(Int32ul, 0),
+ "unk5" / Default(Int32ul, 0),
+ "unk6" / Default(Int32ul, 0),
+ "unk7" / Default(Int32ul, 0),
+ "unk8" / Default(Int32ul, 0),
+ "addr_format" / Default(AddrFormat, 0),
+ "unk9" / Default(Int32ul, 0),
+)
+
+IBootLayerInfo = Struct(
+ "planes" / Array(3, IBootPlaneInfo),
+ "unk" / Default(Int32ul, 0),
+ "plane_cnt" / Int32ul,
+ "width" / Int32ul,
+ "height" / Int32ul,
+ "surface_fmt" / SurfaceFormat,
+ "colorspace" / Colorspace,
+ "eotf" / EOTF,
+ "transform" / Transform,
+ Padding(3)
+)
+
+SwapSetLayer = Struct(
+ "unk" / Default(Int32ul, 0),
+ "layer_id" / Int32ul,
+ "layer_info" / IBootLayerInfo,
+ "src_w" / Int32ul,
+ "src_h" / Int32ul,
+ "src_x" / Int32ul,
+ "src_y" / Int32ul,
+ "dst_w" / Int32ul,
+ "dst_h" / Int32ul,
+ "dst_x" / Int32ul,
+ "dst_y" / Int32ul,
+ "unk2" / Default(Int32ul, 0),
+)
+
+class DCPIBootService(EPICService):
+ NAME = "disp0-service"
+ SHORT = "disp0"
+
+ def send_cmd(self, op, data=b'', replen=None):
+ msg = struct.pack("<IIII", op, 16 + len(data), 0, 0) + data
+ if replen is not None:
+ replen += 8
+ resp = super().send_cmd(0xc0, msg, replen)
+ if not resp:
+ return
+ rcmd, rlen = struct.unpack("<II", resp[:8])
+ return resp[8:rlen]
+
+ def setPower(self, power):
+ self.send_cmd(2, b"\x01" if power else b"\x00")
+
+ def getModeCount(self):
+ buf = self.send_cmd(3, b"", 12)
+ hpd, timing_cnt, color_cnt = struct.unpack("<B3xII", buf)
+ return bool(hpd), timing_cnt, color_cnt
+
+ def getTimingModes(self):
+ return TimingModeList.parse(self.send_cmd(4, replen=4096)).list
+
+ def getColorModes(self):
+ return ColorModeList.parse(self.send_cmd(5, replen=4096)).list
+
+ def setMode(self, timing_mode, color_mode):
+ data = TimingMode.build(timing_mode) + ColorMode.build(color_mode)
+ self.send_cmd(6, data)
+
+ def swapBegin(self):
+ return SwapInfo.parse(self.send_cmd(15, replen=128))
+
+ def swapSetLayer(self, layer_id, info, src_rect, dst_rect):
+ data = Container()
+ data.layer_id = layer_id
+ data.layer_info = info
+ data.src_w, data.src_h, data.src_x, data.src_y = src_rect
+ data.dst_w, data.dst_h, data.dst_x, data.dst_y = dst_rect
+ return self.send_cmd(16, SwapSetLayer.build(data), replen=128)
+
+ def swapSetTimestamp(self):
+ pass
+ # 17
+
+ def swapEnd(self):
+ return self.send_cmd(18, b"\x00" * 12, replen=128)
+
+ #def swapWait(self, swap_id):
+ #buf = struct.pack("<IIII", 1, swap_id, 0, swap_id)
+ #return self.send_cmd(19, buf, replen=128)
+
+class DCPIBootEndpoint(EPICEndpoint):
+ SHORT = "iboot"
+
+ SERVICES = [
+ DCPIBootService,
+ ]
+
+
+class DCPIBootClient(StandardASC):
+ DVA_OFFSET = 0xf00000000
+
+ ENDPOINTS = {
+ 0x20: AFKSystemEndpoint,
+ 0x23: DCPIBootEndpoint,
+ 0x24: DCPDPTXEndpoint,
+ 0x2a: DCPDPTXPortEndpoint,
+ 0x27: DCPAVDeviceEndpoint,
+ 0x28: DCPAVServiceEndpoint,
+ 0x29: DCPAVVideoEndpoint,
+ }
+
+ def __init__(self, u, asc_base, dart=None, disp_dart=None):
+ super().__init__(u, asc_base, dart)
+ self.disp_dart = disp_dart