User:Kmeisthax/Findings/2012/2/4/Malias2 Listing
< User:Kmeisthax | Findings
This is a listing of the disassembly for Malias2 Compression, marked up and annotated by me.
ROM:0811E39C ; ---------------------------------------------------------------------------
ROM:0811E39C CODE16
ROM:0811E39C
ROM:0811E39C DeCompress
ROM:0811E39C PUSH {R4,LR}
ROM:0811E39E ADDS R3, R0, #0 ; R3: Compression Source
ROM:0811E3A0 ADDS R4, R1, #0 ; R4: Decompression Destination
ROM:0811E3A2 LDRB R0, [R3]
ROM:0811E3A4 CMP R0, #0x4C
ROM:0811E3A6 BNE DeCompress_NoMagic ; ret false
ROM:0811E3A8 LDRB R0, [R3,#1]
ROM:0811E3AA CMP R0, #0x65
ROM:0811E3AC BEQ DeCompress_MagicValid ; test for magic bytes 4C 65
ROM:0811E3AE
ROM:0811E3AE DeCompress_NoMagic ; CODE XREF: ROM:0811E3A6�j
ROM:0811E3AE MOVS R0, #0 ; ret false
ROM:0811E3B0 B DeCompress_Return
ROM:0811E3B2 ; ---------------------------------------------------------------------------
ROM:0811E3B2
ROM:0811E3B2 DeCompress_MagicValid ; CODE XREF: ROM:0811E3AC�j
ROM:0811E3B2 LDR R0, =0xFBFFFFFF
ROM:0811E3B4 ADDS R1, R4, R0 ; R1 = R4 - 0x4000001
ROM:0811E3B6 LDR R0, =0x3FFFFFE
ROM:0811E3B8 CMP R1, R0
ROM:0811E3BA BLS DeCompress_ToVolatile ; branch if (R4 - 0x4000001) <= 0x3FFFFFE
ROM:0811E3BA ; (if memory location in I/Oregs, palram, vram, or oam)
ROM:0811E3BC LDRB R2, [R3,#2]
ROM:0811E3BE LDRB R0, [R3,#3]
ROM:0811E3C0 LSLS R0, R0, #8
ROM:0811E3C2 ORRS R2, R0 ; unaligned little-endian 16 bit read
ROM:0811E3C4 LDRB R0, [R3,#4]
ROM:0811E3C6 LSLS R0, R0, #0x10
ROM:0811E3C8 ORRS R2, R0 ; unaligned little-endian 24-bit read
ROM:0811E3CA ADDS R0, R3, #0
ROM:0811E3CC ADDS R1, R4, #0 ; Size (32-bit align, 24-bits used)
ROM:0811E3CE BL DecompCore ; call(CmpSrc, CmpDst, Size)
ROM:0811E3D2 B DeCompress_Return
ROM:0811E3D2 ; ---------------------------------------------------------------------------
ROM:0811E3D4 dword_811E3D4 DCD 0xFBFFFFFF ; DATA XREF: ROM:DeCompress_MagicValid�r
ROM:0811E3D8 dword_811E3D8 DCD 0x3FFFFFE ; DATA XREF: ROM:0811E3B6�r
ROM:0811E3DC ; ---------------------------------------------------------------------------
ROM:0811E3DC
ROM:0811E3DC DeCompress_ToVolatile ; CODE XREF: ROM:0811E3BA�j
ROM:0811E3DC ADDS R0, R3, #0
ROM:0811E3DE ADDS R1, R4, #0
ROM:0811E3E0 BL VolatileDeComp ; It's just DeCompCore, retasked to only do
ROM:0811E3E0 ; 16-bit reads and writes, i.e. it RMWs all over
ROM:0811E3E0 ; the place.
ROM:0811E3E4
ROM:0811E3E4 DeCompress_Return ; CODE XREF: ROM:0811E3B0�j
ROM:0811E3E4 ; ROM:0811E3D2�j
ROM:0811E3E4 POP {R4}
ROM:0811E3E6 POP {R1}
ROM:0811E3E8 BX R1
ROM:0811E3E8 ; ---------------------------------------------------------------------------
ROM:0811E3EA DCB 0
ROM:0811E3EB DCB 0
ROM:0811E3EC
ROM:0811E3EC ; =============== S U B R O U T I N E =======================================
ROM:0811E3EC
ROM:0811E3EC
ROM:0811E3EC DecompCore ; CODE XREF: ROM:0811E3CE�p
ROM:0811E3EC PUSH {R4-R7,LR}
ROM:0811E3EE MOV R7, R10
ROM:0811E3F0 MOV R6, R9
ROM:0811E3F2 MOV R5, R8
ROM:0811E3F4 PUSH {R5-R7} ; preamble: using R4-R10
ROM:0811E3F6 MOV R10, R2 ; R10: Size
ROM:0811E3F8 MOV R7, R10
ROM:0811E3FA ADDS R3, R1, #0 ; R3: Decompression Destination
ROM:0811E3FC ADDS R4, R0, #6 ; R4: Compression Source + 6
ROM:0811E3FE MOV R0, R10
ROM:0811E400 CMP R0, #0
ROM:0811E402 BEQ DecompCore_Return
ROM:0811E404
ROM:0811E404 DecompCore_ExecuteBundle ; CODE XREF: DecompCore+F4�j
ROM:0811E404 LDRB R5, [R4] ; R5: Current bundle command list
ROM:0811E406 ADDS R4, #1
ROM:0811E408 MOVS R6, #0 ; R6: Number of commands in current bundle
ROM:0811E40A CMP R7, #0
ROM:0811E40C BEQ DecompCore_Return
ROM:0811E40E MOVS R1, #3
ROM:0811E410 MOV R9, R1 ; R9=+3
ROM:0811E412 MOVS R2, #1
ROM:0811E414 NEGS R2, R2
ROM:0811E416 MOV R8, R2 ; R8=-1 or 0xFFFFFFFF
ROM:0811E418
ROM:0811E418 DecompCore_ExecuteCmd ; CODE XREF: DecompCore+F0�j
ROM:0811E418 ADDS R0, R5, #0
ROM:0811E41A MOV R1, R9
ROM:0811E41C ANDS R0, R1 ; *CmpSrc & 3
ROM:0811E41E CMP R0, #1
ROM:0811E420 BEQ DecompCore_Mode1 ; Mode 1
ROM:0811E422 CMP R0, #1
ROM:0811E424 BGT DecompCore_UncompressedModes
ROM:0811E426 CMP R0, #0
ROM:0811E428 BEQ DecompCore_Mode0 ; Mode 0
ROM:0811E42A B DecompCore_Mode23_End ; You just &ed this with 3.
ROM:0811E42A ; There is no way to reach this code.
ROM:0811E42A ; What the hell compiled this swill?!
ROM:0811E42C ; ---------------------------------------------------------------------------
ROM:0811E42C
ROM:0811E42C DecompCore_UncompressedModes ; CODE XREF: DecompCore+38�j
ROM:0811E42C CMP R0, #2
ROM:0811E42E BEQ DecompCore_Mode2 ; Mode 2
ROM:0811E42E ; Copy 1 uncompressed byte.
ROM:0811E430 CMP R0, #3
ROM:0811E432 BEQ DecompCore_Mode3 ; Mode 3
ROM:0811E432 ; Copy 3 uncompressed bytes.
ROM:0811E434 B DecompCore_Mode23_End ; ANOTHER UNREACHABLE BRANCH
ROM:0811E434 ; MAYBE YOU WOULDN'T NEED COMPRESSION
ROM:0811E434 ; IF YOUR COMPILER ACTUALLY DID DEAD
ROM:0811E434 ; CODE ELIMINATION
ROM:0811E436 ; ---------------------------------------------------------------------------
ROM:0811E436
ROM:0811E436 DecompCore_Mode0 ; CODE XREF: DecompCore+3C�j
ROM:0811E436 LDRB R1, [R4] ; LZ77 copy operation.
ROM:0811E436 ;
ROM:0811E436 ; The following 2 bytes are interpreted as a little
ROM:0811E436 ; endian value. The low 12 bits are an offset from the
ROM:0811E436 ; current copy head. The high 4 are the number of bytes
ROM:0811E436 ; to copy, minus four. Bytes will be copied from the
ROM:0811E436 ; offset to the output, byte-by-byte.
ROM:0811E438 LDRB R0, [R4,#1]
ROM:0811E43A LSLS R0, R0, #8
ROM:0811E43C ADDS R1, R1, R0
ROM:0811E43E ADDS R4, #2
ROM:0811E440 LDR R0, =0xFFF
ROM:0811E442 ANDS R0, R1
ROM:0811E444 ADDS R0, #5
ROM:0811E446 SUBS R2, R3, R0 ; CopySrc = Dest - (*((uint_16*)Src) & 0xFFF + 5)
ROM:0811E448 LSRS R0, R1, #0xC
ROM:0811E44A ADDS R1, R0, #3
ROM:0811E44C SUBS R7, R7, R1 ; BytesLeft -= *((uint_16*)Src) >> 12 + 3
ROM:0811E44E ADDS R1, R0, #2 ; CopyLen = *((uint_16*)Src) >> 12 + 2
ROM:0811E450 ADDS R6, #1
ROM:0811E452 LSRS R5, R5, #2 ; grab next command
ROM:0811E454 CMP R1, R8
ROM:0811E456 BEQ DecompCore_LoopPostamble ; if (CopyLen == -1) break
ROM:0811E458 MOVS R0, #1
ROM:0811E45A NEGS R0, R0
ROM:0811E45C MOV R12, R0 ; R12 = -1
ROM:0811E45C ; WTF I THOUGHT YOU ALREADY HAD ANOTHER
ROM:0811E45C ; REGISTER WITH THIS CONSTANT IN IT
ROM:0811E45C ; WHY ARE YOU REMATERIALIZING IT HERE
ROM:0811E45E
ROM:0811E45E DecompCore_Mode0CopyLoop ; CODE XREF: DecompCore+7E�j
ROM:0811E45E LDRB R0, [R2]
ROM:0811E460 STRB R0, [R3]
ROM:0811E462 ADDS R2, #1
ROM:0811E464 ADDS R3, #1
ROM:0811E466 SUBS R1, #1
ROM:0811E468 CMP R1, R12
ROM:0811E46A BNE DecompCore_Mode0CopyLoop
ROM:0811E46C B DecompCore_LoopPostamble
ROM:0811E46C ; ---------------------------------------------------------------------------
ROM:0811E46E DCB 0
ROM:0811E46F DCB 0
ROM:0811E470 dword_811E470 DCD 0xFFF ; DATA XREF: DecompCore+54�r
ROM:0811E474 ; ---------------------------------------------------------------------------
ROM:0811E474
ROM:0811E474 DecompCore_Mode1 ; CODE XREF: DecompCore+34�j
ROM:0811E474 LDRB R1, [R4] ; LZ77 copy operation.
ROM:0811E474 ;
ROM:0811E474 ; The following byte is read. The low 2 bits are an
ROM:0811E474 ; offset from the current copy head minus one. The
ROM:0811E474 ; high 6 are the number of bytes to copy, minus three.
ROM:0811E474 ; Bytes will be copied from the offset to the output,
ROM:0811E474 ; byte-by-byte.
ROM:0811E476 ADDS R4, #1
ROM:0811E478 ADDS R0, R1, #0
ROM:0811E47A MOV R2, R9 ; +3
ROM:0811E47C ANDS R0, R2
ROM:0811E47E ADDS R0, #1
ROM:0811E480 SUBS R2, R3, R0 ; CopySrc = Dest - (*Src & 3 + 1)
ROM:0811E482 LSRS R0, R1, #2
ROM:0811E484 ADDS R1, R0, #2
ROM:0811E486 SUBS R7, R7, R1 ; BytesLeft -= *Src >> 2 + 2
ROM:0811E488 ADDS R1, R0, #1 ; CopyLen = *Src >> 2 + 1
ROM:0811E48A ADDS R6, #1
ROM:0811E48C LSRS R5, R5, #2 ; grab next command
ROM:0811E48E CMP R1, R8
ROM:0811E490 BEQ DecompCore_LoopPostamble
ROM:0811E492 MOVS R0, #1
ROM:0811E494 NEGS R0, R0
ROM:0811E496 MOV R12, R0 ; another rematerialization of R8
ROM:0811E496 ; THIS WAS WHY RISC WAS INVENTED
ROM:0811E496 ;
ROM:0811E496 ; MORANS
ROM:0811E498
ROM:0811E498 DecompCore_Mode1CopyLoop ; CODE XREF: DecompCore+B8�j
ROM:0811E498 LDRB R0, [R2]
ROM:0811E49A STRB R0, [R3]
ROM:0811E49C ADDS R2, #1
ROM:0811E49E ADDS R3, #1
ROM:0811E4A0 SUBS R1, #1
ROM:0811E4A2 CMP R1, R12
ROM:0811E4A4 BNE DecompCore_Mode1CopyLoop
ROM:0811E4A6 B DecompCore_LoopPostamble
ROM:0811E4A8 ; ---------------------------------------------------------------------------
ROM:0811E4A8
ROM:0811E4A8 DecompCore_Mode3 ; CODE XREF: DecompCore+46�j
ROM:0811E4A8 LDRB R0, [R4]
ROM:0811E4AA STRB R0, [R3]
ROM:0811E4AC ADDS R4, #1
ROM:0811E4AE ADDS R3, #1
ROM:0811E4B0 LDRB R0, [R4]
ROM:0811E4B2 STRB R0, [R3]
ROM:0811E4B4 ADDS R4, #1
ROM:0811E4B6 ADDS R3, #1
ROM:0811E4B8 LDRB R0, [R4]
ROM:0811E4BA STRB R0, [R3]
ROM:0811E4BC ADDS R4, #1
ROM:0811E4BE ADDS R3, #1
ROM:0811E4C0 SUBS R7, #3 ; for (int i = 0; i < 3; i++)
ROM:0811E4C0 ; *Dest++ = *CmpSrc++
ROM:0811E4C0 ;
ROM:0811E4C0 ; Size -= 3
ROM:0811E4C2 B DecompCore_Mode23_End
ROM:0811E4C4 ; ---------------------------------------------------------------------------
ROM:0811E4C4
ROM:0811E4C4 DecompCore_Mode2 ; CODE XREF: DecompCore+42�j
ROM:0811E4C4 LDRB R0, [R4]
ROM:0811E4C6 STRB R0, [R3]
ROM:0811E4C8 ADDS R4, #1
ROM:0811E4CA ADDS R3, #1
ROM:0811E4CC SUBS R7, #1
ROM:0811E4CE
ROM:0811E4CE DecompCore_Mode23_End ; CODE XREF: DecompCore+3E�j
ROM:0811E4CE ; DecompCore+48�j ...
ROM:0811E4CE ADDS R6, #1
ROM:0811E4D0 LSRS R5, R5, #2 ; Grab next command
ROM:0811E4D2
ROM:0811E4D2 DecompCore_LoopPostamble ; CODE XREF: DecompCore+6A�j
ROM:0811E4D2 ; DecompCore+80�j ...
ROM:0811E4D2 LSLS R0, R5, #0x18
ROM:0811E4D4 LSRS R5, R0, #0x18 ; WTF THIS DOES NOTHING WHY DO YOU HAVE IT HERE
ROM:0811E4D6 CMP R6, #3 ; Number of commands read in bundle
ROM:0811E4D8 BHI DecompCore_LoopPostamble2
ROM:0811E4DA CMP R7, #0
ROM:0811E4DC BNE DecompCore_ExecuteCmd
ROM:0811E4DE
ROM:0811E4DE DecompCore_LoopPostamble2 ; CODE XREF: DecompCore+EC�j
ROM:0811E4DE CMP R7, #0
ROM:0811E4E0 BNE DecompCore_ExecuteBundle ; R5: Current bundle command list
ROM:0811E4E2
ROM:0811E4E2 DecompCore_Return ; CODE XREF: DecompCore+16�j
ROM:0811E4E2 ; DecompCore+20�j
ROM:0811E4E2 MOV R0, R10
ROM:0811E4E4 POP {R3-R5}
ROM:0811E4E6 MOV R8, R3
ROM:0811E4E8 MOV R9, R4
ROM:0811E4EA MOV R10, R5
ROM:0811E4EC POP {R4-R7}
ROM:0811E4EE POP {R1}
ROM:0811E4F0 BX R1
ROM:0811E4F0 ; End of function DecompCore
ROM:0811E4F0
ROM:0811E4F0 ; ---------------------------------------------------------------------------
ROM:0811E4F2 DCB 0
ROM:0811E4F3 DCB 0
ROM:0811E4F4
ROM:0811E4F4 ; =============== S U B R O U T I N E =======================================
ROM:0811E4F4
ROM:0811E4F4 ; It's just DeCompCore, retasked to only do
ROM:0811E4F4 ; 16-bit reads and writes, i.e. it RMWs all over
ROM:0811E4F4 ; the place.
ROM:0811E4F4
ROM:0811E4F4 VolatileDeComp ; CODE XREF: ROM:0811E3E0�p