working on vector

This commit is contained in:
Steven Hugg 2017-02-01 13:21:17 -05:00
parent e579663a8d
commit 52b58f471c
12 changed files with 210 additions and 51 deletions

View File

@ -192,7 +192,7 @@ canvas.pixelated {
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="?platform=vcs" id="item_platform_vcs">Atari VCS</a></li>
<li><a class="dropdown-item" href="?platform=apple2" id="item_platform_apple2">Apple ][</a></li>
<li><a class="dropdown-item" href="?platform=atarivec" id="item_platform_atarivec">Asteroids</a></li>
<li><a class="dropdown-item" href="?platform=vector" id="item_platform_atarivec">Asteroids</a></li>
<li><a class="dropdown-item" href="?platform=mw8080bw" id="item_platform_mw8080bw">Midway 8080 B/W</a></li>
</ul>
</li>

View File

@ -374,6 +374,12 @@ var AY38910_Audio = function(master) {
var Base6502Platform = function() {
this.newCPU = function(membus) {
var cpu = new jt.M6502();
cpu.connectBus(membus);
return cpu;
}
this.getOpcodeMetadata = function(opcode, offset) {
return Javatari.getOpcodeMetadata(opcode, offset); // TODO
}
@ -544,12 +550,13 @@ function cpuStateToLongString_Z80(c) {
;
}
window.buildZ80({
applyContention: false // TODO???
});
var BaseZ80Platform = function() {
window.buildZ80({
applyContention: false // TODO???
});
// TODO: refactor w/ platforms
this.newCPU = function(membus, iobus) {
return window.Z80({
@ -559,6 +566,24 @@ var BaseZ80Platform = function() {
});
}
// TODO: refactor other parts into here
this.runCPU = function(cpu, cycles) {
var debugCond = this.getDebugCallback();
var targetTstates = cpu.getTstates() + cycles;
if (debugCond) { // || trace) {
while (cpu.getTstates() < targetTstates) {
//_trace(); // TODO
if (debugCond && debugCond()) {
debugCond = null;
break;
}
cpu.runFrame(cpu.getTstates() + 1);
}
} else {
cpu.runFrame(targetTstates);
}
}
var onBreakpointHit;
var debugCondition;
var debugSavedState = null;

View File

@ -1,4 +1,5 @@
"use strict";
var GALAXIAN_PRESETS = [
];
@ -111,7 +112,8 @@ var GalaxianPlatform = function(mainElement) {
missile = which;
}
}
for (var which of [shell,missile]) {
for (var i=0; i<2; i++) {
which = i ? missile : shell;
if (which != 0xff) {
var sx = 255 - oram.mem[0x60 + (which<<2)+3];
var outi = pixofs+sx;

View File

@ -1,8 +1,22 @@
"use strict";
var ATARIVEC_PRESETS = [
var VECTOR_PRESETS = [
]
var ASTEROIDS_KEYCODE_MAP = makeKeycodeMap([
[Keys.VK_SHIFT, 3, 0xff],
[Keys.VK_SPACE, 4, 0xff],
[Keys.VK_5, 8, 0xff],
[Keys.VK_6, 9, 0xff],
[Keys.VK_7, 10, 0xff],
[Keys.VK_1, 11, 0xff],
[Keys.VK_2, 12, 0xff],
[Keys.VK_UP, 13, 0xff],
[Keys.VK_RIGHT, 14, 0xff],
[Keys.VK_LEFT, 15, 0xff],
]);
var AtariVectorPlatform = function(mainElement) {
var self = this;
var cpuFrequency = 1500000.0;
@ -16,25 +30,11 @@ var AtariVectorPlatform = function(mainElement) {
this.__proto__ = new Base6502Platform();
var ASTEROIDS_KEYCODE_MAP = makeKeycodeMap([
[Keys.VK_SHIFT, 3, 0xff],
[Keys.VK_SPACE, 4, 0xff],
[Keys.VK_5, 8, 0xff],
[Keys.VK_6, 9, 0xff],
[Keys.VK_7, 10, 0xff],
[Keys.VK_1, 11, 0xff],
[Keys.VK_2, 12, 0xff],
[Keys.VK_UP, 13, 0xff],
[Keys.VK_RIGHT, 14, 0xff],
[Keys.VK_LEFT, 15, 0xff],
]);
this.getPresets = function() {
return ATARIVEC_PRESETS;
return VECTOR_PRESETS;
}
this.start = function() {
cpu = new jt.M6502();
cpuram = new RAM(0x400);
dvgram = new RAM(0x2000);
//switches[5] = 0xff;
@ -60,7 +60,7 @@ var AtariVectorPlatform = function(mainElement) {
], {gmask:0x7fff})
};
cpu.connectBus(bus);
cpu = self.newCPU(bus);
// create video/audio
video = new VectorVideo(mainElement,1024,1024);
dvg = new DVGStateMachine(bus, video);
@ -68,15 +68,12 @@ var AtariVectorPlatform = function(mainElement) {
video.create();
timer = new AnimationTimer(60, function() {
video.clear();
// 262.5 scanlines per frame
var iaddr = 0x4000;
var iofs = 0;
var debugCond = self.getDebugCallback();
clock = 0;
for (var i=0; i<cpuCyclesPerFrame; i++) {
if (debugCond && debugCond()) { debugCond = null; }
clock++;
if (--nmicount == 0) {
if (--nmicount == 0) {
//console.log("NMI", cpu.saveState());
var n = cpu.setNMIAndWait();
clock += n;
@ -101,7 +98,7 @@ var AtariVectorPlatform = function(mainElement) {
}
this.getRasterPosition = function() {
return {x:0, y:0};
return {x:0, y:0}; // TODO
}
this.isRunning = function() {
@ -140,6 +137,107 @@ var AtariVectorPlatform = function(mainElement) {
}
}
//
var VectorZ80Platform = function(mainElement, proto) {
var self = this;
var cpuFrequency = 3000000.0;
var cpuCyclesPerFrame = Math.round(cpuFrequency/60);
var cpu, cpuram, dvgram, rom, bus, dvg;
var video, audio, timer;
var clock;
var switches = new RAM(16).mem;
this.__proto__ = new BaseZ80Platform();
this.getPresets = function() {
return VECTOR_PRESETS;
}
this.start = function() {
cpuram = new RAM(0x1000);
dvgram = new RAM(0x2000);
//switches[5] = 0xff;
//switches[7] = 0xff;
// bus
bus = {
read: new AddressDecoder([
[0x0, 0x3fff, 0, function(a) { return rom[a]; }],
[0x4000, 0x5fff, 0x1fff, function(a) { return dvgram.mem[a]; }],
[0x6000, 0x6fff, 0xfff, function(a) { return cpuram.mem[a]; }],
[0x7001, 0x7001, 0, function(a) { return ((clock/1000) & 1) ? 0xff : 0x00; }],
[0x7000, 0x7007, 0x7, function(a) { return switches[a]; }],
[0x7400, 0x7407, 0x7, function(a) { return switches[a+8]; }],
]),
write: new AddressDecoder([
[0x7000, 0x7000, 0, function(a,v) { dvg.runUntilHalt(); }],
// TODO: draw asynchronous or allow poll of HALT ($2002)
[0x4000, 0x5fff, 0x1fff, function(a,v) { dvgram.mem[a] = v; }],
[0x6000, 0x6fff, 0xfff, function(a,v) { cpuram.mem[a] = v; }],
])
};
cpu = self.newCPU(bus);
// create video/audio
video = new VectorVideo(mainElement,1024,1024);
dvg = new DVGStateMachine(bus, video);
audio = new SampleAudio(cpuFrequency);
video.create();
timer = new AnimationTimer(60, function() {
video.clear();
self.runCPU(cpu, cpuCyclesPerFrame);
cpu.requestInterrupt();
self.restartDebugState();
});
setKeyboardFromMap(video, switches, ASTEROIDS_KEYCODE_MAP);
}
this.loadROM = function(title, data) {
rom = padBytes(data, 0x4000);
this.reset();
}
this.getRasterPosition = function() {
return {x:0, y:0}; // TODO
}
this.isRunning = function() {
return timer.isRunning();
}
this.pause = function() {
timer.stop();
}
this.resume = function() {
timer.start();
}
this.reset = function() {
cpu.reset();
}
this.readAddress = function(addr) {
return bus.read(addr);
}
this.loadState = function(state) {
cpu.loadState(state.c);
cpuram.mem.set(state.db);
dvgram.mem.set(state.db);
}
this.saveState = function() {
return {
c:cpu.saveState(),
cb:cpuram.mem.slice(0),
db:dvgram.mem.slice(0),
}
}
this.getCPUState = function() {
return cpu.saveState();
}
}
// DIGITAL VIDEO GENERATOR
var DVGStateMachine = function(bus, video) {
var self = this;
var pc = 0;
@ -172,7 +270,7 @@ var DVGStateMachine = function(bus, video) {
this.runUntilHalt = function() {
this.go();
for (var i=0; i<10000; i++) { // TODO
for (var i=0; i<10000; i++) { // TODO: limit execution
if (!running) break;
this.nextInstruction();
}
@ -243,4 +341,7 @@ var DVGStateMachine = function(bus, video) {
}
}
PLATFORMS['atarivec'] = AtariVectorPlatform;
//
PLATFORMS['vector-ataribw'] = AtariVectorPlatform;
PLATFORMS['vector-z80'] = VectorZ80Platform;

View File

@ -246,6 +246,8 @@ var WilliamsPlatform = function(mainElement, proto) {
memwrite_williams(dstaddr, curpix);
}
// TODO
/*
var trace = false;
var _traceinsns = {};
function _trace() {
@ -255,7 +257,7 @@ var WilliamsPlatform = function(mainElement, proto) {
console.log(hex(pc), cpu.getTstates());
}
}
*/
this.start = function() {
ram = new RAM(0xc000);
nvram = new RAM(0x400);
@ -283,7 +285,6 @@ var WilliamsPlatform = function(mainElement, proto) {
timer = new AnimationTimer(60, function() {
if (!self.isRunning())
return;
var debugCond = self.getDebugCallback();
// interrupts happen every 1/4 of the screen
for (var quarter=0; quarter<4; quarter++) {
video_counter = [0x00, 0x3c, 0xbc, 0xfc][quarter];
@ -293,19 +294,7 @@ var WilliamsPlatform = function(mainElement, proto) {
if (cpu.requestInterrupt)
cpu.requestInterrupt();
}
var targetTstates = cpu.getTstates() + cpuCyclesPerFrame/4;
if (debugCond || trace) {
while (cpu.getTstates() < targetTstates) {
_trace();
if (debugCond && debugCond()) {
debugCond = null;
break;
}
cpu.runFrame(cpu.getTstates() + 1);
}
} else {
cpu.runFrame(targetTstates);
}
self.runCPU(cpu, cpuCyclesPerFrame/4);
}
if (screenNeedsRefresh) {
for (var i=0; i<0x9800; i++)
@ -377,6 +366,18 @@ var WilliamsPlatform = function(mainElement, proto) {
var WilliamsZ80Platform = function(mainElement) {
this.__proto__ = new WilliamsPlatform(mainElement, BaseZ80Platform);
this.ramStateToLongString = function(state) {
var blt = state.blt;
var sstart = (blt[2] << 8) + blt[3];
var dstart = (blt[4] << 8) + blt[5];
var w = blt[6] ^ 4; // blitter bug fix
var h = blt[7] ^ 4;
return "\nBLIT"
+ " " + hex(sstart,4) + " " + hex(dstart,4)
+ " w:" + hex(w) + " h:" + hex(h)
+ " f:" + hex(blt[0]) + " s:" + hex(blt[1]);
}
}
PLATFORMS['williams'] = WilliamsPlatform;

View File

@ -25,6 +25,12 @@ var PLATFORM_PARAMS = {
data_start: 0x9000,
data_size: 0x3000,
},
'vector-z80': {
code_start: 0x0,
code_size: 0x4000,
data_start: 0x4000,
data_size: 0x3000,
},
};
var loaded = {}
@ -96,6 +102,7 @@ function match_msvc(s) {
var errline = parseInt(matches[2]);
msvc_errors.push({
line:errline,
type:matches[3],
msg:matches[4]
});
}
@ -417,6 +424,7 @@ function compileCC65(code, platform) {
var errors = [];
var errline = 0;
function match_fn(s) {
console.log(s);
var matches = re_err1.exec(s);
if (matches) {
errline = parseInt(matches[1]);
@ -636,26 +644,38 @@ function compileSDCC(code, platform) {
setupFS(FS, 'sdcc');
//FS.writeFile("main.c", code, {encoding:'utf8'});
msvc_errors = [];
SDCC.callMain(['--vc', '--std-sdcc99', '-mz80', '-Wall',
SDCC.callMain(['--vc', '--std-sdcc99', '-mz80', //'-Wall',
'--c1mode', // '--debug',
//'-S', 'main.c',
//'--asm=z80asm',
'--fomit-frame-pointer', '--opt-code-speed',
'-o', 'main.asm']);
if (msvc_errors.length) {
// ignore if all are warnings (TODO?)
var nwarnings = 0;
for (var err of msvc_errors) {
if (err.type && err.type.startsWith("warning"))
nwarnings++;
}
if (msvc_errors.length && nwarnings < msvc_errors.length) {
return {errors:msvc_errors};
}
try {
var asmout = FS.readFile("main.asm", {encoding:'utf8'});
} catch (e) {
return {errors:[{line:1, msg:e+""}]};
msvc_errors.push({line:1, msg:e+""});
return {errors:msvc_errors};
}
var warnings = msvc_errors;
var result = assemblelinkSDASZ80(asmout, platform, true);
try {
var result = assemblelinkSDASZ80(asmout, platform, true);
} catch (e) {
msvc_errors.push({line:1, msg:e+""});
return {errors:msvc_errors};
}
result.asmlines = result.lines;
result.lines = result.srclines;
result.srclines = null;
result.errors = result.errors.concat(warnings);
//result.errors = result.errors.concat(warnings);
return result;
}

View File

@ -36,6 +36,9 @@
<script src="src/disasm.js"></script>
<script src="src/platform/vcs.js"></script>
<script src="src/platform/mw8080bw.js"></script>
<script src="src/platform/vicdual.js"></script>
<script src="src/platform/williams.js"></script>
<script src="src/platform/galaxian.js"></script>
<script src="test/ui/testemus.js"></script>
<script>

0
tools/p4_to_48pix.py Normal file → Executable file
View File

0
tools/p4_to_pfbytes.py Normal file → Executable file
View File

6
tools/parsebdf3x5.py Normal file → Executable file
View File

@ -41,6 +41,7 @@ output = []
outputlo = []
outputhi = []
for ch in range(lochar,hichar+1):
x = 0
bytes = chars.get(ch)
#bytes = bytes + [0]
if not bytes:
@ -57,9 +58,12 @@ for ch in range(lochar,hichar+1):
def tohex(v):
return '%02x'%v
def tohex2(v):
return '0x%02x'%v
print '\thex ' + string.join(map(tohex,output),'')
print string.join(map(tohex2,output),',')
print '\thex ' + string.join(map(tohex,outputlo),'')
print '\thex ' + string.join(map(tohex,outputhi),'')
print len(output),len(outputlo),len(outputhi)
print len(output),len(outputlo),len(outputhi)

5
tools/parsebdf8.py Normal file → Executable file
View File

@ -36,6 +36,7 @@ with open(sys.argv[1],'r') as f:
x = 0
output = []
invoutput = []
revoutput = []
rotoutput = []
rot2output = []
for ch in range(lochar,hichar+1):
@ -48,6 +49,8 @@ for ch in range(lochar,hichar+1):
invoutput.append(b ^ 0xff)
rotoutput.append(0)
rot2output.append(0)
for i in range(0,8):
revoutput.append(bytes[7-i])
for x in range(0,height):
for y in range(0,height):
#rotoutput[-7+x] |= (((output[-1-y]>>x)&1)<<y)
@ -59,7 +62,7 @@ def tohex(v):
def tohex2(v):
return '0x%02x'%v
for arr in [output,invoutput,rotoutput,rot2output]:
for arr in [output,revoutput,invoutput,rotoutput,rot2output]:
print '\thex ' + string.join(map(tohex,arr),'')
for i in range(0,len(output),height):
print '{', string.join(map(tohex2,arr[i:i+height]),','), '},',

0
tools/pbm_to_c.py Normal file → Executable file
View File