change clock to be 14mhz, variable for CPU

This commit is contained in:
Brad Grantham 2018-07-30 16:01:39 -07:00
parent 064a9704d6
commit ea3930a8f0
2 changed files with 100 additions and 88 deletions

View File

@ -43,16 +43,24 @@ const float paddle_max_pulse_seconds = .00282;
typedef unsigned long long clk_t; typedef unsigned long long clk_t;
struct system_clock struct system_clock
{ {
clk_t value = 0; clk_t clock_cpu = 0; // Actual CPU and memory clocks, variable rate
operator clk_t() const { return value; } clk_t clock_14mhz = 0; // Fixed 14.31818MHz clock
clk_t operator+=(clk_t i) { return value += i; } clk_t phase_hpe = 0; // Phase of CPU clock within horizontal lines
clk_t operator++(int) { clk_t v = value; value ++; return v; } operator clk_t() const { return clock_14mhz; }
void add_cpu_cycles(clk_t elapsed_cpu)
{
clock_cpu += elapsed_cpu;
clock_14mhz += elapsed_cpu * 14 + (elapsed_cpu + phase_hpe) / 65 * 2;
phase_hpe = (phase_hpe + elapsed_cpu) % 65;
if(0) printf("added %llu, new cpu clock %llu, 14mhz clock %llu, phase %llu\n", elapsed_cpu, clock_cpu, clock_14mhz, phase_hpe);
}
} clk; } clk;
// was 1023000 // was 1023000
// 3.579545 * 4 / 14 // 3.579545 * 4 / 14
// 1.02272714285714285714 // 1.02272714285714285714
const int machine_clock_rate = 1022727; const int machine_clock_rate = 14318180;
bool read_blob(char *name, unsigned char *b, size_t sz) bool read_blob(char *name, unsigned char *b, size_t sz)
{ {
@ -1067,22 +1075,22 @@ struct CPU6502
} }
int cycles[256] = int cycles[256] =
{ {
7, 6, -1, -1, -1, 3, 5, -1, 3, 2, 2, -1, -1, 4, 6, -1, /* 0x0- */ 7, 6, -1, -1, -1, 3, 5, -1, 3, 2, 2, -1, -1, 4, 6, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0x1- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, 2, -1, -1, 4, 7, -1,
6, 6, -1, -1, 3, 3, 5, -1, 4, 2, 2, -1, 4, 4, 6, -1, /* 0x2- */ 6, 6, -1, -1, 3, 3, 5, -1, 4, 2, 2, -1, 4, 4, 6, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0x3- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, 2, -1, -1, 4, 7, -1,
6, 6, -1, -1, -1, 3, 5, -1, 3, 2, 2, -1, 3, 4, 6, -1, /* 0x4- */ 6, 6, -1, -1, -1, 3, 5, -1, 3, 2, 2, -1, 3, 4, 6, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0x5- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1,
6, 6, -1, -1, -1, 3, 5, -1, 4, 2, 2, -1, 5, 4, 6, -1, /* 0x6- */ 6, 6, -1, -1, -1, 3, 5, -1, 4, 2, 2, -1, 5, 4, 6, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0x7- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1,
2, 6, -1, -1, 3, 3, 3, -1, 2, -1, 2, -1, 4, 4, 4, -1, /* 0x8- */ 2, 6, -1, -1, 3, 3, 3, -1, 2, -1, 2, -1, 4, 4, 4, -1,
2, 6, -1, -1, 4, 4, 4, -1, 2, 5, 2, -1, -1, 5, -1, -1, /* 0x9- */ 2, 6, 5, -1, 4, 4, 4, -1, 2, 5, 2, -1, -1, 5, -1, -1,
2, 6, 2, -1, 3, 3, 3, -1, 2, 2, 2, -1, 4, 4, 4, -1, /* 0xA- */ 2, 6, 2, -1, 3, 3, 3, -1, 2, 2, 2, -1, 4, 4, 4, -1,
2, 5, -1, -1, 4, 4, 4, -1, 2, 4, 2, -1, 4, 4, 4, -1, /* 0xB- */ 2, 5, -1, -1, 4, 4, 4, -1, 2, 4, 2, -1, 4, 4, 4, -1,
2, 6, -1, -1, 3, 3, 5, -1, 2, 2, 2, -1, 4, 4, 3, -1, /* 0xC- */ 2, 6, -1, -1, 3, 3, 5, -1, 2, 2, 2, -1, 4, 4, 3, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0xD- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1,
2, 6, -1, -1, 3, 3, 5, -1, 2, 2, 2, -1, 4, 4, 6, -1, /* 0xE- */ 2, 6, -1, -1, 3, 3, 5, -1, 2, 2, 2, -1, 4, 4, 6, -1,
2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1, /* 0xF- */ 2, 5, -1, -1, -1, 4, 6, -1, 2, 4, -1, -1, -1, 4, 7, -1,
}; };
enum Operand { enum Operand {
A, A,
@ -1261,7 +1269,7 @@ struct CPU6502
case 0xFE: { // INC abs, X case 0xFE: { // INC abs, X
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x;
if((addr - x) / 256 != addr / 256) if((addr - x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, m = bus.read(addr) + 1); set_flags(N | Z, m = bus.read(addr) + 1);
bus.write(addr, m); bus.write(addr, m);
break; break;
@ -1301,9 +1309,9 @@ struct CPU6502
case 0x10: { // BPL case 0x10: { // BPL
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(!isset(N)) { if(!isset(N)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1312,9 +1320,9 @@ struct CPU6502
case 0x50: { // BVC case 0x50: { // BVC
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(!isset(V)) { if(!isset(V)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1323,9 +1331,9 @@ struct CPU6502
case 0x70: { // BVS case 0x70: { // BVS
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(isset(V)) { if(isset(V)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1334,9 +1342,9 @@ struct CPU6502
case 0x30: { // BMI case 0x30: { // BMI
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(isset(N)) { if(isset(N)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1345,9 +1353,9 @@ struct CPU6502
case 0x90: { // BCC case 0x90: { // BCC
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(!isset(C)) { if(!isset(C)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1356,9 +1364,9 @@ struct CPU6502
case 0xB0: { // BCS case 0xB0: { // BCS
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(isset(C)) { if(isset(C)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1367,9 +1375,9 @@ struct CPU6502
case 0xD0: { // BNE case 0xD0: { // BNE
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(!isset(Z)) { if(!isset(Z)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1378,9 +1386,9 @@ struct CPU6502
case 0xF0: { // BEQ case 0xF0: { // BEQ
int rel = (read_pc_inc(bus) + 128) % 256 - 128; int rel = (read_pc_inc(bus) + 128) % 256 - 128;
if(isset(Z)) { if(isset(Z)) {
clk++; clk.add_cpu_cycles(1);
if((pc + rel) / 256 != pc / 256) if((pc + rel) / 256 != pc / 256)
clk++; clk.add_cpu_cycles(1);
pc += rel; pc += rel;
} }
break; break;
@ -1405,7 +1413,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = bus.read(addr)); set_flags(N | Z, a = bus.read(addr));
break; break;
} }
@ -1420,7 +1428,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + x); m = bus.read(addr + x);
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
flag_change(C, m <= a); flag_change(C, m <= a);
set_flags(N | Z, m = a - m); set_flags(N | Z, m = a - m);
break; break;
@ -1430,7 +1438,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + y); m = bus.read(addr + y);
if((addr + y) / 256 != addr / 256) if((addr + y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
flag_change(C, m <= a); flag_change(C, m <= a);
set_flags(N | Z, m = a - m); set_flags(N | Z, m = a - m);
break; break;
@ -1440,7 +1448,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
set_flags(N | Z, a = bus.read(addr + y)); set_flags(N | Z, a = bus.read(addr + y));
if((addr + y) / 256 != addr / 256) if((addr + y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
break; break;
} }
@ -1448,7 +1456,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
set_flags(N | Z, y = bus.read(addr + x)); set_flags(N | Z, y = bus.read(addr + x));
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
break; break;
} }
@ -1456,7 +1464,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
set_flags(N | Z, a = bus.read(addr + x)); set_flags(N | Z, a = bus.read(addr + x));
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
break; break;
} }
@ -1500,7 +1508,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xff) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xff) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
int borrow = isset(C) ? 0 : 1; int borrow = isset(C) ? 0 : 1;
if(isset(D)) { if(isset(D)) {
@ -1520,7 +1528,7 @@ struct CPU6502
case 0xF9: { // SBC abs, Y case 0xF9: { // SBC abs, Y
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
unsigned char m = bus.read(addr); unsigned char m = bus.read(addr);
int borrow = isset(C) ? 0 : 1; int borrow = isset(C) ? 0 : 1;
if(isset(D)) { if(isset(D)) {
@ -1540,7 +1548,7 @@ struct CPU6502
case 0xFD: { // SBC abs, X case 0xFD: { // SBC abs, X
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x;
if((addr - x) / 256 != addr / 256) if((addr - x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
unsigned char m = bus.read(addr); unsigned char m = bus.read(addr);
int borrow = isset(C) ? 0 : 1; int borrow = isset(C) ? 0 : 1;
if(isset(D)) { if(isset(D)) {
@ -1596,7 +1604,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
int carry = isset(C) ? 1 : 0; int carry = isset(C) ? 1 : 0;
if(isset(D)) { if(isset(D)) {
@ -1652,7 +1660,7 @@ struct CPU6502
case 0x7D: { // ADC abs, X case 0x7D: { // ADC abs, X
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x;
if((addr - x) / 256 != addr / 256) if((addr - x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
int carry = isset(C) ? 1 : 0; int carry = isset(C) ? 1 : 0;
if(isset(D)) { if(isset(D)) {
@ -1672,7 +1680,7 @@ struct CPU6502
case 0x79: { // ADC abs, Y case 0x79: { // ADC abs, Y
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
int carry = isset(C) ? 1 : 0; int carry = isset(C) ? 1 : 0;
if(isset(D)) { if(isset(D)) {
@ -1817,7 +1825,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + y); m = bus.read(addr + y);
if((addr + y) / 256 != addr / 256) if((addr + y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = a | m); set_flags(N | Z, a = a | m);
break; break;
} }
@ -1826,7 +1834,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + x); m = bus.read(addr + x);
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = a | m); set_flags(N | Z, a = a | m);
break; break;
} }
@ -1835,7 +1843,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
set_flags(N | Z, a = a | m); set_flags(N | Z, a = a | m);
break; break;
@ -1864,7 +1872,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = a & bus.read(addr)); set_flags(N | Z, a = a & bus.read(addr));
break; break;
} }
@ -1873,7 +1881,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
set_flags(N | Z, a = a & bus.read(addr + x)); set_flags(N | Z, a = a & bus.read(addr + x));
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
break; break;
} }
@ -1881,7 +1889,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
set_flags(N | Z, a = a & bus.read(addr + y)); set_flags(N | Z, a = a & bus.read(addr + y));
if((addr + y) / 256 != addr / 256) if((addr + y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
break; break;
} }
@ -2094,7 +2102,7 @@ struct CPU6502
case 0xBE: { // LDX case 0xBE: { // LDX
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, x = bus.read(addr)); set_flags(N | Z, x = bus.read(addr));
break; break;
} }
@ -2197,7 +2205,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + x); m = bus.read(addr + x);
if((addr + x) / 256 != addr / 256) if((addr + x) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = a ^ m); set_flags(N | Z, a = a ^ m);
break; break;
} }
@ -2206,7 +2214,7 @@ struct CPU6502
int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256;
m = bus.read(addr + y); m = bus.read(addr + y);
if((addr + y) / 256 != addr / 256) if((addr + y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
set_flags(N | Z, a = a ^ m); set_flags(N | Z, a = a ^ m);
break; break;
} }
@ -2227,7 +2235,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
set_flags(N | Z, a = a ^ m); set_flags(N | Z, a = a ^ m);
break; break;
@ -2237,7 +2245,7 @@ struct CPU6502
unsigned char zpg = read_pc_inc(bus); unsigned char zpg = read_pc_inc(bus);
int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y;
if((addr - y) / 256 != addr / 256) if((addr - y) / 256 != addr / 256)
clk++; clk.add_cpu_cycles(1);
m = bus.read(addr); m = bus.read(addr);
flag_change(C, m <= a); flag_change(C, m <= a);
set_flags(N | Z, m = a - m); set_flags(N | Z, m = a - m);
@ -2395,7 +2403,7 @@ struct CPU6502
printf("%s ", (p & C) ? "C" : "c"); printf("%s ", (p & C) ? "C" : "c");
printf("S:%02X (%02X %02X %02X ...) PC:%04X (%02X %02X %02X ...)\n", s, s0, s1, s2, pc, pc0, pc1, pc2); printf("S:%02X (%02X %02X %02X ...) PC:%04X (%02X %02X %02X ...)\n", s, s0, s1, s2, pc, pc0, pc1, pc2);
} }
clk += cycles[inst]; clk.add_cpu_cycles(cycles[inst]);
} }
}; };
@ -2608,7 +2616,7 @@ enum APPLE2Einterface::EventType process_events(MAINboard *board, bus_frontend&
cpu.reset(bus); cpu.reset(bus);
} else if(e.type == APPLE2Einterface::REBOOT) { } else if(e.type == APPLE2Einterface::REBOOT) {
bus.reset(); bus.reset();
board->momentary_open_apple(machine_clock_rate / 5); board->momentary_open_apple(machine_clock_rate / (5 * 14));
if(use_fake6502) if(use_fake6502)
reset6502(); reset6502();
else else
@ -2768,7 +2776,7 @@ int main(int argc, char **argv)
if(use_fake6502) { if(use_fake6502) {
clockticks6502 = 0; clockticks6502 = 0;
step6502(); step6502();
clk += clockticks6502; clk.add_cpu_cycles(clockticks6502);
} else { } else {
cpu.cycle(bus); cpu.cycle(bus);
} }
@ -2833,7 +2841,7 @@ int main(int argc, char **argv)
if(use_fake6502) { if(use_fake6502) {
clockticks6502 = 0; clockticks6502 = 0;
step6502(); step6502();
clk += clockticks6502; clk.add_cpu_cycles(clockticks6502);
} else { } else {
cpu.cycle(bus); cpu.cycle(bus);
} }

50
notes
View File

@ -3,34 +3,38 @@ per-scanline modes
Not for DHGR or 80-col but they're probably just same address twice alternating banks Not for DHGR or 80-col but they're probably just same address twice alternating banks
tracking clock and reporting video memory contents tracking clock and reporting video memory contents
clock clock
actual fastest clock is 14.31818MHz
one tick of ~1MHz clock maps to one tick of address counter one tick of ~1MHz clock maps to one tick of address counter
so is 7 HGR bits or one GR/TEXT horizontal cell so is 7 HGR bits or one GR/TEXT horizontal cell
unsigned long would overflow after 20 minutes "most 6502 cycles are 978 nS long [14 14mhz clocks], but every 65th cycle is 1117 nS long [16 14mhz clocks]."
But could modulo byteclock by 14318180 at interface update source clock is 14.31818MHz
time and not overflow unsigned long would overflow after 20 minutes
as long as it doesn't take longer than 20 minutes between calls to APPLE2Einterface::iterate Could modulo byteclock by 14318180 at iterate() and not overflow
than 20 minutes...) as long as it doesn't take longer than 20 minutes between calls to APPLE2Einterface::iterate than 20 minutes...)
Want current CPU clock count after "cycle()" - map that to 14MHz clocks, can map that to actual wall clock Could have clk be in 14MHz ticks.
"most 6502 cycles are 978 nS long [14 14mhz clocks], but every 65th cycle is 1117 nS long [16 14mhz clocks]." unsigned long long will last 40853 years (could be slow on embedded systems)
So wall clock time is (((clockcount / 65) * 912 + clockcount * 16) / 14318180 seconds) but only starting from 0 Keep track of phase at clk delta time, and add 14 usually but 16 every 65th
so need seconds from t_phase to t_clocks in clock counts where t_phase != 0 Then wall clock is just always ticks / 14318180.0
initially t_phase = 0 phase_hpe initially 0
t_elapsed_14mhz = t_clocks * 14 + (t_clocks + t_phase) / 65 * 16 add_cpu_cycles(elapsed_cpu) {
t = t + t_elapsed_14mhz / 14318180 clock_cpu += elapsed_cpu
t_phase = (t_phase + t_clocks) % 65 clock_14mhz = elapsed_cpu * 14 + (elapsed_cpu + phase_hpe) / 65 * 16
So clk would remain machine clock cycles, but actual wall clock time won't be known until calculated phase_hpe = (phase_hpe + elapsed_cpu) % 65
Could increment wall clock at clk++ depending on phase, but then probably accumulate error because 14MHz clock rate is so high }
Current CPU clk (in 1MHz CPU cycles) : clock_14mhz is 14mhz ticks
is used to determine to which audio sample (at libAO sample rate) in the audio waveform we should fill clock_cpu is CPU clocks, averaging 1.023MHz
phase_hpe is clock_cpu within horizontal line
Current CPU clk (in 1MHz CPU cycles) is used for
which audio sample (at libAO sample rate) in the audio waveform we should fill
OK - should work with higher fixed rate OK - should work with higher fixed rate
is used to mark after how many cycles the open apple key should be raised mark after how many cycles the open apple key should be raised
checked against clk in OK - should work with higher fixed rate
HM - need to convert to wall clock? mark paddle timer
doesn't need to be that OK - should work with higher fixed rate
incrementing CPU instruction cycles
OK - call add_cpu_cycles()
address generator address generator
honor softswitches honor softswitches
convert byteclock to address convert clock_cpu to address
read empty memory address on bus no longer fails but instead read empty memory address on bus no longer fails but instead
generate address, get byte from RAM and return it generate address, get byte from RAM and return it
recording softswitch mode changes recording softswitch mode changes