Copy Link
Add to Bookmark
Report

Playstation System Operation

PS_2's profile picture
Published in 
Playstation
 · 21 Jun 2019

 

--------------------------------------------------------------------------
System Operation
--------------------------------------------------------------------------

Introduction
--------------------------------------------------------------------------
This text covers the usage of the R3000, the system control coprocessor and
hardware registers, the file server and some system calls.

--------------------------------------------------------------------------
R3000
--------------------------------------------------------------------------
The heart of the psx is a MIPS R3000. The version in the PSX has two
coproccors, (cop0 - System Control Coproccessor, cop2 - GTE), one
multiplier/divider, 32 general registers, one ALU, one shifter, one
address adder, 4kb of Instuction Cache, 1 kb of Data cache and NO floating
point unit.

Registers
-------------------------------------------------------------
All registers are 32 bits wide.

0 zero Constant, always 0
1 at Assembler temporary.
2- 3 v0-v1 Subroutine return values
4- 7 a0-a3 Subroutine arguments
8-15 t0-t7 Temporaries, may be changed by subroutines
16-23 s0-s7 Register variables, must be saved by subs.
24-25 t8-t9 Temporaries, may be changed by subroutines
26-27 k0-k1 Reserved for the kernel
28 gp Global pointer
29 sp Stack pointer
30 fp(s8) 9th register variable, subs can use this as a frame
pointer
31 ra Return address

- pc Program counter
- hi,lo Registers of the multiplier/divider.

All registers behave the same, remarks are not hardware bound, but general
programming good practice. Respect these for compatability, especially if
you intend to use kernel routines.
Exceptions are register 0, and 31. Zero will always return 0, regardless
of any writing attempts. Ra is used by the normal jal instruction for the
return address. (points to the second instruction after the jal). Note that
the jalr instruction can use any register for the return address, though
usually only register 31 is used.

The PC is not really a register, and should not be seen like one. Hi, Lo
are the registers which the multiplier/divider returns its results to.
Special instructions are implemented to deal with them.

-------------------------------------------------------------
Instructions
-------------------------------------------------------------
rt target register (cpu general register 0-31)
rs source register (cpu general register 0-31)
rd destination register (cpu general register 0-31)
base base register (cpu general register 0-31)
imm 16 bit immediate
b? immediate value of ? bits wide.
c0r Coprocessor 0 register
c2d Coprocessor 2 (GTE) data register
c2c Coprocessor 2 (GTE) control register


imm(base) means an address of the value in the register + the immediate
value.

inst instruction name.
d number of instructions to wait before using r1 (target reg).
args format of the operand fields.
desc. description of the instruction.


inst d args desc.

*Load/Store instructions

lb 1 rt,imm(base) loads lowest byte of rt with addressed byte and
extends sign.
lbu 1 rt,imm(base) loads lowest byte of rt with addressed byte.
lh 1 rt,imm(base) loads lowest halfword of rt with addressed halfword
and extends sign.
lhu 1 rt,imm(base) loads lowest halfword of rt with addressed halfword.
lw 1 rt,imm(base) loads r1 with addressed word.
lwl 0 rt,imm(base) loads high order byte of rt with addressed byte and
then loads up to the low order word boundary into rt.
lwr 0 rt,imm(base) loads low order byte of rt with addressed byte and
then loads up to the high order word boundary into
rt.

There's no delay for lwl and lwr, so you can use them
directly following eachother. fe. to load a word
anywhere in memory without regard to alignment:
lwl a0,$0003(t0)
lwr a0,$0000(t0)

sb 1 rt,imm(base) stores lowest byte of rt in addressed byte.
sh 1 rt,imm(base) stores lowest halfword of rt in addressed halfword.
sw 1 rt,imm(base) stores rt in addressed word.
swl 0 rt,imm(base) unaligned store, see lwl
swr 0 rt,imm(base) unaligned store, see lwr

lui 0 rt,imm loads rt with immediate<<$10

*arithmic instructions

When an arithmic overflow occurs, rd will not be modified.

add 0 rd,rs,rt Adds rt to rs and stores the result in rd.
addu 0 rd,rs,rt Adds rt to rs, ignores arithmic overflow and stores
result in rd.
sub 0 rd,rs,rt Substracts rt from rs and stores result in rd.
subu 0 rd,rs,rt Substracts rt from rs, ignores arithmic overflow and
stores result in rd.

addi 0 rd,rs,imm Adds signextended immediate to rs, and stores the
result in rd.
addiu 0 rd,rs,imm Adds signextended immediate to rs, ignores arithmic
overflow and stores the result in rd.

subi 0 rd,rs,imm Substracts signextended immediate from rs and stores
the result in rd.
subiu 0 rd,rs,imm Substracts signextended immediate from rs, ignores
arithmic overflow, and stores the result in rd.

mult rs,rt Multiplies rs with rt, and stores the 64 bit sign
extended result in hi/lo.
multu rs,rt Multiplies rs with rt, and stores the 64 bit result
in hi/lo.
div rs,rt Divides rs by rt, and stores the quotient into lo,
and the remainder into high. Results are sign
extended.
divu rs,rt Divides rs by rt, and stores the quotient into lo,
and the remainder into high.


*logical instructions

and 0 rd,rs,rt Performs a bit wise AND between rs and rt, and
stores the result in rd.
or 0 rd,rs,rt Performs a bit wise OR between rs and rt, and
stores the result in rd.
xor 0 rd,rs,rt Performs a bit wise XOR between rs and rt, and
stores the result in rd.
nor 0 rd,rs,rt Performs a bit wise NOR between rs and rt, and
stores the result in rd.

andi 0 rd,rs,imm Performs a bit wise AND between rs and unsigned
immediate and stores the result in rd.
ori 0 rd,rs,imm Performs a bit wise OR between rs and unsigned
immediate and stores the result in rd.
xori 0 rd,rs,imm Performs a bit wise XOR between rs and unsigned
immediate and stores the result in rd.

*shifting instructions

sllv 0 rd,rs,rt Shifts rs rt bits to the left and stores the result
in rd.
srlv 0 rd,rs,rt Shifts rs rt bits to the right and stores the result
in rd.
srav 0 rd,rs,rt Shifts the value in rs rt bits to the right,
preserving sign, and stores the value in rd.


sll 0 rd,rs,b5 Shifts rs b5 bits to the left and stores the result
in rd.
srl 0 rd,rs,b5 Shifts rs b5 bits to the right and stores the result
in rd.
sra 0 rd,rs,b5 Shifts rs b5 bits to the right, preserving sign and
stores the result in rd.

*comparison instructions.

slt 0 rd,rs,rt rd=1 if rs < rt, else rd = 0
sltu 0 rd,rs,rt rd=1 if (unsigned)rs <(unsigned)rt, else rd = 0

slti 0 rd,rs,imm rd=1 if rs < imm, else rd = 0
sltiu 0 rd,rs,imm rd=1 if (unsigned)rs < (unsigned)imm, else rd = 0

*jumps and branches

Note the the instruction following the branch will always be executed.

j target jumps to target
jal target jumps to target and stores pc+8 into RA (second
instruction after the jal instruction)

jr rd jumps to address in rd
jalr (rt,) rd jumps to address in rd and stores pc+8 into RA, or
in rt.

beq rs,rt,imm branches to imm if rs == rt
bne rs,rt,imm branches to imm if rs != rt

bgtz rs,imm branches to imm if rs > 0
bltz rs,imm branches to imm if rs < 0
blez rs,imm branches to imm if rs <= 0
bgez rs,imm branches to imm if rs >= 0
bltzal rs,imm branches to imm and stores pc+8 into RA if rs < 0
bgezal rs,imm branches to imm rd and stores pc+8 into RA if rs >= 0

*system instructions

mfhi 2 rd moves HI into rd
mflo 2 rd moves LO into rd
mthi 2 rs moves rs into HI
mtlo 2 rs moves rs into LO

mtc0 2 rs,c0r moves rs into cop0 register c0r
mfc0 2 rd,c0r moves cop0 register c0r into rd

mtc2 2 rs,c2d moves rs into cop2 data register c2d
mfc2 2 rd,c2d moves cop2 data register c2d into rd

ctc2 2 rs,c2c moves rs into cop2 control register c2d
cfc2 2 rd,c2c moves cop2 control register c2d into rd

lwc2 1 c2d,imm(base) load cop2 data register with addressed word
swc2 1 c2d,imm(base) stores cop2 data register at addressed word

syscall (b20) generates a system call exception
break (b20) generates a breakpoint exception
the 20bits wide code field is not passed, but
must be read from the instuction itself if you
want to use it.

cop2 b25 Coprocessor operation is started. b25 is
passed as parameter.

rfe restores the interrupt enable and kernel
previlege bits.

tlb instructions see MIPS doc.

--------------------------------------------------------------------------
Cop0 - System control coprocessor
--------------------------------------------------------------------------

Registers:
# Name rw Desciption.

-------------------------------------------------------------
16 ERREG
-------------------------------------------------------------
15 PRid r COP0 type and rev level
bit |31 16|15 8|7 0|
desc| |Imp |Rev |

Imp 3 CP0 type R3000A
7 IDT unique (3041) use REV to determine correct
config.
Rev Revision level.
-------------------------------------------------------------
14 EPC r Return address from trap

Contains the return address after an exception. This address is
the instruction at which the exception took place, unless BD is
set in CAUSE, when the instruction is EPC+4.
-------------------------------------------------------------
13 CAUSE r Describes the most recently recognised exception
bit |31|30|29 28|27 26 25 24 23 22 21 20 19 18 17 16|
desc|BD| 0|CE | 0|
bit |15 14 13 12 11 10 09 08|07|06 05 04 03 02|01 00|
desc|Ip | 0|Excode | 0|

BD Is set when last exception points to the
branch instuction instead of the instruction
in the branch delay slot, where the exception
occurred.
CE Contains the coprocessor number if the exception
occurred because of a coprocessor instuction for
a coprocessor which wasn't enabled in SR.
Ip Interrupt pending field. Bit 8 and 9 are RW, and
contain the last value written to them. As long
as any of the bits are set they will cause an
interrupt if the corresponding bit is set in IM.
Excode Describes what kind of exception occured:
0 INT Interrupt
1 MOD Tlb modification
2 TLBL Tlb load
3 TLBS Tlb store
4 AdEL Address error, load/I-fetch
5 AdES Address error, store
The address errors occur when attempting to read
outside of KUseg in user mode and when the address
is misaligned.
6 IBE Bus error on Instruction fetch.
7 DBE Bus error on Data load.
8 Syscall Generated unconditionally by at syscall instruction
9 BP Breakpoint - break instruction.
10 RI Reserved instruction
11 CpU Coprocessor unusable
12 Ov Arithmic overflow
-------------------------------------------------------------
12 SR rw System status register
bit |31 |30 |29 |28 |27 26|25|24 23|22 |21|20|19|18|17 |16 |
desc|CU3|CU2|CU1|CU0| 0|RE| 0|BEV|TS|PE|CM|PZ|SwC|IsC|

bit |15 14 13 12 11 10 09 08|07 06|05 |04 |03 |02 |01 |00 |
desc|Im | 0|KUo|IEo|KUp|IEp|KUc|IEc|

CUx 0 Coprocessor x disabled
1 Coprocessor x enabled
CU2 is for the GTE, CU1 is for the FPA, which is
not available in the PSX.
CU0 0 Cop0 in kernal mode.
1 Cop0 in user mode.
Makes some nominally privileged instruction usable
in user mode. Normal instructions are usable regardless
of this bit's setting.
RE 0 Normal 'endianness'
1 Reverse 'endianness'
Reverses the byte order in which data is stored in
memory. (lo-hi -> hi-lo)
BEV 0 Boot exception vectors in RAM
1 Boot exception vectors in ROM (kseg1)
TS TLB shutdown. Gets set if a programm address simultaniously
matches 2 TLB entries.
PE Cache parity error. Does not cause exception.
CM Shows the result of the last load operation with the D-cache
isolated. It gets set if the cache really contained data
for the addressed memory location.
PZ When set cache parity bits are written as 0.
Isc 0 Do not isolate cache.
1 Isolate cache. All load and store operations are targetted
to the Data cache, and never the main memory.
Swc 0 Normal cache mode.
1 Swapped cache mode. I cache will act as D cache and vice
versa. Use only with Isc to access & invalidate i cache
entries
Im 8 bit interrupt mask fields. When set the corresponding
interrupts are allowed to cause an exception.
KUc 0 User mode privilege , rfe pops KUp here
1 Kernal mode privilege
IEc 0 Interrupts enabled , rfe pops IUp here
1 All interrupts disabled.
KUp KUc gets pushed here on an exception, rfe pops KUo here
IUp IUc gets pushed here on an exception, rfe pops IUo here
KUo KUp gets pushed here on an exception
IUo IUp gets pushed here on an exception
-------------------------------------------------------------
11 BPCM rw Execute breakpoint mask.

Program counter is ANDed with this value and then compared to
the value in BPC.
-------------------------------------------------------------
10 TLBHI/PID
-------------------------------------------------------------
9 BDAM rw Data Access breakpoint mask.

Data fetch address is ANDed with this value and then compared
to the value in BDA
-------------------------------------------------------------
8 BadVaddr r Bad Virtual Address.

Contains the address whose reference caused an exception. Set
on any MMU type of exceptions, on references outside of kuseg
and on any misaligned reference.
-------------------------------------------------------------
7 DCIC rw Breakpoint control
|1f 1e 1d 1c|1b|1a|19|18|17|16 15 14 13 12 11 10||0f 00|
| 1 1 1 0| W| R|DA|PC| 1| 0| 0|

W 0
1 Break on Write
R 0
1 Break on Read
DA 0 Data access breakpoint disabled
1 Data access breakpoint enabled
PC 0 Execution breakpoint disabled
1 Execution breakpoint enabled

To use the Execution breakpoint, set PC. To use the Data access
breakpoint set DA and either R, W or both. Both breakpoints
can be used simultaniously. When a breakpoint occurs the PSX
jumps to $00000040.
-------------------------------------------------------------
6 PIDMASK
-------------------------------------------------------------
5 BDA rw Breakpoint on data access.

Sets the breakpoint address for load/store operations
-------------------------------------------------------------
4 CTXT
-------------------------------------------------------------
3 BPC rw Breakpoint on execute.

Sets the breakpoint address to break on on execute.
-------------------------------------------------------------
2 TLBLO
1 RAND
0 INX

For TLB details see mips doc.

--------------------------------------------------------------------------
PC file server
--------------------------------------------------------------------------
Caetla supports pcdrv: device, the SN systems device extension to access
files on the drive of the pc. This fileserver can be accessed by using the
kernel functions, with the 'pcdrv:' device name prefix to the filenames or
using the SN system calls.

-------------------------------------------------------------
SN System calls
-------------------------------------------------------------
The following SN system calls for the fileserver are provided.
Accessed by setting the registers and using the break command
with the specified field.
-------------------------------------------------------------
PCInit Inits the fileserver.
break $0101
-------------------------------------------------------------
PCCreat Creates a new file on PC.
break $0102
in: a1 pointer to file name
a2 file attribute
out: v0 0 = success, -1 = failure
v1 file handle or error code if v0 is negative
-------------------------------------------------------------
PCOpen Opens a file on the PC.
break $0103
in: a1 pointer to file name
a2 access mode 0 read only
1 write only
2 r/w
out: v0 0 = succes, -1 = failure
v1 file handle or error code if v0 is negative
-------------------------------------------------------------
PCClose Closes a file on the PC.
break $0104
in: a1 file handle
out: v0 0 = succes, -1 = failure
v1 0 = succes, error code if v0 is negative
-------------------------------------------------------------
PCRead Reads from an open file on PC.
break $0105
in: a1 file handle
a2 length in bytes
a3 pointer to store address
out: v0 0 = succes, -1 = failure
v1 number of read bytes or error code if v0 is
negative.

Note: Does not stop at eof, so if you set more bytes to read
than the filelength, the fileserver will pad with zero
bytes. If you are not sure of the the filelength obtain
the filelength by PClSeek (a2 = 0, a3 = 2, v1 will return
the length of the file, don't forget to reset the file
pointer to the start before calling PCread!)
-------------------------------------------------------------
PCWrite Writes to an open file on PC.
break $0106
in: a1 file handle
a2 length in bytes
a3 pointer to read address
out: v0 0 = succes, -1 = failure
v1 number of written bytes or error code if v0
is negative.
-------------------------------------------------------------
PClSeek Repositions the file pointer
break $0107
in: a1 file handle
a2 number of bytes to move.
a3 position from 0 Beginning of file
1 Current pointer
2 End of file
out: v0 0 = succes, -1 = failure
v1 file pointer
-------------------------------------------------------------
Attributes are passed as is. File attributes for the pc file
system are like this:
bit | 7 6| 5| 4| 3| 2| 1| 0|
desc| 0| A| D| 0| S| H| R|

A Archive file
D Directory
S System file
H Hidden file
R Read only file
-------------------------------------------------------------


--------------------------------------------------------------------------
System calls
--------------------------------------------------------------------------
Kernel system calls are accessed by loading the call number in t1, and
jumping to the specifeed address.
A0 call $3f means: load t1 with $3f and jump to $000000a0.

-------------------------------------------------------------
Printf Print string to console.
A0 call $3f
in: a0 Pointer to 0 terminated string.
a1-a3 Arguments.
sp+$10

Prints the specified string to the console (ie. pc screen).
String can contain standard C escape sequences and conversion
characters, except the floating point types (%e, %f, %g).
Variables are passed in a1 to a3. More variables are passed at
sp+$10.
-------------------------------------------------------------
openevent adds an event structure to the event table.
B0 call $08
in: a0 Event class.
a1 Event spec.
a2 Event mode.
a3 Address of function to be executed when
event occurs.
out: v0 Event descriptor, -1 if failed.

Opens an event, should be called within a critical section.
The return value is used to identify the event to the other
even functions.
A list of event classes, specs and modes is at the end of this
section.
-------------------------------------------------------------
closeevent releases an event structure from the
B0 call $09 event table.
in: a0 Event descriptor.
out: v0 1 on success, 0 if failed.
-------------------------------------------------------------
enableevent Turns on event handling for specified event.
B0 call $0c
in: a0 Event descriptor.
out: v0 1 on success, 0 if failed.
-------------------------------------------------------------
disableevent Turns off event handling for specified event.
B0 call $0d
in: a0 Event descriptor.
out: v0 1 on success, 0 if failed.
-------------------------------------------------------------
open Opens a file for IO.
B0 call $32
in: a0 File name, terminated with 0
a1 Access mode
out: v0 File handle, or -1 if error.

Opens a file on the target device for io. Access mode is set
like this:

bit 0 1 = Read
1 1 = Write
9 1 = New file
15 1 = Asynchronous mode?
16-31 Number of memory card blocks for a new file on the
memory card.

The PSX can have a maximum of 16 files open at any time.
-------------------------------------------------------------
lseek Move the file pointer.
B0 call $33
in: a0 File handle
a1 Movement offset in bytes
a2 0 = from start of file
1 = from current file pointer
2 = Bugs. Should be from end of file.

Moves the file pointer the number of bytes in a1, relative to
the location specified by a2. Movement from the eof is incorrect.
Also, movement beyond the end of the file is not checked.
-------------------------------------------------------------
read Read data from an open file.
B0 call $34
in: a0 File Handle
a1 Pointer to address to store read data
a2 Number of bytes to read
out: v0 Number of bytes actually read, -1 if failed.

Reads the number of bytes from the specified open file. If length
is not specified an error is returned. Read per $0080 bytes from
memory card (bu:) and per $0800 from cdrom (cdrom:).
-------------------------------------------------------------
write Write data to an open file.
B0 call $35
in: a0 File handle
a1 Pointer to adress to read data from.
a2 Number of bytes to write.
out: v0 Number of bytes written.

Writes the number of bytes to the specified open file. Write
to the memory card per $0080 bytes. Writing to the cdrom returns 0.
-------------------------------------------------------------
close Close an open file.
B0 call $36
in: a0 File handle
out: v0 File hande if success, -1 if failed.
-------------------------------------------------------------
cd Change the current directory on target device.
B0 call $40
in: a0 Pointer to new directory path
out: v0 1 if success, 0 if failed.

Changes the current directory on target system.
-------------------------------------------------------------
firstfile Finds the first file to match the name.
B0 call $42
in: a0 Pointer to the file name.
a1 Pointer to direntry structure.
out: v0 0 if unsuccessfull, else same as a1.

Searches for the first file to match the name in the string
pointed to by a0. Wildcards (?, *) may be used. Start the name
with the device you want to address. (ie. pcdrv:) Different
drives can be accessed as normally by their drive names (a:, c:)
if path is omitted after the device, the current directory will
be used.

A direntry structure looks like this:

$00 - $13 db Filename, terminated with 0.
$14 dw File attribute
$18 dw File size
$1c dw Pointer to next direntry
$20 - $27 db Reserved by system
-------------------------------------------------------------
nextfile Searches for the next file to match the name.
B0 call $43
in: a0 Pointer to direntry structure
out: v0 0 if unsuccesful, else same as a0.

Uses the settings of a previous firstfile command.
-------------------------------------------------------------
rename Rename a file on target device.
B0 call $44
in: a0 Pointer to old file name
a1 Pointer to new file name
out: v0 1 if successful, 0 if failed.
-------------------------------------------------------------
delete Delete a file on target device.
B0 call $45
in: a0 Pointer to file name
out: v0 1 if successful, 0 if failed.
-------------------------------------------------------------

Event Classes

The upper byte of each event type, is a descriptor byte, which
identifies the type of event to kernal routines.

Descriptors:
$ff Thread
$f0 Hardware
$f1 Event
$f2 Root counter
$f3 User event
$f4 BIOS

Hardware events:
$f0000001 VBLANK
$f0000002 GPU
$f0000003 CDROM Decoder
$f0000004 DMA controller
$f0000005 RTC0
$f0000006 RTC1
$f0000007 RTC2
$f0000008 Controller
$f0000009 SPU
$f000000a PIO
$f000000b SIO
$f0000010 Exception
$f0000011 memory card
$f0000012 memory card
$f0000013 memory card

Root counter events:
$f2000000 counter 0 (pixel clock)
$f2000001 counter 1 (horizontal retrace)
$f2000002 counter 2 (one-eighth of system clock)
$f2000003 counter 3 (vertical retrace)

Bios events:
$f4000001 memory card
$f4000002 libmath

Event Specs:
$0001 counter becomes zero
$0002 interrupted
$0004 end of i/o
$0008 file was closed
$0010 command acknowledged
$0020 command completed
$0040 data ready
$0080 data end
$0100 time out
$0200 unknown command
$0400 end of read buffer
$0800 end of write buffer
$1000 general interrupt
$2000 new device
$4000 system call instruction
$8000 error happned
$8001 previous write error happned
$0301 domain error in libmath
$0302 range error in libmath

Event modes:
$1000 Handle on interrupt
$2000 Do not handle on interrupt.

--------------------------------------------------------------------------
Root Counters
--------------------------------------------------------------------------
There are 4 root counters.

Counter Base address Synced to
0 $1f801100 pixelclock
1 $1f801110 horizontal retrace
2 $1f801120 1/8 system clock
3 vertical retrace

Each have three registers, one with the current value, one with the counter
mode, and one with a target value.

-------------------------------------------------------------
$11x0 Count r
bit |31 16|15 0|
desc|Garbage |Count |

Count Current count value, 0-$ffff

Upper word seems to contain only garbage.
-------------------------------------------------------------
$11x4 Mode rw
bit |31 10|9 |8 |7 |6 |5 |4 |3 | 2 1| 0|
desc|Garbage |Div|Clc| |Iq2| |Iq1|Tar| |En|

En 0 Counter running
1 Counter stopped (only counter 2)
Tar 0 Count to $ffff
1 Count to value in target register
Iq1 Set both for IRQ on target reached.
Iq2
Clc 0 System clock (it seems)
1 Pixel clock (counter 0)
Horizontal retrace (counter 1)
Div 0 System clock (it seems)
1 1/8 * System clock (counter 2)

When Clc and Div of the counters are zero, they all run at the
same speed. This speed seems to be about 8 times the normal
speed of root counter 2, which is specified as 1/8 the system
clock.

Bits 10 to 31 seem to contain only garbage.
-------------------------------------------------------------
$11x8 Target rw
bit |31 16|15 0|
desc|Garbage? |Target |

Target Target value, 0-$ffff

Upper word seems to contain only garbage.
-------------------------------------------------------------
Quick step-by-step:

To set up an interrupt using these counters you can do the following:
1 - Reset the counter. (Mode = 0)
2 - Set its target value, set mode.
3 - Enable corresponding bit in the interrupt mask register ($1f801074)
bit 3 = Counter 3 (Vblank)
bit 4 = Counter 0 (System clock)
bit 5 = Counter 1 (Hor retrace)
bit 6 = Counter 2 (Pixel)
4 - Open an event. (Openevent bios call - $b0, $08)
With following arguments:
a0-Rootcounter event descriptor or'd with the counter number.
($f2000000 - counter 0, $f2000001 - counter 1,$f2000002 - counter 2,
$f2000003 - counter 3)
a1-Spec = $0002 - interrupt event.
a2-Mode = Interrupt handling ($1000)
a3-Pointer to your routine to be excuted.
The return value in V0 is the event identifier.

5 - Enable the event, with the corresponding bioscall ($b0,$0c) with
the identifier as argument.

6 - Make sure interrupts are enabled. (Bit 0 and bit 10 of the COP0 status
register must be set.)

Your handler just has to restore the registers it uses, and it should
terminate with a normal jr ra.

To turn off the interrupt, first call disable event ($b0, $0d) and then
close it using the Close event call ($b0,$09) both with the event number
as argument.

--------------------------------------------------------------------------
DMA
--------------------------------------------------------------------------

-------------------------------------------------------------
DPCR Dma control register $1f8010f0
|1f 1c|1b 18|17 14|13 10|0f 0c|0b 08|07 04|03 00|
| |Dma6 |Dma5 |Dma4 |Dma3 |Dma2 |Dma1 |Dma0 |

Each register has a 4 bit control block allocated in this
register.
Bit 3: 1= Dma Enabled
2: ?
1: ?
0: ?

Bit 3 must be set for a channel to operate.
-------------------------------------------------------------
DICR Dma interrupt register $1f8010f4

-------------------------------------------------------------
The DMA channel registers are located starting at $1f801080. The
base adress for each channel is:
$1f801080 DMA channel 0 MDECin
$1f801090 DMA channel 1 MDECout
$1f8010a0 DMA channel 2 GPU (lists + image data)
$1f8010b0 DMA channel 3 CDrom
$1f8010c0 DMA channel 4 SPU
$1f8010d0 DMA channel 5 PIO
$1f8010e0 DMA channel 6 OTC (reverse clear OT)

-------------------------------------------------------------
D_MADR DMA base address. $1f8010x0
bit |1f 00|
desc|madr |

madr pointer to the adress the DMA will start reading
from/writing to
-------------------------------------------------------------
D_BCR DMA block control $1f8010x4
bit |1f 10|0f 00|
desc|ba |bs |

ba Amount of blocks
bs Blocksize (words)

The channel will transfer ba blocks of bs words. Take care
not to set the size larger than the buffer of the corresponding
unit can hold. (GPU & SPU both have a $10 word buffer). A
larger blocksize, means a faster transfer.
-------------------------------------------------------------
D_CHCR DMA channel control $1f8010x8
bit |1f-19|18|17-0c|0b|0a|09|08|07 01|00|
desc| 0|Tr| 0| 0|Li|Co| 0| 0|Dr|

Tr 0 No DMA transfer busy.
1 Start DMA transfer/DMA transfer busy.
Li 1 Transfer linked list. (GPU only)
Co 1 Transfer continous stream of data.
Dr 0 direction to memory
1 direction from memory
-------------------------------------------------------------

--------------------------------------------------------------------------
doomed@c64.org <- corrections/additions latest update -> psx.rules.org
--------------------------------------------------------------------------
16/may/1999 Initial version.
19/may/1999 Added Breakpoint info. <Herozero>
3/jun/1999 Root counters, some stuff on events and DMA added.

(thanx to ppl in <>)
--------------------------------------------------------------------------
thanx & hello to the usual.

← previous
next →
loading
sending ...
New to Neperos ? Sign Up for free
download Neperos App from Google Play
install Neperos as PWA

Let's discover also

Recent Articles

Recent Comments

Neperos cookies
This website uses cookies to store your preferences and improve the service. Cookies authorization will allow me and / or my partners to process personal data such as browsing behaviour.

By pressing OK you agree to the Terms of Service and acknowledge the Privacy Policy

By pressing REJECT you will be able to continue to use Neperos (like read articles or write comments) but some important cookies will not be set. This may affect certain features and functions of the platform.
OK
REJECT