Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
Jessica Hawkwell
/
kcpu
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
2
Merge Requests
0
Pipelines
Wiki
Snippets
Settings
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit 8aa59d72
authored
Sep 27, 2017
by
Jessica Hawkwell
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
got some opcodes
1 parent
486876bc
Pipeline
#203
passed
in 1 minute 4 seconds
Changes
18
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
18 changed files
with
599 additions
and
143 deletions
src/main/java/me/felinewith/kcpu/Converter.java
src/main/java/me/felinewith/kcpu/IDevice.java
src/main/java/me/felinewith/kcpu/IMemory.java
src/main/java/me/felinewith/kcpu/KBoard.java
src/main/java/me/felinewith/kcpu/memory/KMemoryRange.java → src/main/java/me/felinewith/kcpu/KMemoryRange.java
src/main/java/me/felinewith/kcpu/memory/KMemorySecurity.java → src/main/java/me/felinewith/kcpu/KMemorySecurity.java
src/main/java/me/felinewith/kcpu/Kcpu.java
src/main/java/me/felinewith/kcpu/hardware/Kfpu.java → src/main/java/me/felinewith/kcpu/hardware/Kmcp.java
src/main/java/me/felinewith/kcpu/hardware/BootRom.java → src/main/java/me/felinewith/kcpu/memory/BootRom.java
src/main/java/me/felinewith/kcpu/memory/Buffer.java
src/main/java/me/felinewith/kcpu/memory/MemHelper.java
src/main/java/me/felinewith/kcpu/opcodes/BasicMath.java
src/main/java/me/felinewith/kcpu/opcodes/IHandler.java
src/main/java/me/felinewith/kcpu/opcodes/Memory.java
src/main/java/me/felinewith/kcpu/opcodes/OpDirector.java
src/main/java/me/felinewith/kcpu/opcodes/ValueType.java
src/main/java/me/felinewith/kcpu/util/BaseDevice.java
src/main/java/me/felinewith/kcpu/util/BaseMemory.java
src/main/java/me/felinewith/kcpu/Converter.java
View file @
8aa59d7
...
...
@@ -34,13 +34,13 @@ public class Converter {
}
private
static
byte
[]
byteShifterDown
(
int
input
,
int
length
)
{
int
a
=
0
;
int
a
;
byte
[]
temp
=
new
byte
[
length
];
int
shift
=
0
;
int
shift
;
int
mask
=
0xff
;
for
(
a
=
0
;
a
<
length
;
a
++)
{
shift
=
a
*
8
;
mask
=
mask
<<
shift
;
mask
<<=
shift
;
temp
[
a
]
=
(
byte
)((
mask
&
input
)
>>
shift
);
}
return
temp
;
...
...
@@ -54,4 +54,6 @@ public class Converter {
}
return
output
;
}
private
Converter
()
{}
}
src/main/java/me/felinewith/kcpu/IDevice.java
View file @
8aa59d7
...
...
@@ -6,13 +6,7 @@ package me.felinewith.kcpu;
*/
public
interface
IDevice
extends
IMemory
{
public
void
init
(
IMemory
board
);
public
short
getInterrupt
();
public
void
setInterrupt
(
short
irq
);
public
short
getSetting
(
short
setting
);
public
void
setSetting
(
short
setting
,
short
value
);
public
byte
[]
getName
();
public
abstract
void
sendIrq
(
byte
irq
);
public
void
exec
();
}
src/main/java/me/felinewith/kcpu/IMemory.java
View file @
8aa59d7
...
...
@@ -6,7 +6,8 @@ package me.felinewith.kcpu;
*/
public
interface
IMemory
{
public
abstract
short
length
();
public
abstract
byte
[]
read
(
short
offset
,
short
length
);
public
abstract
void
write
(
short
offset
,
byte
[]
data
);
public
void
copy
(
short
offsetSrc
,
short
offsetDest
,
short
length
,
IMemory
dest
);
public
abstract
byte
read
(
short
addr
);
public
abstract
void
write
(
short
addr
,
byte
data
);
public
void
copy
(
short
addrSrc
,
short
addrDest
,
IMemory
dest
);
public
abstract
void
memIrq
(
short
addr
);
}
src/main/java/me/felinewith/kcpu/KBoard.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
;
import
java.util.Arrays
;
import
java.io.ByteArrayInputStream
;
import
java.io.ByteArrayOutputStream
;
import
java.io.IOException
;
import
java.io.InputStream
;
import
java.io.InputStreamReader
;
import
java.io.OutputStream
;
import
java.io.OutputStreamWriter
;
import
java.nio.charset.Charset
;
import
java.util.Timer
;
import
java.util.TimerTask
;
import
java.util.concurrent.LinkedBlockingQueue
;
import
java.util.concurrent.ThreadPoolExecutor
;
import
java.util.concurrent.TimeUnit
;
import
me.felinewith.kcpu.hardware.
BootRom
;
import
me.felinewith.kcpu.
hardware.Kfpu
;
import
me.felinewith.kcpu.memory.
KMemoryRange
;
import
me.felinewith.kcpu.util.Base
Memory
;
import
me.felinewith.kcpu.hardware.
Kmcp
;
import
me.felinewith.kcpu.
memory.BootRom
;
import
me.felinewith.kcpu.memory.
Buffer
;
import
me.felinewith.kcpu.util.Base
Device
;
import
me.felinewith.kcpu.util.HardwareTask
;
import
me.felinewith.kcpu.util.IDeviceRunner
;
/**
*
* @author jlhawkwell
*/
public
class
KBoard
extends
Base
Memory
implements
IMemory
{
public
class
KBoard
extends
Base
Device
implements
IMemory
{
ThreadPoolExecutor
tpe
;
TimerTask
tt
;
Timer
t
;
byte
[]
memory
;
private
final
ThreadPoolExecutor
tpe
;
private
TimerTask
tt
;
private
Timer
t
;
IDevice
[]
devices
;
KMemoryRange
[]
deviceMaps
;
private
final
IDevice
[]
devices
;
private
final
KMemoryRange
[]
deviceMaps
;
private
final
IMemory
[]
memDevs
;
private
final
KMemoryRange
[]
memDevMaps
;
private
final
Charset
cs
;
private
final
InputStream
stdin
;
private
final
OutputStream
stdout
;
private
final
byte
[]
bin
;
private
final
InputStreamReader
bufin
;
private
final
OutputStreamWriter
bufout
;
public
KBoard
()
{
tpe
=
new
ThreadPoolExecutor
(
16
,
32
,
30
,
TimeUnit
.
SECONDS
,
new
LinkedBlockingQueue
<
Runnable
>(
16
));
memory
=
new
byte
[
0x
ffff
];
tpe
=
new
ThreadPoolExecutor
(
16
,
32
,
30
,
TimeUnit
.
SECONDS
,
new
LinkedBlockingQueue
<>(
16
));
memory
=
new
byte
[
0x
010000
];
devices
=
new
IDevice
[
16
];
deviceMaps
=
new
KMemoryRange
[
16
];
memDevs
=
new
IMemory
[
16
];
memDevMaps
=
new
KMemoryRange
[
16
];
cs
=
Charset
.
forName
(
"UTF-8"
);
bin
=
new
byte
[
16
];
stdin
=
new
ByteArrayInputStream
(
bin
);
stdout
=
new
ByteArrayOutputStream
(
16
);
bufin
=
new
InputStreamReader
(
stdin
);
bufout
=
new
OutputStreamWriter
(
stdout
);
}
public
void
init
()
{
attachDevice
(
0
,
0x8000
,
new
Kcpu
(
this
));
attachDevice
(
1
,
0x8800
,
new
Kfpu
());
attachDevice
(
2
,
0x1000
,
new
BootRom
());
attachDevice
(
1
,
0x8800
,
new
Kmcp
());
attachMemory
(
0
,
0xff00
,
new
Buffer
());
attachMemory
(
1
,
0x1000
,
new
BootRom
());
tt
=
new
HardwareTask
(
devices
[
0
]);
t
=
new
Timer
(
"CPU Cycler"
);
t
.
schedule
(
tt
,
0
,
1
);
}
@Override
public
void
memIrq
(
short
addr
)
{
short
dev
=
checkDevice
(
addr
);
short
rdev
=
(
short
)(
0x0f
&
dev
);
if
(
dev
==
0x7f
)
{
devices
[
0
].
memIrq
(
addr
);
}
else
if
(
dev
<=
0x0f
)
{
short
devOff
=
deviceMaps
[
rdev
].
getOffset
();
short
devAddr
=
(
short
)(
addr
-
devOff
);
devices
[
rdev
].
memIrq
(
devAddr
);
}
else
if
(
0x10
<=
dev
&&
dev
<=
0x1f
)
{
short
devOff
=
memDevMaps
[
rdev
].
getOffset
();
short
devAddr
=
(
short
)(
addr
-
devOff
);
memDevs
[
rdev
].
memIrq
(
devAddr
);
}
}
@Override
public
void
sendIrq
(
byte
irq
)
{
if
(
irq
>=
16
)
{
return
;
}
if
(
devices
[
irq
]
!=
null
)
{
devices
[
irq
].
exec
();
}
}
@Override
public
short
length
()
{
return
(
short
)
memory
.
length
;
};
@Override
public
byte
[]
read
(
short
offset
,
short
length
)
{
short
dev
=
checkDevice
(
offset
,
length
);
if
(
dev
==
0x7f
)
{
return
Arrays
.
copyOfRange
(
memory
,
offset
,
offset
+
length
);
}
else
{
short
devOff
=
(
short
)(
offset
-
deviceMaps
[
dev
].
getOffset
());
return
devices
[
dev
].
read
(
devOff
,
length
);
@Override
public
byte
read
(
short
addr
)
{
short
dev
=
checkDevice
(
addr
);
short
rdev
=
(
short
)(
0x0f
&
dev
);
if
(
dev
<=
0x0f
)
{
short
devOff
=
deviceMaps
[
rdev
].
getOffset
();
short
devAddr
=
(
short
)(
addr
-
devOff
);
return
devices
[
rdev
].
read
(
devAddr
);
}
else
if
(
0x10
<=
dev
&&
dev
<=
0x1f
)
{
short
devOff
=
memDevMaps
[
rdev
].
getOffset
();
short
devAddr
=
(
short
)(
addr
-
devOff
);
return
memDevs
[
rdev
].
read
(
devAddr
);
}
return
memory
[
addr
];
}
@Override
public
void
write
(
short
offset
,
byte
[]
data
)
{
IDeviceRunner
idr
;
short
dev
=
checkDevice
(
offset
,
(
short
)
data
.
length
);
if
(
dev
==
0x7f
)
{
short
len
=
(
short
)
data
.
length
;
short
a
;
short
addr
;
for
(
a
=
0
;
a
<
len
;
a
++)
{
addr
=
(
short
)(
offset
+
a
);
memory
[
addr
]
=
data
[
a
];
}
idr
=
new
IDeviceRunner
(
devices
[
0
]);
@Override
public
void
write
(
short
addr
,
byte
data
)
{
short
dev
=
checkDevice
(
addr
);
short
rdev
=
(
short
)(
0x0f
&
dev
);
if
(
dev
<=
0x0f
)
{
short
devOff
=
deviceMaps
[
rdev
].
getOffset
();
short
devAddr
=
(
short
)(
addr
-
devOff
);
devices
[
rdev
].
write
(
devAddr
,
data
);
}
else
{
short
devOff
=
(
short
)(
offset
-
deviceMaps
[
dev
].
getOffset
()
);
devices
[
dev
].
write
(
devOff
,
data
);
idr
=
new
IDeviceRunner
(
devices
[
dev
]
);
else
if
(
0x10
<=
dev
&&
dev
<=
0x1f
)
{
short
devOff
=
memDevMaps
[
rdev
].
getOffset
(
);
short
devAddr
=
(
short
)(
addr
-
devOff
);
memDevs
[
rdev
].
write
(
devAddr
,
data
);
}
tpe
.
execute
(
idr
);
memory
[
addr
]
=
data
;
}
private
void
attachDevice
(
int
port
,
int
offset
,
IDevice
device
)
{
...
...
@@ -85,10 +141,22 @@ public class KBoard extends BaseMemory implements IMemory {
devices
[
port
]
=
device
;
deviceMaps
[
port
]
=
new
KMemoryRange
(
offset
,
device
.
length
());
device
.
init
(
this
);
}
private
short
checkDevice
(
short
offset
,
short
length
)
{
private
void
attachMemory
(
int
port
,
int
offset
,
IMemory
device
)
{
attachMemory
(
port
,
(
short
)
offset
,
device
);
}
private
void
attachMemory
(
int
port
,
short
offset
,
IMemory
device
)
{
if
(
memDevs
[
port
]
!=
null
)
{
return
;
}
else
if
(
memDevMaps
[
port
]
!=
null
)
{
return
;
}
memDevs
[
port
]
=
device
;
memDevMaps
[
port
]
=
new
KMemoryRange
(
offset
,
device
.
length
());
}
private
short
checkDevice
(
short
addr
)
{
short
a
;
short
top
=
(
short
)(
offset
+
length
);
KMemoryRange
io
;
short
devOff
;
...
...
@@ -100,12 +168,38 @@ public class KBoard extends BaseMemory implements IMemory {
devOff
=
io
.
getOffset
();
devTop
=
(
short
)(
devOff
+
io
.
getLength
());
if
(
devOff
<=
offset
&&
offset
<=
devTop
)
{
return
a
;
}
else
if
(
devOff
<=
top
&&
top
<=
devTop
)
{
return
a
;
}
if
(
devOff
<=
addr
&&
addr
<=
devTop
)
{
return
a
;
}
// range is entirely in device
}
}
for
(
a
=
0
;
a
<
16
;
a
++)
{
if
(
memDevMaps
[
a
]
!=
null
)
{
io
=
memDevMaps
[
a
];
devOff
=
io
.
getOffset
();
devTop
=
(
short
)(
devOff
+
io
.
getLength
());
if
(
devOff
<=
addr
&&
addr
<=
devTop
)
{
return
(
short
)(
0x10
+
a
);
}
// range is entirely in device
}
}
return
0x7f
;
}
@Override
public
void
exec
()
{
try
{
if
(
bufin
.
ready
()
)
{
byte
[]
temp
=
bufin
.
toString
().
getBytes
(
cs
);
int
len
=
temp
.
length
;
if
(
len
>=
16
)
{
len
=
16
;
}
short
addr
;
short
a
;
for
(
a
=
0
;
a
<
len
;
a
++)
{
addr
=
(
short
)(
0x10
+
a
);
memDevs
[
0
].
write
(
addr
,
temp
[
a
]);
}
}
}
catch
(
IOException
e
)
{}
}
}
src/main/java/me/felinewith/kcpu/
memory/
KMemoryRange.java
→
src/main/java/me/felinewith/kcpu/KMemoryRange.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
memory
;
package
me
.
felinewith
.
kcpu
;
/**
*
...
...
src/main/java/me/felinewith/kcpu/
memory/
KMemorySecurity.java
→
src/main/java/me/felinewith/kcpu/KMemorySecurity.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
memory
;
package
me
.
felinewith
.
kcpu
;
import
me.felinewith.kcpu.KMemoryRange
;
/**
*
...
...
src/main/java/me/felinewith/kcpu/Kcpu.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
;
import
java.nio.charset.Charset
;
import
java.util.Arrays
;
import
java.util.TimerTask
;
import
me.felinewith.kcpu.memory.MemHelper
;
import
me.felinewith.kcpu.opcodes.OpDirector
;
import
me.felinewith.kcpu.opcodes.ValueType
;
/**
*
...
...
@@ -10,38 +11,26 @@ import java.util.TimerTask;
*/
public
class
Kcpu
extends
TimerTask
implements
IDevice
{
byte
[]
memory
;
String
name
;
short
[]
settings
;
private
byte
[]
memory
;
private
String
name
;
private
short
[]
settings
;
KBoard
board
;
short
pc
;
short
[]
registers
;
private
KBoard
board
;
public
Kcpu
(
KBoard
system
)
{
memory
=
new
byte
[
0x0800
];
name
=
"Kcpu"
;
settings
=
new
short
[
4
];
settings
=
new
short
[
6
];
board
=
system
;
}
@Override
public
void
init
(
IMemory
system
)
{
}
@Override
public
short
getInterrupt
()
{
return
0
;
}
@Override
public
void
setInterrupt
(
short
irq
)
{
}
@Override
public
short
getSetting
(
short
setting
)
{
int
addr
=
0x07f0
+
setting
;
if
(
addr
>
0x07ff
)
{
return
0x7fff
;
}
return
memory
[
addr
];
}
@Override
public
void
setSetting
(
short
setting
,
short
value
)
{
int
addr
=
0x07f0
+
setting
;
if
(
addr
>
0x07ff
)
{
return
;
}
memory
[
addr
]
=
(
byte
)(
0xff
&
value
);
pc
=
0x1000
;
registers
=
new
short
[
4
];
}
@Override
public
byte
[]
getName
()
{
return
"Kcpu"
.
getBytes
(
Charset
.
forName
(
"UTF-8"
));
}
@Override
public
void
init
(
IMemory
system
)
{
}
// use this one during interrupts
@Override
public
void
exec
()
{
...
...
@@ -49,16 +38,106 @@ public class Kcpu extends TimerTask implements IDevice {
@Override
public
short
length
()
{
return
0x07ff
;
}
@Override
public
byte
[]
read
(
short
offset
,
short
length
)
{
return
Arrays
.
copyOfRange
(
memory
,
offset
,
offset
+
length
);
@Override
public
byte
read
(
short
addr
)
{
if
(
(
0xffff
&
addr
)
>
length
()
)
{
return
(
byte
)
0xff
;
}
return
memory
[
addr
];
}
@Override
public
void
write
(
short
offset
,
byte
[]
data
)
{
}
@Override
public
void
copy
(
short
offsetSrc
,
short
offsetDest
,
short
length
,
IMemory
dest
)
{
}
@Override
public
void
write
(
short
offset
,
byte
data
)
{
}
@Override
public
void
copy
(
short
addrSrc
,
short
addrDest
,
IMemory
dest
)
{
}
// this one for normal execution
@Override
public
void
run
()
{
@Override
public
void
run
()
{
workCycle
();
}
@Override
public
void
memIrq
(
short
addr
)
{
if
(
0
<=
addr
&&
addr
<=
memory
.
length
)
{
exec
();
}
}
@Override
public
void
sendIrq
(
byte
irq
)
{
board
.
sendIrq
(
irq
);
}
private
void
workCycle
()
{
short
inst
=
MemHelper
.
readShort
(
pc
,
board
);
OpDirector
od
=
null
;
for
(
OpDirector
o
:
OpDirector
.
values
())
{
if
(
o
.
getOpcode
()
==
inst
)
{
od
=
o
;
break
;
}
}
if
(
od
==
null
)
{
pc
+=
2
;
return
;
}
if
(
od
.
hasHandler
()
)
{
registers
=
od
.
call
(
pc
,
registers
,
board
);
ValueType
[]
vt
=
od
.
getArgs
();
if
(
vt
==
null
)
{
pc
+=
2
;
}
else
if
(
vt
[
0
]
==
ValueType
.
NONE
)
{
pc
+=
2
;
}
else
{
pc
+=
(
2
*
vt
.
length
);
}
return
;
}
pc
+=
2
;
// increment the program counter
switch
(
od
)
{
case
IRQD_A:
case
IRQD_D:
case
IRQD_R:
case
IRQM_A:
case
IRQM_D:
case
IRQM_R:
case
JMPA_A:
case
JMPA_D:
case
JMPA_R:
case
JMPD_A:
case
JMPD_D:
case
JMPD_R:
case
JMP_A:
case
JMP_D:
case
JMP_R:
pc
+=
2
;
break
;
}
short
a
=
MemHelper
.
readShort
(
pc
+
2
,
board
);
short
b
=
MemHelper
.
readShort
(
pc
+
4
,
board
);
short
c
=
MemHelper
.
readShort
(
pc
+
6
,
board
);
short
d
=
MemHelper
.
readShort
(
pc
+
8
,
board
);
short
ra
=
(
short
)(
0x03
&
a
);
short
rb
=
(
short
)(
0x03
&
b
);
short
rc
=
(
short
)(
0x03
&
c
);
short
rd
=
(
short
)(
0x03
&
d
);
switch
(
od
)
{
// interrupt to port
case
IRQD
:
board
.
sendIrq
((
byte
)
registers
[
0
]);
return
;
case
IRQD_A:
board
.
sendIrq
((
byte
)
MemHelper
.
readShort
(
a
,
board
));
return
;
case
IRQD_D:
board
.
sendIrq
((
byte
)
a
);
return
;
case
IRQD_R:
board
.
sendIrq
((
byte
)
registers
[
ra
]);
return
;
// interrupt to memory address
case
IRQM
:
board
.
memIrq
(
registers
[
0
]);
return
;
case
IRQM_A:
board
.
memIrq
(
a
);
return
;
case
IRQM_D:
board
.
memIrq
(
MemHelper
.
readShort
(
a
,
board
));
return
;
case
IRQM_R:
board
.
memIrq
(
registers
[
ra
]);
return
;
// jump absolute
case
JMPA
:
pc
=
registers
[
0
];
return
;
case
JMPA_A:
pc
=
MemHelper
.
readShort
(
a
,
board
);
return
;
case
JMPA_D:
pc
=
a
;
return
;
case
JMPA_R:
pc
=
registers
[
ra
];
return
;
// jump down
case
JMPD
:
pc
-=
registers
[
0
];
return
;
case
JMPD_A:
pc
-=
MemHelper
.
readShort
(
a
,
board
);
return
;
case
JMPD_D:
pc
-=
a
;
return
;
case
JMPD_R:
pc
-=
registers
[
ra
];
return
;
// jump up
case
JMP
:
pc
+=
registers
[
0
];
return
;
case
JMP_A:
pc
+=
MemHelper
.
readShort
(
a
,
board
);
return
;
case
JMP_D:
pc
+=
a
;
return
;
case
JMP_R:
pc
+=
registers
[
ra
];
return
;
}
}
}
src/main/java/me/felinewith/kcpu/hardware/K
fpu
.java
→
src/main/java/me/felinewith/kcpu/hardware/K
mcp
.java
View file @
8aa59d7
...
...
@@ -7,12 +7,11 @@ import me.felinewith.kcpu.util.BaseDevice;
*
* @author jlhawkwell
*/
public
class
K
fpu
extends
BaseDevice
{
public
class
K
mcp
extends
BaseDevice
{
public
Kfpu
()
{
memory
=
new
byte
[
0x010
];
name
=
"Kfpu"
;
settings
=
new
short
[
2
];
public
Kmcp
()
{
memory
=
new
byte
[
0x20
];
name
=
"Kmcp"
;
}
@Override
public
void
exec
()
{
...
...
@@ -28,13 +27,25 @@ public class Kfpu extends BaseDevice {
reg
[
a
]
=
readReg
(
setting
,
a
);
}
a
=
(
short
)(
0xff
&
settings
[
setting
]);
temp
=
doTheWork
(
a
,
reg
[
0
],
reg
[
1
]);
short
starts
;
switch
(
setting
)
{
case
0
:
starts
=
0x10
;
break
;
case
1
:
starts
=
0x12
;
break
;
default
:
starts
=
0
;
break
;
}
byte
[]
data
=
{
read
(
starts
),
read
(
starts
+
1
)
};
short
opcode
=
Converter
.
byte2short
(
data
);
a
=
(
short
)(
0xff
&
opcode
);
temp
=
do2reg
(
a
,
reg
[
0
],
reg
[
1
]);
reg
[
0
]
=
temp
[
0
];
reg
[
1
]
=
temp
[
1
];
a
=
(
short
)((
0xff00
&
setting
)
>>
8
);
temp
=
do
TheWork
(
a
,
reg
[
2
],
reg
[
3
]);
a
=
(
short
)((
0xff00
&
opcode
)
>>
8
);
temp
=
do
2reg
(
a
,
reg
[
2
],
reg
[
3
]);
reg
[
2
]
=
temp
[
0
];
reg
[
3
]
=
temp
[
1
];
...
...
@@ -42,12 +53,13 @@ public class Kfpu extends BaseDevice {
writeReg
(
setting
,
a
,
reg
[
a
]);
}
}
private
short
[]
doTheWork
(
short
setting
,
short
reg0
,
short
reg1
)
{
private
short
[]
do2reg
(
short
opcode
,
short
reg0
,
short
reg1
)
{
short
[]
out
=
new
short
[
2
];
out
[
0
]
=
reg0
;
out
[
1
]
=
reg1
;
switch
(
setting
)
{
switch
(
opcode
)
{
case
0x10
:
// add
out
[
0
]
=
(
short
)(
reg0
+
reg1
);
break
;
...
...
@@ -71,7 +83,12 @@ public class Kfpu extends BaseDevice {
if
(
setting
==
1
)
{
addr
+=
0x8
;
}
addr
+=
(
reg
*
2
);
return
Converter
.
byte2short
(
read
(
addr
,
(
short
)
2
));
byte
[]
data
=
{
read
(
addr
),
read
(
addr
+
1
)
};
return
Converter
.
byte2short
(
data
);
}
private
void
writeReg
(
short
setting
,
short
reg
,
short
data
)
{
...
...
@@ -79,6 +96,16 @@ public class Kfpu extends BaseDevice {
if
(
setting
==
1
)
{
addr
+=
0x8
;
}
addr
+=
(
reg
*
2
);
write
(
addr
,
Converter
.
short2byte
(
data
));
byte
[]
bytes
=
Converter
.
short2byte
(
data
);
int
a
;
for
(
a
=
0
;
a
<
bytes
.
length
;
a
++)
{
write
(
addr
+
a
,
bytes
[
a
]);
}
}
@Override
public
void
memIrq
(
short
addr
)
{
if
(
0
<=
addr
&&
addr
<=
memory
.
length
)
{
exec
();
}
}
@Override
public
void
sendIrq
(
byte
irq
)
{
}
}
src/main/java/me/felinewith/kcpu/
hardware
/BootRom.java
→
src/main/java/me/felinewith/kcpu/
memory
/BootRom.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
hardware
;
package
me
.
felinewith
.
kcpu
.
memory
;
import
java.util.Arrays
;
import
me.felinewith.kcpu.util.Base
Device
;
import
me.felinewith.kcpu.util.Base
Memory
;
/**
*
* @author jlhawkwell
*/
public
class
BootRom
extends
Base
Device
{
public
class
BootRom
extends
Base
Memory
{
public
BootRom
()
{
memory
=
new
byte
[
0x0fff
];
Arrays
.
fill
(
memory
,
(
byte
)
0x75
);
settings
=
new
short
[
0
];
name
=
"BootRom"
;
}
@Override
public
void
write
(
short
offset
,
byte
[]
data
)
{
}
@Override
public
void
exec
()
{
}
@Override
public
void
write
(
short
offset
,
byte
data
)
{
}
}
src/main/java/me/felinewith/kcpu/memory/Buffer.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
memory
;
import
me.felinewith.kcpu.util.BaseMemory
;
/**
*
* @author jlhawkwell
*/
public
class
Buffer
extends
BaseMemory
{
public
Buffer
()
{
memory
=
new
byte
[
32
];
}
}
src/main/java/me/felinewith/kcpu/memory/MemHelper.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
memory
;
import
me.felinewith.kcpu.Converter
;
import
me.felinewith.kcpu.IMemory
;
/**
*
* @author jlhawkwell
*/
public
class
MemHelper
{
public
static
short
readShort
(
int
addr
,
IMemory
memory
)
{
return
readShort
((
short
)
addr
,
memory
);
}
public
static
short
readShort
(
short
addr
,
IMemory
memory
)
{
byte
[]
data
=
new
byte
[
2
];
data
[
0
]
=
memory
.
read
(
addr
);
data
[
1
]
=
memory
.
read
((
short
)(
addr
+
1
));
return
Converter
.
byte2short
(
data
);
}
public
static
void
writeShort
(
int
addr
,
short
data
,
IMemory
memory
)
{
writeShort
((
short
)
addr
,
data
,
memory
);
}
public
static
void
writeShort
(
short
addr
,
int
data
,
IMemory
memory
)
{
writeShort
(
addr
,
(
short
)
data
,
memory
);
}
public
static
void
writeShort
(
int
addr
,
int
data
,
IMemory
memory
)
{
writeShort
((
short
)
addr
,
(
short
)
data
,
memory
);
}
public
static
void
writeShort
(
short
addr
,
short
data
,
IMemory
memory
)
{
byte
[]
dt
=
Converter
.
short2byte
(
data
);
memory
.
write
(
addr
,
dt
[
0
]);
memory
.
write
((
short
)(
addr
+
1
),
dt
[
1
]);
}
}
src/main/java/me/felinewith/kcpu/opcodes/BasicMath.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
opcodes
;
import
java.util.Arrays
;
import
me.felinewith.kcpu.IMemory
;
/**
*
* @author jlhawkwell
*/
public
class
BasicMath
implements
IHandler
{
@Override
public
short
[]
opcode
(
OpDirector
opcode
,
short
pc
,
short
[]
regs
,
IMemory
memory
)
{
short
[]
output
=
Arrays
.
copyOf
(
regs
,
regs
.
length
);
switch
(
opcode
)
{
case
ADD:
output
[
0
]
+=
output
[
1
];
break
;
case
DIV:
short
rem
=
(
short
)(
output
[
0
]
%
output
[
1
]);
output
[
0
]
/=
output
[
1
];
output
[
1
]
=
rem
;
break
;
case
MUL:
output
[
0
]
*=
output
[
1
];
break
;
case
SUB:
output
[
0
]
-=
output
[
1
];
break
;
}
return
output
;
}
@Override
public
ValueType
[]
getArgs
(
OpDirector
opcode
)
{
return
new
ValueType
[]{
ValueType
.
NONE
};
}
}
src/main/java/me/felinewith/kcpu/opcodes/IHandler.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
opcodes
;
import
me.felinewith.kcpu.IMemory
;
/**
*
* @author jlhawkwell
*/
public
interface
IHandler
{
public
abstract
short
[]
opcode
(
OpDirector
opcode
,
short
pc
,
short
[]
regs
,
IMemory
memory
);
public
abstract
ValueType
[]
getArgs
(
OpDirector
opcode
);
}
src/main/java/me/felinewith/kcpu/opcodes/Memory.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
opcodes
;
import
java.util.Arrays
;
import
me.felinewith.kcpu.IMemory
;
import
me.felinewith.kcpu.memory.MemHelper
;
/**
*
* @author jlhawkwell
*/
public
class
Memory
implements
IHandler
{
@Override
public
short
[]
opcode
(
OpDirector
opcode
,
short
pc
,
short
[]
regs
,
IMemory
memory
)
{
short
a
=
MemHelper
.
readShort
(
pc
+
2
,
memory
);
short
b
=
MemHelper
.
readShort
(
pc
+
4
,
memory
);
short
ra
=
(
short
)(
0x03
&
a
);
short
rb
=
(
short
)(
0x03
&
b
);
short
[]
output
=
Arrays
.
copyOf
(
regs
,
regs
.
length
);
switch
(
opcode
)
{
case
MOVRR:
// movrr
output
[
ra
]
=
output
[
rb
];
return
output
;
case
MOVRD:
// movrd
output
[
ra
]
=
b
;
return
output
;
case
MOVRA:
// movra
output
[
ra
]
=
MemHelper
.
readShort
(
b
,
memory
);
return
output
;
case
MOVDR:
// movdr
MemHelper
.
writeShort
(
a
,
output
[
rb
],
memory
);
return
output
;
case
MOVAR:
// movar
MemHelper
.
writeShort
(
MemHelper
.
readShort
(
a
,
memory
),
output
[
rb
],
memory
);
return
output
;
case
MOVAD:
// movad
MemHelper
.
writeShort
(
MemHelper
.
readShort
(
a
,
memory
),
b
,
memory
);
return
output
;
case
MOVAA:
// movaa
MemHelper
.
writeShort
(
MemHelper
.
readShort
(
a
,
memory
),
MemHelper
.
readShort
(
b
,
memory
),
memory
);
return
output
;
}
return
output
;
}
@Override
public
ValueType
[]
getArgs
(
OpDirector
opcode
)
{
ValueType
[]
output
=
new
ValueType
[
2
];
output
[
0
]
=
ValueType
.
NONE
;
output
[
1
]
=
ValueType
.
NONE
;
switch
(
opcode
)
{
case
MOVRR:
// movrr
output
[
0
]
=
ValueType
.
REGISTER
;
output
[
1
]
=
ValueType
.
REGISTER
;
return
output
;
case
MOVRD:
// movrd
output
[
0
]
=
ValueType
.
REGISTER
;
output
[
1
]
=
ValueType
.
DATA
;
return
output
;
case
MOVRA:
// movra
output
[
0
]
=
ValueType
.
REGISTER
;
output
[
1
]
=
ValueType
.
ADDRESS
;
return
output
;
case
MOVDR:
// movdr
output
[
0
]
=
ValueType
.
DATA
;
output
[
1
]
=
ValueType
.
REGISTER
;
return
output
;
case
MOVAR:
// movar
output
[
0
]
=
ValueType
.
ADDRESS
;
output
[
1
]
=
ValueType
.
REGISTER
;
return
output
;
case
MOVAD:
// movad
output
[
0
]
=
ValueType
.
ADDRESS
;
output
[
1
]
=
ValueType
.
DATA
;
return
output
;
case
MOVAA:
// movaa
output
[
0
]
=
ValueType
.
ADDRESS
;
output
[
1
]
=
ValueType
.
ADDRESS
;
return
output
;
}
return
output
;
}
}
src/main/java/me/felinewith/kcpu/opcodes/OpDirector.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
opcodes
;
import
me.felinewith.kcpu.IMemory
;
/**
*
* @author jlhawkwell
*/
public
enum
OpDirector
{
// basic math stuffies
ADD
(
0x0001
,
BasicMath
.
class
),
SUB
(
0x0002
,
BasicMath
.
class
),
MUL
(
0x0003
,
BasicMath
.
class
),
DIV
(
0x0004
,
BasicMath
.
class
),
// memory stuffies
MOVRR
(
0x0011
,
Memory
.
class
),
MOVRD
(
0x0012
,
Memory
.
class
),
MOVRA
(
0x0013
,
Memory
.
class
),
MOVDR
(
0x0014
,
Memory
.
class
),
MOVAR
(
0x0015
,
Memory
.
class
),
MOVAD
(
0x0016
,
Memory
.
class
),
MOVAA
(
0x0017
,
Memory
.
class
),
// cpu stuffies
IRQM
(
0x8f00
,
null
),
IRQM_R
(
0x8f01
,
null
),
IRQM_D
(
0x8f02
,
null
),
IRQM_A
(
0x8f03
,
null
),
IRQD
(
0x8f10
,
null
),
IRQD_R
(
0x8f11
,
null
),
IRQD_D
(
0x8f12
,
null
),
IRQD_A
(
0x8f13
,
null
),
JMPA
(
0x8f0c
,
null
),
JMPA_R
(
0x8f0d
,
null
),
JMPA_D
(
0x8f1c
,
null
),
JMPA_A
(
0x8f1d
,
null
),
JMPD
(
0x8f18
,
null
),
JMPD_R
(
0x8f19
,
null
),
JMPD_D
(
0x8f1a
,
null
),
JMPD_A
(
0x8f1b
,
null
),
JMP
(
0x8f08
,
null
),
JMP_R
(
0x8f09
,
null
),
JMP_D
(
0x8f0a
,
null
),
JMP_A
(
0x8f0b
,
null
),
;
short
o
;
Class
<?
extends
IHandler
>
c
;
private
OpDirector
(
short
opcode
,
Class
<?
extends
IHandler
>
cls
)
{
o
=
opcode
;
c
=
cls
;
}
private
OpDirector
(
int
opcode
,
Class
<?
extends
IHandler
>
cls
)
{
o
=
(
short
)(
0xffff
&
opcode
);
c
=
cls
;
}
public
short
getOpcode
()
{
return
o
;
}
public
boolean
hasHandler
()
{
return
(
c
!=
null
);
}
public
short
[]
call
(
short
pc
,
short
[]
regs
,
IMemory
memory
)
{
try
{
if
(
c
==
null
)
{
return
regs
;
}
IHandler
ih
=
c
.
newInstance
();
return
ih
.
opcode
(
this
,
pc
,
regs
,
memory
);
}
catch
(
IllegalAccessException
|
InstantiationException
e
)
{}
return
regs
;
}
public
ValueType
[]
getArgs
()
{
try
{
if
(
c
==
null
)
{
return
null
;
}
IHandler
ih
=
c
.
newInstance
();
return
ih
.
getArgs
(
this
);
}
catch
(
IllegalAccessException
|
InstantiationException
e
)
{}
return
null
;
}
}
src/main/java/me/felinewith/kcpu/opcodes/ValueType.java
0 → 100644
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
opcodes
;
/**
*
* @author jlhawkwell
*/
public
enum
ValueType
{
NONE
(
0
),
REGISTER
(
1
),
DATA
(
2
),
ADDRESS
(
3
);
int
t
;
private
ValueType
(
int
type
)
{
t
=
type
;
}
public
int
getValue
()
{
return
t
;
}
}
src/main/java/me/felinewith/kcpu/util/BaseDevice.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
util
;
import
java.nio.charset.Charset
;
import
me.felinewith.kcpu.IDevice
;
import
me.felinewith.kcpu.IMemory
;
...
...
@@ -11,32 +10,21 @@ import me.felinewith.kcpu.IMemory;
public
abstract
class
BaseDevice
extends
BaseMemory
implements
IDevice
{
protected
String
name
;
protected
short
[]
settings
;
protected
IMemory
board
;
@Override
public
void
init
(
IMemory
system
)
{
board
=
system
;
}
@Override
public
short
getInterrupt
()
{
return
settings
[
0
];
}
@Override
public
void
setInterrupt
(
short
irq
)
{
settings
[
0
]
=
irq
;}
@Override
public
short
getSetting
(
short
setting
)
{
if
(
setting
>
settings
.
length
)
{
return
0x7fff
;
}
return
settings
[
setting
];
@Override
public
void
memIrq
(
short
addr
)
{
if
(
0
<=
addr
&&
addr
<=
memory
.
length
)
{
exec
();
}
}
@Override
public
void
setSetting
(
short
setting
,
short
value
)
{
if
(
setting
>
settings
.
length
)
{
return
;
}
else
if
(
setting
==
0
)
{
return
;
}
settings
[
setting
]
=
value
;
protected
void
sendIrq
()
{
int
addr
=
memory
.
length
-
1
;
sendIrq
(
memory
[
addr
]);
}
@Override
public
byte
[]
getName
()
{
return
name
.
getBytes
(
Charset
.
forName
(
"UTF-8"
));
}
@Override
public
short
length
()
{
return
(
short
)
memory
.
length
;
}
@Override
public
short
length
()
{
return
(
short
)
memory
.
length
;
}
}
src/main/java/me/felinewith/kcpu/util/BaseMemory.java
View file @
8aa59d7
package
me
.
felinewith
.
kcpu
.
util
;
import
java.util.Arrays
;
import
me.felinewith.kcpu.IMemory
;
/**
...
...
@@ -11,24 +10,27 @@ public abstract class BaseMemory implements IMemory {
protected
byte
[]
memory
;
@Override
public
byte
[]
read
(
short
offset
,
short
length
)
{
return
Arrays
.
copyOfRange
(
memory
,
offset
,
offset
+
length
)
;
@Override
public
short
length
(
)
{
return
(
short
)
memory
.
length
;
}
@Override
public
void
write
(
short
offset
,
byte
[]
data
)
{
short
len
=
(
short
)
data
.
length
;
short
a
;
short
addr
;
public
final
byte
read
(
int
addr
)
{
return
read
((
short
)
addr
);
}
@Override
public
byte
read
(
short
addr
)
{
if
(
(
0xffff
&
addr
)
>
length
()
)
{
return
(
byte
)
0xff
;
}
return
memory
[
addr
];
}
for
(
a
=
0
;
a
<
len
;
a
++)
{
addr
=
(
short
)(
offset
+
a
);
memory
[
addr
]
=
data
[
a
];
}
public
final
void
write
(
int
addr
,
byte
data
)
{
write
((
short
)
addr
,
data
);
}
@Override
public
void
write
(
short
addr
,
byte
data
)
{
if
(
(
0xffff
&
addr
)
>
length
()
)
{
return
;
}
memory
[
addr
]
=
data
;
}
@Override
public
void
copy
(
short
offsetSrc
,
short
offsetDest
,
short
length
,
IMemory
dest
)
{
byte
[]
data
=
read
(
offsetSrc
,
length
);
dest
.
write
(
offsetDest
,
data
);
public
final
void
copy
(
int
addrSrc
,
int
addrDest
,
IMemory
dest
)
{
copy
((
short
)
addrSrc
,
(
short
)
addrDest
,
dest
);
}
@Override
public
void
copy
(
short
addrSrc
,
short
addrDest
,
IMemory
dest
)
{
if
(
(
0xffff
&
addrSrc
)
>
length
()
)
{
return
;
}
dest
.
write
(
addrDest
,
read
(
addrSrc
));
}
@Override
public
void
memIrq
(
short
addr
)
{
}
}
Write
Preview
Markdown
is supported
Attach a file
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to post a comment