pcsx2/pcsx2/IopBios.cpp

302 lines
9.0 KiB
C++

/* Pcsx2 - Pc Ps2 Emulator
* Copyright (C) 2002-2009 Pcsx2 Team
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "PrecompiledHeader.h"
#include <ctype.h>
#include "IopCommon.h"
namespace R3000A {
const char *biosA0n[256] = {
// 0x00
"open", "lseek", "read", "write",
"close", "ioctl", "exit", "sys_a0_07",
"getc", "putc", "todigit", "atof",
"strtoul", "strtol", "abs", "labs",
// 0x10
"atoi", "atol", "atob", "setjmp",
"longjmp", "strcat", "strncat", "strcmp",
"strncmp", "strcpy", "strncpy", "strlen",
"index", "rindex", "strchr", "strrchr",
// 0x20
"strpbrk", "strspn", "strcspn", "strtok",
"strstr", "toupper", "tolower", "bcopy",
"bzero", "bcmp", "memcpy", "memset",
"memmove", "memcmp", "memchr", "rand",
// 0x30
"srand", "qsort", "strtod", "malloc",
"free", "lsearch", "bsearch", "calloc",
"realloc", "InitHeap", "_exit", "getchar",
"putchar", "gets", "puts", "printf",
// 0x40
"sys_a0_40", "LoadTest", "Load", "Exec",
"FlushCache", "InstallInterruptHandler", "GPU_dw", "mem2vram",
"SendGPUStatus", "GPU_cw", "GPU_cwb", "SendPackets",
"sys_a0_4c", "GetGPUStatus", "GPU_sync", "sys_a0_4f",
// 0x50
"sys_a0_50", "LoadExec", "GetSysSp", "sys_a0_53",
"_96_init()", "_bu_init()", "_96_remove()", "sys_a0_57",
"sys_a0_58", "sys_a0_59", "sys_a0_5a", "dev_tty_init",
"dev_tty_open", "sys_a0_5d", "dev_tty_ioctl","dev_cd_open",
// 0x60
"dev_cd_read", "dev_cd_close", "dev_cd_firstfile", "dev_cd_nextfile",
"dev_cd_chdir", "dev_card_open", "dev_card_read", "dev_card_write",
"dev_card_close", "dev_card_firstfile", "dev_card_nextfile","dev_card_erase",
"dev_card_undelete","dev_card_format", "dev_card_rename", "dev_card_6f",
// 0x70
"_bu_init", "_96_init", "_96_remove", "sys_a0_73",
"sys_a0_74", "sys_a0_75", "sys_a0_76", "sys_a0_77",
"_96_CdSeekL", "sys_a0_79", "sys_a0_7a", "sys_a0_7b",
"_96_CdGetStatus", "sys_a0_7d", "_96_CdRead", "sys_a0_7f",
// 0x80
"sys_a0_80", "sys_a0_81", "sys_a0_82", "sys_a0_83",
"sys_a0_84", "_96_CdStop", "sys_a0_86", "sys_a0_87",
"sys_a0_88", "sys_a0_89", "sys_a0_8a", "sys_a0_8b",
"sys_a0_8c", "sys_a0_8d", "sys_a0_8e", "sys_a0_8f",
// 0x90
"sys_a0_90", "sys_a0_91", "sys_a0_92", "sys_a0_93",
"sys_a0_94", "sys_a0_95", "AddCDROMDevice", "AddMemCardDevide",
"DisableKernelIORedirection", "EnableKernelIORedirection", "sys_a0_9a", "sys_a0_9b",
"SetConf", "GetConf", "sys_a0_9e", "SetMem",
// 0xa0
"_boot", "SystemError", "EnqueueCdIntr", "DequeueCdIntr",
"sys_a0_a4", "ReadSector", "get_cd_status", "bufs_cb_0",
"bufs_cb_1", "bufs_cb_2", "bufs_cb_3", "_card_info",
"_card_load", "_card_auto", "bufs_cd_4", "sys_a0_af",
// 0xb0
"sys_a0_b0", "sys_a0_b1", "do_a_long_jmp", "sys_a0_b3",
"?? sub_function",
};
const char *biosB0n[256] = {
// 0x00
"SysMalloc", "sys_b0_01", "sys_b0_02", "sys_b0_03",
"sys_b0_04", "sys_b0_05", "sys_b0_06", "DeliverEvent",
"OpenEvent", "CloseEvent", "WaitEvent", "TestEvent",
"EnableEvent", "DisableEvent", "OpenTh", "CloseTh",
// 0x10
"ChangeTh", "sys_b0_11", "InitPAD", "StartPAD",
"StopPAD", "PAD_init", "PAD_dr", "ReturnFromExecption",
"ResetEntryInt", "HookEntryInt", "sys_b0_1a", "sys_b0_1b",
"sys_b0_1c", "sys_b0_1d", "sys_b0_1e", "sys_b0_1f",
// 0x20
"UnDeliverEvent", "sys_b0_21", "sys_b0_22", "sys_b0_23",
"sys_b0_24", "sys_b0_25", "sys_b0_26", "sys_b0_27",
"sys_b0_28", "sys_b0_29", "sys_b0_2a", "sys_b0_2b",
"sys_b0_2c", "sys_b0_2d", "sys_b0_2e", "sys_b0_2f",
// 0x30
"sys_b0_30", "sys_b0_31", "open", "lseek",
"read", "write", "close", "ioctl",
"exit", "sys_b0_39", "getc", "putc",
"getchar", "putchar", "gets", "puts",
// 0x40
"cd", "format", "firstfile", "nextfile",
"rename", "delete", "undelete", "AddDevice",
"RemoteDevice", "PrintInstalledDevices", "InitCARD", "StartCARD",
"StopCARD", "sys_b0_4d", "_card_write", "_card_read",
// 0x50
"_new_card", "Krom2RawAdd", "sys_b0_52", "sys_b0_53",
"_get_errno", "_get_error", "GetC0Table", "GetB0Table",
"_card_chan", "sys_b0_59", "sys_b0_5a", "ChangeClearPAD",
"_card_status", "_card_wait",
};
const char *biosC0n[256] = {
// 0x00
"InitRCnt", "InitException", "SysEnqIntRP", "SysDeqIntRP",
"get_free_EvCB_slot", "get_free_TCB_slot", "ExceptionHandler", "InstallExeptionHandler",
"SysInitMemory", "SysInitKMem", "ChangeClearRCnt", "SystemError",
"InitDefInt", "sys_c0_0d", "sys_c0_0e", "sys_c0_0f",
// 0x10
"sys_c0_10", "sys_c0_11", "InstallDevices", "FlushStfInOutPut",
"sys_c0_14", "_cdevinput", "_cdevscan", "_circgetc",
"_circputc", "ioabort", "sys_c0_1a", "KernelRedirect",
"PatchAOTable",
};
//#define r0 (psxRegs.GPR.n.r0)
#define at (psxRegs.GPR.n.at)
#define v0 (psxRegs.GPR.n.v0)
#define v1 (psxRegs.GPR.n.v1)
#define a0 (psxRegs.GPR.n.a0)
#define a1 (psxRegs.GPR.n.a1)
#define a2 (psxRegs.GPR.n.a2)
#define a3 (psxRegs.GPR.n.a3)
#define t0 (psxRegs.GPR.n.t0)
#define t1 (psxRegs.GPR.n.t1)
#define t2 (psxRegs.GPR.n.t2)
#define t3 (psxRegs.GPR.n.t3)
#define t4 (psxRegs.GPR.n.t4)
#define t5 (psxRegs.GPR.n.t5)
#define t6 (psxRegs.GPR.n.t6)
#define t7 (psxRegs.GPR.n.t7)
#define s0 (psxRegs.GPR.n.s0)
#define s1 (psxRegs.GPR.n.s1)
#define s2 (psxRegs.GPR.n.s2)
#define s3 (psxRegs.GPR.n.s3)
#define s4 (psxRegs.GPR.n.s4)
#define s5 (psxRegs.GPR.n.s5)
#define s6 (psxRegs.GPR.n.s6)
#define s7 (psxRegs.GPR.n.s7)
#define t8 (psxRegs.GPR.n.t6)
#define t9 (psxRegs.GPR.n.t7)
#define k0 (psxRegs.GPR.n.k0)
#define k1 (psxRegs.GPR.n.k1)
#define gp (psxRegs.GPR.n.gp)
#define sp (psxRegs.GPR.n.sp)
#define fp (psxRegs.GPR.n.s8)
#define ra (psxRegs.GPR.n.ra)
#define pc0 (psxRegs.pc)
#define Ra0 (iopVirtMemR<char>(a0))
#define Ra1 (iopVirtMemR<char>(a1))
#define Ra2 (iopVirtMemR<char>(a2))
#define Ra3 (iopVirtMemR<char>(a3))
#define Rv0 (iopVirtMemR<char>(v0))
#define Rsp (iopVirtMemR<char>(sp))
void bios_write() { // 0x35/0x03
if (a0 == 1) { // stdout
const char *ptr = Ra1;
while (a2 > 0) {
SysPrintf("%c", *ptr++); a2--;
}
pc0 = ra; return;
}
PSXBIOS_LOG("bios_%s: %x,%x,%x", biosB0n[0x35], a0, a1, a2);
v0 = -1;
pc0 = ra;
}
void bios_printf() { // 3f
char tmp[1024];
char tmp2[1024];
unsigned long save[4];
char *ptmp = tmp;
int n=1, i=0, j;
memcpy(save, iopVirtMemR<void>(sp), 4*4);
iopMemWrite32(sp, a0);
iopMemWrite32(sp + 4, a1);
iopMemWrite32(sp + 8, a2);
iopMemWrite32(sp + 12, a3);
// old code used phys... is tlb more correct?
//psxMu32(sp) = a0;
//psxMu32(sp + 4) = a1;
//psxMu32(sp + 8) = a2;
//psxMu32(sp + 12) = a3;
while (Ra0[i]) {
switch (Ra0[i]) {
case '%':
j = 0;
tmp2[j++] = '%';
_start:
switch (Ra0[++i]) {
case '.':
case 'l':
tmp2[j++] = Ra0[i]; goto _start;
default:
if (Ra0[i] >= '0' && Ra0[i] <= '9') {
tmp2[j++] = Ra0[i];
goto _start;
}
break;
}
tmp2[j++] = Ra0[i];
tmp2[j] = 0;
switch (Ra0[i]) {
case 'f': case 'F':
ptmp+= sprintf(ptmp, tmp2, (float)iopMemRead32(sp + n * 4)); n++; break;
case 'a': case 'A':
case 'e': case 'E':
case 'g': case 'G':
ptmp+= sprintf(ptmp, tmp2, (double)iopMemRead32(sp + n * 4)); n++; break;
case 'p':
case 'i':
case 'd': case 'D':
case 'o': case 'O':
case 'x': case 'X':
ptmp+= sprintf(ptmp, tmp2, (unsigned int)iopMemRead32(sp + n * 4)); n++; break;
case 'c':
ptmp+= sprintf(ptmp, tmp2, (unsigned char)iopMemRead32(sp + n * 4)); n++; break;
case 's':
ptmp+= sprintf(ptmp, tmp2, iopVirtMemR<char>(iopMemRead32(sp + n * 4))); n++; break;
case '%':
*ptmp++ = Ra0[i]; break;
}
i++;
break;
default:
*ptmp++ = Ra0[i++];
}
}
*ptmp = 0;
// Note: Use Read to obtain a write pointer here, since we're just writing back the
// temp buffer we saved earlier.
memcpy( (void*)iopVirtMemR<void>(sp), save, 4*4);
Console::Write( Color_Cyan, "%s", params tmp);
pc0 = ra;
}
void bios_putchar () { // 3d
Console::Write( Color_Cyan, "%c", params a0 );
pc0 = ra;
}
void bios_puts () { // 3e/3f
Console::Write( Color_Cyan, Ra0 );
pc0 = ra;
}
void (*biosA0[256])();
void (*biosB0[256])();
void (*biosC0[256])();
void psxBiosInit() {
int i;
for(i = 0; i < 256; i++) {
biosA0[i] = NULL;
biosB0[i] = NULL;
biosC0[i] = NULL;
}
biosA0[0x3e] = bios_puts;
biosA0[0x3f] = bios_printf;
biosB0[0x3d] = bios_putchar;
biosB0[0x3f] = bios_puts;
}
void psxBiosShutdown() {
}
} // end namespace R3000A