Files
krane-fb-stub/uboot-wrapper.S
T

102 lines
2.7 KiB
ArmAsm

/*
* krane diagnostic wrapper runs before U-Boot proper after the
* depthcharge handoff (MMU off, caches off; position-independent:
* immediate-encoded addresses only).
*
* Purpose: prove that the payload actually executes and revive the
* display before U-Boot gets a chance to crash, so a dark screen can be
* attributed unambiguously:
* - magenta screen + backlight on, 3 slow blinks, magenta held ~5 s,
* then U-Boot takes over: wrapper ran
* - blink train repeating periodically: watchdog reset loop
* - dark screen, no blink train: wrapper never executed
*
* Register sources (all verified on device, see RESEARCH.md rounds 4/10):
* OVL0 base 0x14008000: OVL_EN @ +0x000c, OVL0_2L_EN @ +0x100c,
* OVL_L0_ADDR @ +0x0f40 (depthcharge device-era mtk_ddp.c).
* GPIO controller 0x10005000, dout block +0x100, 16 B per 32-pin
* group, set @ +4 / rst @ +8 (mt8183.h GpioRegs):
* DISP_PWM = pin 43 (bit 11, set 0x10005114 / rst 0x10005118),
* EN_LCD_BL = pin 176 (bit 16, set 0x10005154 / rst 0x10005158).
* Scanout geometry: 1200*1920, 32bpp xRGB, 0x8ca000 bytes.
*/
.text
.globl _start
_start:
/* OVL_EN = 1 */
mov w2, #1
mov w3, #0x800c
movk w3, #0x1400, lsl #16
str w2, [x3]
/* OVL0_2L_EN = 1 */
mov w3, #0x900c
movk w3, #0x1400, lsl #16
str w2, [x3]
/* backlight on: pin 43 (DISP_PWM), dout set 0x10005114, bit 11 */
mov w2, #0x800
mov w3, #0x5114
movk w3, #0x1000, lsl #16
str w2, [x3]
/* backlight on: pin 176 (EN_LCD_BL), dout set 0x10005154, bit 16 */
mov w2, #0x10000
mov w3, #0x5154
movk w3, #0x1000, lsl #16
str w2, [x3]
/* live scanout address: OVL_L0_ADDR = 0x14008f40 */
mov w3, #0x8f40
movk w3, #0x1400, lsl #16
ldr w4, [x3]
/* fill only when the address looks like DRAM (>= 0x40000000) */
mov w5, #0x4000
movk w5, #0x4000, lsl #16
cmp w4, w5
b.lo 1f
/* fill the scanout with magenta (0x00ff00ff): 0x8ca000/4 words */
mov w2, #0xff
movk w2, #0xff00, lsl #16
mov x6, #0x2800
movk x6, #0x23, lsl #16
2: str w2, [x4], #4
subs x6, x6, #1
b.ne 2b
/* blink the backlight 3x: repeating trains reveal a reset loop */
mov w11, #3
6: mov w2, #0x800
mov w3, #0x5118
movk w3, #0x1000, lsl #16
str w2, [x3]
mov w2, #0x10000
mov w3, #0x5158
movk w3, #0x1000, lsl #16
str w2, [x3]
bl delay
mov w2, #0x800
mov w3, #0x5114
movk w3, #0x1000, lsl #16
str w2, [x3]
mov w2, #0x10000
mov w3, #0x5154
movk w3, #0x1000, lsl #16
str w2, [x3]
bl delay
subs w11, w11, #1
b.ne 6b
/* hold magenta for ~5 s so the phase cannot be missed */
mov w12, #20
7: bl delay
subs w12, w12, #1
b.ne 7b
1: b . /* PATCHED: branch to U-Boot entry */
/* ~250 ms delay using the arch timer */
delay:
mrs x7, cntfrq_el0
lsr x7, x7, #2
mrs x8, cntvct_el0
add x8, x8, x7
9: mrs x9, cntvct_el0
cmp x9, x8
b.lo 9b
ret