Visão geral de segurança do software do processador S905X (inicialização segura)

Este artigo discutirá a proteção de software no processador S905X. O objetivo final é lançar software não autorizado.

S905X


O processador S905X é um ARM Cortex-A53 com uma frequência de clock de até 1,5 GHz, repleto de todos os tipos de decodificadores para fluxos de vídeo e áudio, como H.265 4K, VP9, ​​suportando 4KUHD, etc. Em geral, não é uma má escolha. Diferentemente de seu antecessor, o AMLogic integrou o chamado "sistema de segurança Advanced TrustZone" neste processador, que controla todas as operações críticas do sistema, como acessar áreas protegidas da memória ROM, verificar a assinatura e descriptografar o software, etc. Documentação detalhada sobre esse tópico pode ser encontrada no site do fabricante . O SecureOS atua como ATOS-V1.5-g3e467d9 (não afirmo, não verifiquei).

Treinamento


Depois de desmontar o prefixo, encontrei facilmente os pinos RxD, TxD e GND para o UART. No verso, havia um conector para o botão de reinicialização (não verificado) e um local para o conector. A julgar pela localização, o conector parecia uma placa-a-placa para uma placa eMMS alternativa (a pinagem está naturalmente ausente).



A documentação de acesso livre para tópicos importantes do S905 como, por exemplo, a sequência de inicialização não afetou muito ou menos e foi praticamente inútil do ponto de vista do ER. Colocando a documentação de lado, conectei o UART e ... fiquei agradavelmente surpreendido com a velocidade de carregamento do processador. Mas isso é provavelmente tudo. O U-Boot não reagiu de maneira alguma ao teclado e, após algumas configurações de hardware, carregou e lançou o kernel Android de forma inteligente.

U-Boot'a log de inicialização
 GXL:BL1:9ac50e:bb16dc;FEAT:BDFC31BC:0;POC:3;RCY:0;EMMC:0;READ:0;0.0;0.0;CHK:0;
TE: 351954

BL2 Built : 16:42:36, Nov  3 2016. 
gxl g3eddb43 - xiaobo.gu@droid05

set vcck to 1120 mv
set vddee to 1000 mv
Board ID = 4
CPU clk: 1200MHz
DQS-corr enabled
DDR scramble enabled
DDR3 chl: Rank0+1 @ 768MHz - FAIL
DDR3 chl: Rank0 @ 768MHz - PASS
Rank0: 1024MB(auto)-2T-11
DataBus test pass!
AddrBus test pass!
-s
Load fip header from eMMC, src: 0x0000c200, des: 0x01400000, size: 0x00004000
aml log : R2048 check pass!
New fip structure!
Load bl30 from eMMC, src: 0x00010200, des: 0x01700000, size: 0x0000d600
aml log : R2048 check pass!
Load bl31 from eMMC, src: 0x00020200, des: 0x01700000, size: 0x00015400
aml log : R2048 check pass!
Load bl32 from eMMC, src: 0x00038200, des: 0x01700000, size: 0x00035a00
aml log : R2048 check pass!
Load bl33 from eMMC, src: 0x00070200, des: 0x01700000, size: 0x000aa200
aml log : R2048 check pass!
NOTICE:  BL3-1: v1.0(debug):fb68908
NOTICE:  BL3-1: Built : 18:30:11, Nov  1 2016
aml log : bl31 detect secure boot !
[Image: gxl_v1.1.3154-065f772 2016-09-29 14:08:54 yan.wang@droid05]

OPS=0x84

bc fc af 5f a2 b4 4d 4b 1c 91 59 9f [1.280536 Inits done]

secure task start!
high task start!
low task start!
INFO:    BL3-1: Initializing runtime services
INFO:    BL3-1: Initializing BL3-2
INFO:    BL3-2: ATOS-V1.5-g3e467d9 #1 Mon Aug 22 17:11:43 CST 2016 arm
INFO:    BL3-2: chip version = RevC (21:C - 0:0)
INFO:    BL3-2: crypto engine DMA
INFO:    BL3-2: secure time TEE
INFO:    BL3-1: Preparing for EL3 exit to normal world
INFO:    BL3-1: Next image address = 0x1000000
INFO:    BL3-1: Next image spsr = 0x3c9


U-Boot 2015.01 (Nov 23 2018 - 15:50:35)

DRAM:  1 GiB
Relocation Offset is: 36ec8000
register usb cfg[0][1] = 0000000037f5e258
[CANVAS]canvas init
vpu: error: vpu: check dts: FDT_ERR_BADMAGIC, load default parameters
vpu: clk_level = 7
vpu: set clk: 666667000Hz, readback: 666660000Hz(0x300)
vpp: vpp_init
boot_device_flag : 1
Nand PHY Ver:1.01.001.0006 (c) 2013 Amlogic Inc.
init bus_cycle=6, bus_timing=7, system=5.0ns
reset failed
get_chip_type and ret:fffffffe
get_chip_type and ret:fffffffe
chip detect failed and ret:fffffffe
nandphy_init failed and ret=0xfffffff1
MMC:   aml_priv->desc_buf = 0x0000000033ec86b0
aml_priv->desc_buf = 0x0000000033eca9d0
SDIO Port B: 0, SDIO Port C: 1
emmc/sd response timeout, cmd8, status=0x1ff2800
emmc/sd response timeout, cmd55, status=0x1ff2800
[mmc_startup] mmc refix success
[mmc_init] mmc init success
mmc read lba=0x14000, blocks=0x400
      Amlogic multi-dtb tool
      Multi dtb detected
      Multi dtb tool version: v2 .
      Support 2 dtbs.
        aml_dt soc: gxl platform: sx6b6x variant: 1g
        dtb 0 soc: gxl   plat: sx6b6x   vari: 1g
        dtb 1 soc: gxl   plat: sx6b6x   vari: 2g
      Find match dtb: 0
start dts,buffer=0000000033ecd270,dt_addr=0000000033ecda70
parts: 11
00:      logo	0000000002000000 1
01:  recovery	0000000002000000 1
02:       rsv	0000000000800000 1
03:       tee	0000000000800000 1
04:     crypt	0000000002000000 1
05:      misc	0000000002000000 1
06: instaboot	0000000020000000 1
07:      boot	0000000002000000 1
08:    system	0000000050000000 1
09:     cache	0000000040000000 2
10:      data	ffffffffffffffff 4
get_dtb_struct: Get emmc dtb OK!
overide_emmc_partition_table: overide cache 
[mmc_get_partition_table] skip partition cache.
Partition table get from SPL is : 
        name                        offset              size              flag
===================================================================================
   0: bootloader                         0            400000                  0
   1: reserved                     2400000           4000000                  0
   2: cache                        6c00000          40000000                  2
   3: env                         47400000            800000                  0
   4: logo                        48400000           2000000                  1
   5: recovery                    4ac00000           2000000                  1
   6: rsv                         4d400000            800000                  1
   7: tee                         4e400000            800000                  1
   8: crypt                       4f400000           2000000                  1
   9: misc                        51c00000           2000000                  1
  10: instaboot                   54400000          20000000                  1
  11: boot                        74c00000           2000000                  1
  12: system                      77400000          50000000                  1
  13: data                        c7c00000         10a400000                  4
mmc read lba=0x12000, blocks=0x2
mmc read lba=0x12002, blocks=0x2
mmc_read_partition_tbl: mmc read partition OK!
eMMC/TSD partition table have been checked OK!
mmc env offset: 0x47400000 
WARNING: 'recovery_from_sdcard' neither in running nor in imported env!
WARNING: 'recovery_from_udisk' neither in running nor in imported env!
In:    serial
Out:   serial
Err:   serial
hpd_state=0
cvbs performance type = 6, table = 0
[store]To run cmd[emmc dtb_read 0x1000000 0x40000]
read emmc dtb
      Amlogic multi-dtb tool
      Multi dtb detected
      Multi dtb tool version: v2 .
      Support 2 dtbs.
        aml_dt soc: gxl platform: sx6b6x variant: 1g
        dtb 0 soc: gxl   plat: sx6b6x   vari: 1g
        dtb 1 soc: gxl   plat: sx6b6x   vari: 2g
      Find match dtb: 0
Net:   dwmac.c9410000
wipe_data=successful
wipe_cache=successful
upgrade_step=2
[OSD]load fb addr from dts
[OSD]failed to get fb addr for logo
[OSD]use default fb_addr parameters
[OSD]fb_addr for logo: 0x3d800000
[OSD]load fb addr from dts
[OSD]failed to get fb addr for logo
[OSD]use default fb_addr parameters
[OSD]fb_addr for logo: 0x3d800000
[CANVAS]addr=0x3d800000 width=3840, height=2160
amlkey_init() enter!
[EFUSE_MSG]keynum is 4
[BL31]: tee size: 0
[KM]Error:f[key_manage_query_size]L507:key[deviceid] not programed yet
gpio: pin GPIOAO_2 (gpio 102) value is 1
get_cpu_id flag_12bit=1
SARADC channel(0) is 0x3e1.
SARADC closed.
Hit Enter or space or Ctrl+C key to stop autoboot -- :  0 
[imgread]szTimeStamp[2019121002280214]
[imgread]secureKernelImgSz=0x977000
aml log : R2048 check pass!
aml log : R2048 check pass!
aml log : R2048 check pass!
ee_gate_off ...
## Booting Android Image at 0x01080000 ...
reloc_addr =33f4d440
copy done
      Amlogic multi-dtb tool
      Single dtb detected
load dtb from 0x1000000 ......
   Uncompressing Kernel Image ... OK
   kernel loaded at 0x01080000, end = 0x02258fd0
   Loading Ramdisk to 33d12000, end 33eb6000 ... OK
   Loading Device Tree to 000000001fff3000, end 000000001ffff8f4 ... OK
signature: 
fdt_instaboot: no instaboot image

Starting kernel ...


Vale a pena notar que o próprio U-Boot (bl33) já estava em execução no ambiente do “mundo normal” (BL3-1 mudou o modo imediatamente antes de transferir o controle para ele). Essa. mesmo que de alguma forma assumamos o controle do U-Boot, teremos acesso limitado ao sistema. Em princípio, isso não é tão importante. Afinal, mesmo que você remova o dump da ROM, retire as chaves AES e abra o RSA do fusível, então não haverá grande sentido disso, porque ainda não há chave privada RSA.

O próprio U-Boot não leu nenhuma chave. Ele carregou o kernel na memória e chamou o Security Monitor para descriptografar e verificar o código. O Security Monitor fez todo o necessário e disse ao U-Boot para carregar o kernel ou não. Em geral, uma abordagem séria à proteção de software com seu próprio TrustedOS e algum tipo de funcionalidade como o BIOS.

Meu plano adicional era acessar a memória eMMC.

eMMC


Para conectar-se ao eMMC, era necessário encontrar pelo menos os pinos DAT_0, CLK, CMD e GND. E também descubra em que voltagem o controlador eMMC funcionou (1V8 ou 3V3). Era impossível fazer isso visualmente e, para rastrear trilhas, eu mesmo peguei o eMMC. Como o chip estava em minhas mãos, após o rastreamento, eu o conectei ao adaptador e joguei um despejo completo. Infelizmente, eu não tinha equipamento profissional e usei materiais improvisados ​​para isso. O resultado é um "Dead Bug".


Bem, na verdade a pinagem do conector:



Depois que a pinagem foi concluída, observei como o processador se comporta sem o eMMC. A julgar pelo log, a ROM após uma tentativa malsucedida de inicializar a partir do eMMC tentou carregar o código do cartão mSD. Isso foi encorajador. Carreguei rapidamente o despejo no cartão mSD e liguei o console. Uma pequena surpresa me esperava aqui. A ROM baixou o código BL2 do cartão e transferiu o controle para ele (isso significa que a seção "boot" no eMMC não estava envolvida e não havia necessidade de acesso root). Bem, quando chegou a vez do U-Boot, ele se queixou algumas vezes da falta de eMMC (dev 1) e, por um longo tempo, sem pensar, parou no terminal.

cmd store failed 
Err imgread(L132):Fail to read 0x100000B from part[recovery] at offset 0
gxl_sx6b6x_768_v2#version


U-Boot 2015.01 (Nov 23 2018 - 15:50:35)
aarch64-none-elf-gcc (crosstool-NG linaro-1.13.1-4.8-2013.11 - Linaro GCC 2013.10) 4.8.3 20131111 (prerelease)
GNU ld (crosstool-NG linaro-1.13.1-4.8-2013.11 - Linaro GCC 2013.10) 2.23.2.20130610 Linaro 2013.10-4
gxl_sx6b6x_768_v2#

Para começar, não foi nada mau. Após algumas experiências com o terminal, adicionei o parâmetro bootdelay = 5 à seção “env”, calculei a nova soma de verificação e soldou o eMMC de volta. Com a nova opção, eu esperava que o U-Boot pudesse ser interrompido. Mas, na prática, tudo foi diferente. Parece que o U-Boot não estava interessado nesse parâmetro e o processo de inicialização não foi diferente do normal. É triste porque era necessário um terminal com um eMMC conectado para outras ações. Com um pouco de reflexão, fechei o DAT_0 no chão e inseri meu cartão mSD. A ROM não pôde carregar o código do eMMC e passou para o mSD. Depois de carregar o U-Boot dessa maneira, abri os contatos e perguntei:

gxl_sx6b6x_768_v2#mmc dev 1

emmc/sd response timeout, cmd8, status=0x1ff2800
emmc/sd response timeout, cmd55, status=0x1ff2800
[mmc_startup] mmc refix success
[mmc_init] mmc init success
mmc read lba=0x14000, blocks=0x400
      Amlogic multi-dtb tool
      Multi dtb detected
      Multi dtb tool version: v2 .
      Support 2 dtbs.
        aml_dt soc: gxl platform: sx6b6x variant: 1g
        dtb 0 soc: gxl   plat: sx6b6x   vari: 1g
        dtb 1 soc: gxl   plat: sx6b6x   vari: 2g
      Find match dtb: 0
start dts,buffer=0000000033ee4050,dt_addr=0000000033ee4850
parts: 11
00:      logo	0000000002000000 1
01:  recovery	0000000002000000 1
02:       rsv	0000000000800000 1
03:       tee	0000000000800000 1
04:     crypt	0000000002000000 1
05:      misc	0000000002000000 1
06: instaboot	0000000020000000 1
07:      boot	0000000002000000 1
08:    system	0000000050000000 1
09:     cache	0000000040000000 2
10:      data	ffffffffffffffff 4
get_dtb_struct: Get emmc dtb OK!
overide_emmc_partition_table: overide cache 
[mmc_get_partition_table] skip partition cache.
Partition table get from SPL is : 
        name                        offset              size              flag
===================================================================================
   0: bootloader                         0            400000                  0
   1: reserved                     2400000           4000000                  0
   2: cache                        6c00000          40000000                  2
   3: env                         47400000            800000                  0
   4: logo                        48400000           2000000                  1
   5: recovery                    4ac00000           2000000                  1
   6: rsv                         4d400000            800000                  1
   7: tee                         4e400000            800000                  1
   8: crypt                       4f400000           2000000                  1
   9: misc                        51c00000           2000000                  1
  10: instaboot                   54400000          20000000                  1
  11: boot                        74c00000           2000000                  1
  12: system                      77400000          50000000                  1
  13: data                        c7c00000         10a400000                  4
mmc read lba=0x12000, blocks=0x2
mmc read lba=0x12002, blocks=0x2
mmc_read_partition_tbl: mmc read partition OK!
eMMC/TSD partition table have been checked OK!
switch to partitions #0, OK
mmc1(part 0) is current device
gxl_sx6b6x_768_v2#

O U-Boot não resistiu e passou para o eMMC. Eu olhei, é claro, o que estava no parâmetro bootdelay. E em vez dos meus cinco, vi 0. lá novamente.Parece que o U-Boot em algum momento anotou 0 lá, caso alguém de repente mude algo lá. Mas isso não me interessou mais e o tópico com o eMMC foi encerrado.

Nota: com uma pinagem do conector, é possível conectar ao eMMC sem soldar o chip. Para fazer isso, você precisa de um adaptador especial com um conversor de tensão, porque O controlador eMMC é executado em 1V8 e se você conectar um adaptador SD comum a 3V3, existe o risco de queimar componentes no barramento 1V8.

Também será necessário remover esse resistor, caso contrário, o processador irá interferir no adaptador.


Componentes ausentes


Tendo acesso total ao terminal U-Boot, tive que fazer duas coisas: acessar o decodificador DeviceTree e convencer o U-Boot a recusar os serviços do Monitor de segurança relacionados à verificação do kernel. Para o primeiro lançamento, seria bom ter o kernel original, para não perder tempo depurando um novo.

Foi extremamente fácil obter o DeviceTree. Eu perguntei:

gxl_sx6b6x_768_v2#emmc dtb_read 0x1000000 0x40000

read emmc dtb
gxl_sx6b6x_768_v2#

e ele estava no meu bolso.

O U-Boot exigiu uma análise detalhada. No log, seguiu-se que o próprio U-Boot foi carregado e descriptografado inicialmente em 0x1000000 e, posteriormente, se transferiu para 0x36ES8000 (deslocamento). Despejei o U-Boot e o analisei na IDA.

Obviamente, eu estava interessado no local em que o Monitor de Segurança foi acessado a partir do comando bootm. Aqui é


onde
X0 - AML_D_P_IMG_DECRYPT
X1 - nLoadAddr
X2 - GXB_IMG_SIZE
X3 - GXB_IMG_DEC_ALL

Para remover o despejo original do kernel, você teve que carregá-lo na memória através da função imgread e modificar o bootm para que, imediatamente após chamar aml_sec_boot_check, a memória fosse emitida a partir do endereço 0x1080000 para o terminal (essa certamente não é a única maneira). Para fazer isso, escrevi um pedaço de código e o baixei no lugar certo. Aqui está o que aconteceu (é claro, não posso fornecer um log completo):

gxl_sx6b6x_768_v2#imgread kernel boot

[imgread]szTimeStamp[2019121002280214]
[imgread]secureKernelImgSz=0x977000
gxl_sx6b6x_768_v2#bootm

aml log : R2048 check pass!
aml log : R2048 check pass!
aml log : R2048 check pass!

Ready for dumping kernel

41 4e 44 52 4f 49 44 21 20 d8 7b 20 20 20 08 01  | ANDROID!

Além do kernel, também obtive o ramdisk (pode ser útil caso haja drivers ou firmware importantes, por exemplo, para WiFi).

Eu não sou mais Android


Para o primeiro lançamento do meu software, criei o uImage a partir do kernel original, construí meu rootfs com base no Busybox e usei meu próprio dtb. Carreguei todas as três partes diretamente da unidade USB e executei o comando “bootm”, desativando a descriptografia e a verificação de imagens antes.

gxl_sx6b6x_768_v2#usb start
(Re)start USB...
USB0:   USB3.0 XHCI init start
Register 2000140 NbrPorts 2
Starting the controller
USB XHCI 1.00
scanning bus 0 for devices... 2 USB Device(s) found
       scanning usb for storage devices... 1 Storage Device(s) found
gxl_sx6b6x_768_v2#mw.l 0x37ed240c 0xd2800000
gxl_sx6b6x_768_v2#fatload usb 0:1 0x1000000 dtb.img
reading dtb.img
40960 bytes read in 43 ms (929.7 KiB/s)
gxl_sx6b6x_768_v2#fatload usb 0:1 0x2000000 uImage
reading uImage
8116288 bytes read in 4197 ms (1.8 MiB/s)
gxl_sx6b6x_768_v2#fatload usb 0:1 0x3000000 rootfs.img.uboot
reading rootfs.img.uboot
1041462 bytes read in 563 ms (1.8 MiB/s)
gxl_sx6b6x_768_v2#bootm 0x2000000 0x3000000 0x1000000

ee_gate_off ...
## Booting kernel from Legacy Image at 02000000 ...
   Image Name:   S905X Original
   Image Type:   AArch64 Linux Kernel Image (gzip compressed)
   Data Size:    8116224 Bytes = 7.7 MiB
   Load Address: 01080000
   Entry Point:  01080000
   Verifying Checksum ... OK
## Loading init Ramdisk from Legacy Image at 03000000 ...
   Image Name:   Root Filesystem
   Image Type:   AArch64 Linux RAMDisk Image (gzip compressed)
   Data Size:    1041398 Bytes = 1017 KiB
   Load Address: 033d1200
   Entry Point:  033d1200
   Verifying Checksum ... OK
      Amlogic multi-dtb tool
      Single dtb detected
load dtb from 0x1000000 ......
## Flattened Device Tree blob at 01000000
   Booting using the fdt blob at 0x1000000
   Uncompressing Kernel Image ... OK
   kernel loaded at 0x01080000, end = 0x02258fd0
   Loading Ramdisk to 33db8000, end 33eb63f6 ... OK
   Loading Device Tree to 000000001fff3000, end 000000001ffff8f4 ... OK
fdt_instaboot: no instaboot image

Starting kernel ...

uboot time: 136710682 us
[    0.000000@0] Initializing cgroup subsys cpu
[    0.000000@0] Initializing cgroup subsys cpuacct
[    0.000000@0] Linux version 3.14.29 (build@build2) (gcc version 4.9.2 20140904 (prerelease) (crosstool-NG linaro-1.13.1-4.9-2014.09 - Linaro GCC 4.9-2014.09) ) #1 SMP PREEMPT Thu Sep 12 21:24:53 MSK 2019
[    0.000000@0] CPU: AArch64 Processor [410fd034] revision 4

[    6.302659@2] meson_uart c81004c0.serial: ttyS0 use xtal(8M) 24000000 change 115200 to 115200
# cat /proc/cpuinfo
Processor	: AArch64 Processor rev 4 (aarch64)
processor	: 0
processor	: 1
processor	: 2
processor	: 3
Features	: fp asimd evtstrm aes pmull sha1 sha2 crc32 wp half thumb fastmult vfp edsp neon vfpv3 tlsi vfpv4 idiva idivt 
CPU implementer	: 0x41
CPU architecture: 8
CPU variant	: 0x0
CPU part	: 0xd03
CPU revision	: 4

Hardware	: Amlogic
Serial		: 210c84009f59911c4b4db4a25faffcbc
#

Fuga de presos


Devido ao fato de o U-Boot ter sido imunizado contra a alteração dos parâmetros env (isso envolvia não apenas o "bootdelay"), era impossível influenciar o processo de inicialização por meio do env e, para carregar seu software, o prefixo precisava ser conectado ao computador. Esta opção não combina comigo. Tendo analisado toda a cadeia de carregamento, este comando chamou minha atenção:

init_display=osd open;osd clear;imgread pic logo bootup $loadaddr;bmp display $bootup_offset;bmp scale

em particular:

imgread pic logo bootup $loadaddr

onde o U-Boot estava carregando um determinado recurso de "inicialização" no endereço loadaddr = 0x1080000. O recurso em si foi descrito por essa estrutura:

struct resource_header{
	unsigned int 	magic;		/* Image Header Magic Number	*/
	unsigned int 	hcrc;		/* Image Header CRC Checksum	*/
	unsigned int	size;		/* Image Data Size		*/
	unsigned int	start;		/* item data offset in the image*/
	unsigned int	end;		/* Entry Point Address		*/
	unsigned int	next;		/* Next item head offset in the image*/
	unsigned int	dcrc;		/* Image Data CRC Checksum	*/
	unsigned char	index;		/* Operating System		*/
	unsigned char	nums;		/* CPU architecture		*/
	unsigned char   type;		/* Image Type			*/
	unsigned char 	comp;		/* Compression Type		*/
	char 	name[32];		/* Image Name			*/
}

Obviamente, os parâmetros "size" e "start" eram interessantes. Continuando com eles e também com o parâmetro "loadaddr", o U-Boot resolveu três novos parâmetros para leitura direta no eMMC. Idealmente, é claro, ele baixou uma imagem da seção "logo" em 0x000B00C0 na memória em 0x1130000 ... Acho que o curso de meus pensamentos agora está claro. Resolvi novos parâmetros "size" e "start" e escrevi meu código, que foi salvo no eMMC. Após essas manipulações, o U-Boot não estava mais lendo uma imagem, mas uma exploração, que imediatamente ganhou controle. A exploração consistiu em várias linhas no assembler.

LDR X21, printf
ADR X0, .message
BLR X21

LDR X21, run_command
ADR X0, .command
MOV X1,#0x0
BLR X21

.align 4
printf: .quad 0x37EE50A0
.align 4
run_command: .quad 0x37EE9BA0

.align 4
.message: .string "\nJailbreaking BL3-3...\n"
.align 4
.command: .string "fatload mmc 0:1 0x1000000 uboot.bin; go 0x1000000"


Ele leu o uboot.bin na primeira seção do cartão mSD e transferiu o controle para ele (o uboot.bin era um U-Boot não criptografado recentemente coletado. É claro que era possível usar um modificado nativo). Acontece que o processo de inicialização retornou ao local em que o BL3-1 descriptografou o U-Boot original e transferiu o controle para ele. Somente dessa vez, o código não assinado já estava em execução. E agora o download do eMMS ficou assim (o último fragmento):

Hit Enter or space or Ctrl+C key to stop autoboot -- :  0

Jailbreaking BL3-3...
card in
[mmc_init] mmc init success
reading uboot.bin
408579 bytes read in 28 ms (13.9 MiB/s)
## Starting application at 0x01000000 ...


U-Boot 2017.11-02414-g9b5924abf2-dirty (Mar 01 2020 - 22:17:58 +0100) p212

DRAM:  1 GiB
MMC:   mmc@72000: 0, mmc@74000: 1
reading uboot.env
In:    serial@4c0
Out:   serial@4c0
Err:   serial@4c0
[BL31]: tee size: 0
[BL31]: tee size: 0
Net:   
Warning: ethernet@c9410000 (eth0) using random MAC address - 22:10:89:5b:74:85
eth0: ethernet@c9410000
Hit any key to stop autoboot:  2 0
=> version
U-Boot 2017.11-02414-g9b5924abf2-dirty (Mar 01 2020 - 22:17:58 +0100) p212

aarch64-elf-gcc (Linaro GCC 7.2-2017.11) 7.2.1 20171011
GNU ld (Linaro_Binutils-2017.11) 2.28.2.20170706
=> 

Conclusão


Para que o prefixo não fique ocioso na prateleira, decidi colocar o LibreElec nele. Imagem recém montada lançada quase imediatamente sem problemas. O kernel foi finalizado com um pequeno arquivo, os drivers para WiFi e o controle remoto foram instalados e a função de desligamento foi refeita. E tudo funcionou bem, mas lembrei que o console também suporta Bluetooth, que naturalmente não funcionava no LibreElec. Embora eu não precisasse, ainda decidi configurá-lo para complementar a imagem.
A bordo estava o chip AP6255 da Ampak, responsável por WiFi e Bluetooth. O UART Bluetooth estava conectado ao ttyS1, mas o chip não respondeu a nenhum comando HCI e fingiu estar morto. Além disso, no núcleo nativo, o chip, como esperado, respondeu à equipe.
A documentação para esse chip é muito ruim e tudo o que pode ser extraído de lá é uma pinagem. Antes de tudo, verifiquei a potência do chip e o pino BT_WAKE. Tudo estava normal. Tendo experimentado o próprio driver e a porta ttyS1, não obtive nenhum resultado - o chip ficou silencioso como partidário e eu liguei um osciloscópio a ele. Nele, verifiquei e comparei todos os sinais eletrônicos UART (RTS, TXD, RXD, CTS). Tudo estava normal. Em seguida, verifiquei a sequência de redefinição, que é controlada via rfkill (esses eram os pinos BT_WAKE e BT_REGON). Mas aqui estava tudo bem. Depois verifiquei o pino do LPO, onde, de acordo com a documentação, um sinal com frequência de 32.768KHz deveria entrar, mas mesmo aqui vi um sinal no osciloscópio. Em geral, tudo estava em ordem, mas o chip não funcionou com o meu núcleo. Depois de passar mais alguns dias desmontando o driver UART original, voltei ao sinal LPO e medi sua frequência.O resultado mostrou 26KHz. Ah, como.
O driver wifi_dt foi responsável por esse sinal, que no meu núcleo não gerou corretamente a frequência. Desmontei o driver original e assumi a inicialização do sinal pwm de lá e ... o chip ganhou vida (mais tarde, encontrei uma versão desse driver com o sinal correto). E assim, o chip estava pronto para mais ajustes, mas eu não tinha ideia de como colocá-lo em alerta, porque Não encontrei nenhum driver / firmware / documentação para ele. No Android original, não havia nada no log do kernel, exceto rfkill ao trabalhar com Bluetooth. Isso é compreensível, porque não havia driver do kernel e o lançamento ocorreu no nível do usuário. Era necessário, de alguma forma, acessar o log do Android e, para isso, era necessário o acesso root ao dispositivo. Para fazer isso, na minha ingenuidade, adicionei as configurações necessárias à seção do sistema e ativei o adb.Mas com esse cenário, o Android percebeu que algo estava errado e se recusou a começar, referindo-se a algumas manipulações por aí ... Bem, não, não. Eu restaurei a partição do sistema e refiz o rootfs simplesmente incluindo sh lá. Após o lançamento subsequente, eu tive acesso root no terminal.
Foi assim que o chip foi inicializado.

5759  5781 I bt_hci_h4: hal_open
5759  5781 I bt_userial_vendor: userial vendor open: opening /dev/ttyS1
5759  5781 E bt_userial_vendor: userial vendor open success!!
5759  5781 I bt_userial_vendor: device fd = 52 open
5759  5781 I bt_hwcfg: bt vendor lib: set UART baud 2000000
5759  5781 I bt_hwcfg: FW prepatch file: /etc/bluetooth/4335/bcm4335_prepatch.hcd
5759  5781 I bt_hwcfg: bt vendor lib: loading prepatch /etc/bluetooth/4335/bcm4335_prepatch.hcd
5759  5781 D bt_hwcfg: Chipset BCM4335A0
5759  5781 D bt_hwcfg: Target name = [BCM4335A0]
5759  5781 I bt_hwcfg: FW patchfile: /etc/bluetooth/4335/bcm4335.hcd
5759  5781 I bt_hwcfg: bt vendor lib: set UART baud 115200
5759  5781 D bt_hwcfg: Settlement delay -- 200 ms
5759  5781 I bt_hwcfg: Setting fw settlement delay to 200 
5759  5781 I bt_hwcfg: bt vendor lib: set UART baud 2000000
5759  5781 I bt_hwcfg: Setting local bd addr to 22:22:99:F7:B6:BD
5759  5781 I bt_hwcfg: vendor lib fwcfg completed


Esta informação foi suficiente para escrever um programa que fez o mesmo. O último passo foi iniciar o hciattach e o LibreElec reconheceu o Bluetooth corretamente. Agora o dispositivo foi totalmente configurado. Se alguém estiver interessado, aqui está a imagem final.

All Articles