⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 memory.asm

📁 十七种模拟器源代码 非常有用的作课程设计不可缺少的
💻 ASM
📖 第 1 页 / 共 5 页
字号:

    mov esi,[C4Ram]
    mov dword[C4count],8
    mov cl,[esi+626h]
    mov byte[C4sprites],cl
    mov ecx,[C4sprites]
    shl ecx,2
    mov dword[C4ObjDisp],ecx
    mov ecx,128
;    cmp byte[esi+65],50h
;    jne .noincdisp
    mov dword[C4count],32
    sub ecx,[C4sprites]
.noincdisp
    add esi,[C4ObjDisp]
    ; Clear OAM to-be ram
.next
    mov byte[esi+1],0E0h
    add esi,4
    dec ecx
    jnz .next

    call C4ConvOAM

    pop edx
    pop ebx
    pop edi
    pop esi
    pop ecx
    ret

NEWSYM SprValAdd, db 0
C4Data dd 0
C4sprites dd 0
OBClog dd 0
NumSprites db 0
OBCOldRegArray db 0

NEWSYM InitOBC
    pushad
    mov esi,[romdata]
    add esi,4096*1024
    mov [C4RamR],esi
    mov [C4RamW],esi
    mov [C4Ram],esi
    add dword[C4RamW],8192*4
    add dword[C4Ram],8192*8
    mov ecx,8192
.c4loop
    mov dword[esi],OBCReadReg
    mov dword[esi+8192*4],OBCWriteReg
    mov dword[esi+8192*8],0
    add esi,4
    dec ecx
    jnz .c4loop
    mov esi,[romdata]
    add esi,4096*1024
    mov dword[esi+3A1Eh*4],OBCClear
    mov dword[esi+3FF0h*4],OBCRegs
    mov dword[esi+3FF1h*4],OBCRegs
    mov dword[esi+3FF2h*4],OBCRegs
    mov dword[esi+3FF3h*4],OBCRegs
    mov dword[esi+3FF4h*4],OBCRegs
    mov dword[esi+3FF5h*4],OBCRegs
    mov dword[esi+3FF6h*4],OBCRegs
    mov dword[esi+3FF7h*4],OBCRegs
    popad
    ret

OBCSprites:
    pushad
    mov byte[NumSprites],0
    mov esi,[C4Ram]
    mov edi,esi
    add edi,1800h
    add byte[OBCRegArray],2
    and byte[OBCRegArray],0FEh
    cmp byte[OBCRegArray],0FEh
    je .ohno
    cmp byte[OBCRegArray],0
    je .ohno
    jmp .okay
.ohno
    mov al,[OBCOldRegArray]
    mov [OBCRegArray],al
    jmp .loop
.okay
    mov al,[OBCRegArray]
    mov [OBCOldRegArray],al
.loop
    cmp byte[OBCRegArray],0
    je .nomore
    sub byte[OBCRegArray],2
    xor ebx,ebx
    mov bl,[esi+6]
    shl ebx,2

    ; Get X,Y,OAM, and Attr
    mov al,[esi+3]         ;0,3
    mov [edi+ebx],al
    mov al,[esi+9]
    mov [edi+ebx+1],al
    mov al,[esi+10]       ;2,10
    mov [edi+ebx+2],al
    mov al,[esi+0Bh]
    mov byte[edi+ebx+3],al

    xor ebx,ebx
    mov bl,[esi+6]
    shr ebx,2
    add ebx,512
    mov cl,[esi+6]
    and cl,03h
    add cl,cl

    xor al,al
    mov ah,0FCh
    mov al,byte[esi+4]   ;1,4
    and al,03h
    shl al,cl
    rol ah,cl
    and byte[edi+ebx],ah
    or byte[edi+ebx],al

    inc byte[NumSprites]
    add esi,16
    jmp .loop
.nomore

    mov esi,[C4Ram]
    mov edi,esi
    add edi,1800h
;    mov dword[edi+200h],0AAAAAAAAh
    popad
    ret

OBCClear:
    call OBCSprites
    mov byte[clearmem],1
    mov dword[OBClog],0
    ret

; Affected values: 0,1,2,3,4,6,7,9,A,B
; 0,1 - Another X value (unused?)
; 2   - OAM value
; 3/4 - X value (bits 0-8)
; 5   - N/A (not written to)
; 6   - OAM #
; 7   - Always 0?
; 9   - Y value (bits 0-7)
; A   - OAM value
; B   - OAM Status
; X,Y,OAM,Attr / xhighbit / OAM highbit / Sprite size
;bit 0 = OAM b8, bit 1-3 = palette number bit 4,5 = playfield priority
;bit 6   = horizontal flip bit 7   = horizonal flip
; Extra: bit 0 = X bit 8, bit 1 = Larger sprite size

OBCRegArray times 8 db 0
OBCIncArray db 2,1,1,1,2,2,2,2
clearmem db 0

OBCRegs:
    pushad
    sub ecx,1FF0h

    cmp byte[clearmem],0
    je near .noclearmem
    cmp ecx,6
    je .okay
    popad
    ret
.okay
    mov dword[OBCRegArray],0
    mov dword[OBCRegArray+4],0
    mov byte[OBCRegArray],0FEh
    mov byte[clearmem],0
.noclearmem

    mov ebx,[C4Ram]
    add ebx,1000h
    add ebx,[OBClog]
    inc dword[OBClog]
    mov [ebx],cl
    cmp cl,6
    jne .notsix
    add byte[OBCRegArray],2
    mov bl,[OBCRegArray]
    mov bh,bl
    mov [OBCRegArray+1],bl
    mov [OBCRegArray+2],bx
    mov [OBCRegArray+4],bx
    mov [OBCRegArray+6],bx
.notsix

    xor ebx,ebx
    mov bl,[OBCRegArray+ecx]
    cmp byte[OBCIncArray+ecx],1
    jne .noinc
    or byte[OBCRegArray+ecx],1
.noinc
    shl ebx,3
    add ecx,ebx
    add ecx,[C4Ram]
    mov byte[ecx],al
;    cmp dl,1
;    jne .second
    mov byte[ecx+8],0FFh
;    jmp .first
;.second
;    mov byte[ecx+16],0FFh
;.first
    popad
    ret

OBCReadReg:
    add ecx,[C4Ram]
    mov al,[ecx]
    sub ecx,[C4Ram]
    ret

OBCWriteReg
    add ecx,[C4Ram]
    mov [ecx],al
    sub ecx,[C4Ram]
    ret

NEWSYM InitC4
    pushad
    mov esi,[romdata]
    add esi,4096*1024
    mov [C4Data],esi
    add dword[C4Data],128*1024
    mov [C4RamR],esi
    mov [C4RamW],esi
    mov [C4Ram],esi
    add dword[C4RamW],8192*4
    add dword[C4Ram],8192*8
    mov ecx,8192
.c4loop
    mov dword[esi],C4ReadReg
    mov dword[esi+8192*4],C4WriteReg
    mov dword[esi+8192*8],0
    add esi,4
    dec ecx
    jnz .c4loop
    mov esi,[C4RamW]
    mov dword[esi+1F4Fh*4],C4RegFunction
    mov esi,[C4Data]
    mov ecx,16*4096
.c4loopb
    mov dword[esi],0
    add esi,4
    loop .c4loopb
    popad
    ret

C4ClearSpr:
    mov esi,ebx
    mov edi,eax
;    xor ecx,ecx
;    mov cx,[eax+1F44h]
;    sub cx,6000h
;    add eax,ecx
    shl ch,3
.scloop2
    mov cl,byte[C4SprPos]
    shl cl,2
.scloop
    mov byte[edi],0
    mov byte[edi+2000h],0
    inc edi
    dec cl
    jnz .scloop
    dec ch
    jnz .scloop2
    ret

C4SprBitPlane:
    mov edi,eax
    shl ebx,2
.scloop3
    mov ch,[C4SprPos]
    push esi
.scloop4
    push esi
    mov cl,8
.loop
    mov dh,8
    mov dl,80h
    mov eax,[esi]
.nextd
    test al,1
    jz .not0
    or byte[edi],dl
.not0
    test al,2
    jz .not1
    or byte[edi+1],dl
.not1
    test al,4
    jz .not2
    or byte[edi+16],dl
.not2
    test al,8
    jz .not3
    or byte[edi+17],dl
.not3
    shr eax,4
    shr dl,1
    dec dh
    jnz .nextd
    add esi,ebx
    add edi,2
    dec cl
    jnz .loop
    add edi,16
    pop esi
    add esi,4
    dec ch
    jnz .scloop4
    pop esi
    shl ebx,3
    add esi,ebx
    add edi,dword[C4SprPtrInc]
    shr ebx,3
    dec byte[C4SprPos+1]
    jnz .scloop3
.end
    ret

C4XXScale dw 0
C4XYScale dw 0
C4YXScale dw 0
C4YYScale dw 0
C4CXPos dw 0
C4CYPos dw 0
C4CXMPos dd 0
C4CYMPos dd 0
C4PCXMPos dd 0
C4PCYMPos dd 0

DoScaleRotate:
    pushad
    mov esi,eax
    ; Calculate X scaler
    mov ax,[esi+1F80h]
    and eax,01FFh
    mov ax,[CosTable+eax*2]
    mov bx,[esi+1F8Fh]
    test bx,8000h
    jz .notover
    mov bx,7FFFh
.notover
    imul bx
    add ax,ax
    adc dx,dx
    mov [C4XXScale],dx
    mov ax,[esi+1F80h]
    and eax,01FFh
    mov ax,[SinTable+eax*2]
    imul bx
    add ax,ax
    adc dx,dx
    mov [C4XYScale],dx
    ; Calculate Y scaler
    mov ax,[esi+1F80h]
    and eax,01FFh
    mov ax,[CosTable+eax*2]
    mov bx,[esi+1F92h]
    test bx,8000h
    jz .notoverb
    mov bx,7FFFh
.notoverb
    imul bx
    add ax,ax
    add dx,dx
    mov [C4YYScale],dx
    mov ax,[esi+1F80h]
    and eax,01FFh
    mov ax,[SinTable+eax*2]
    imul bx
    add ax,ax
    adc dx,dx
    neg dx
    mov [C4YXScale],dx
    cmp word[esi+1F80h],0
    jne .effect
    cmp word[esi+1F92h],1000h
    jne .effect
    mov word[C4YYScale],1000h
    mov word[C4YXScale],0
.effect
    ; Calculate Pixel Resolution
    mov cl,byte[C4SprPos]
    shl cl,3
    mov byte[C4SprPos+2],cl
    mov cl,byte[C4SprPos+1]
    shl cl,3
    mov byte[C4SprPos+3],cl
    ; Calculate Positions
    ; (1-scale)*(pos/2)
    xor eax,eax
    mov al,[C4SprPos+2]
    shl eax,11
    mov [C4PCXMPos],eax
    xor eax,eax
    mov al,[C4SprPos+3]
    shl eax,11
    mov [C4PCYMPos],eax

    mov bx,[C4XXScale]
    xor eax,eax
    mov al,[C4SprPos+2]
    shr ax,1
    imul bx
    shl edx,16
    mov dx,ax
    sub [C4PCXMPos],edx
    mov bx,[C4YXScale]
    xor eax,eax
    mov al,[C4SprPos+3]
    shr ax,1
    imul bx
    shl edx,16
    mov dx,ax
    sub [C4PCXMPos],edx

    mov bx,[C4XYScale]
    xor eax,eax
    mov al,[C4SprPos+2]
    shr ax,1
    imul bx
    shl edx,16
    mov dx,ax
    sub [C4PCYMPos],edx
    mov bx,[C4YYScale]
    xor eax,eax
    mov al,[C4SprPos+3]
    shr ax,1
    imul bx
    shl edx,16
    mov dx,ax
    sub [C4PCYMPos],edx

    ; Start loop
    mov word[C4CYPos],0
    xor edi,edi
.loop
    mov ecx,[C4PCXMPos]
    mov [C4CXMPos],ecx
    mov ecx,[C4PCYMPos]
    mov [C4CYMPos],ecx
    mov al,[C4SprPos+2]
    mov byte[C4CXPos],al
.loop2
    xor eax,eax
    mov al,[C4SprPos+2]
    mov ebx,[C4CXMPos]
    sar ebx,12
    cmp ebx,eax
    jae near .blank
    xor eax,eax
    mov al,[C4SprPos+3]
    mov ebx,[C4CYMPos]
    sar ebx,12
    cmp ebx,eax
    jae near .blank
    ; Get pixel value
    mov ebx,[C4CYMPos]
    xor eax,eax
    shr ebx,12
    mov al,[C4SprPos+2]
    mul ebx
    mov ebx,[C4CXMPos]
    shr ebx,12
    add eax,ebx
    mov ebx,[C4SprPtr]
    test al,1
    jnz .upperb
    shr eax,1
    add ebx,eax
    mov al,[ebx]
    jmp .lowerb
.upperb
    shr eax,1
    add ebx,eax
    mov al,[ebx]
    shr al,4
.lowerb
    mov ebx,edi
    shr ebx,1
    add ebx,esi
    test edi,1
    jnz .upperb2
    and al,0Fh
    and byte[ebx+2000h],0F0h
    or byte[ebx+2000h],al
    jmp .done
.upperb2
    shl al,4
    and byte[ebx+2000h],0Fh
    or byte[ebx+2000h],al
    jmp .done
.blank
    mov eax,edi
    shr eax,1
    add eax,esi
    test edi,1
    jnz .upper
    and byte[eax+2000h],0F0h
    jmp .done
.upper
    and byte[eax+2000h],0Fh
.done
    movsx eax,word[C4XXScale]
    add [C4CXMPos],eax
    movsx eax,word[C4XYScale]
    add [C4CYMPos],eax
    inc edi
    dec byte[C4CXPos]
    jne near .loop2
    movsx eax,word[C4YXScale]
    add [C4PCXMPos],eax
    movsx eax,word[C4YYScale]
    add [C4PCYMPos],eax
    inc word[C4CYPos]
    mov al,[C4SprPos+3]
    cmp byte[C4CYPos],al
    jne near .loop
.noimage
    popad
    ret

DoScaleRotate2:
    pushad
    xor ebx,ebx
    mov bx,[eax+1F8Fh]
    cmp bx,1000h
    ja .scaled
    mov bx,1000h
.scaled
    mov [C4SprScale],ebx
    xor ebx,ebx
    mov bx,[eax+1F92h]
    cmp bx,1000h
    ja .scaledb
    mov bx,1000h
.scaledb
    mov [C4SprScaleY],ebx
    mov cl,[C4SprPos]
    shl cl,3
    mov ch,cl
    xor ebx,ebx
.leftovercheck
    dec ch
    add ebx,[C4SprScale]
.leftovercheckb
    cmp ebx,1000h
    jb .leftovercheck
    sub ebx,1000h
    dec cl
    jz .donecheck
    jmp .leftovercheckb
.donecheck
    shr ch,1
    mov cl,ch
    and ecx,0FFh
    mov esi,ecx

    mov cl,[C4SprPos+1]
    shl cl,3
    mov ch,cl
    xor ebx,ebx
.leftovercheckc
    dec ch
    add ebx,[C4SprScaleY]
.leftovercheckd
    cmp ebx,1000h
    jb .leftovercheckc
    sub ebx,1000h
    dec cl
    jz .donecheckc
    jmp .leftovercheckd
.donecheckc
    shr ch,1
    mov cl,ch
    and ecx,0FFh
    push eax
    xor eax,eax
    mov al,[C4SprPos]
    shl al,3
    mul ecx
    add esi,eax
    pop eax

    mov dword[C4SprScalerY],0
    xor edi,edi
    mov cl,[C4SprPos+1]
    shl cl,3
    mov [C4SprPos+3],cl
.next
    push esi
    push edi
    xor ecx,ecx
    mov cl,[C4SprPos]
    shl cl,3
    mov ch,cl
    mov dword[C4SprScaler],0
    xor edx,edx
.loop
    mov edx,edi
    shr edx,1
    add edx,[C4SprPtr]
    mov bl,[edx]
    test esi,1
    jz .notupper
    shr bl,4
.notupper
    and bl,0Fh
    mov edx,esi
    shr edx,1
    test esi,1
    jz .notupperb

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -