summaryrefslogtreecommitdiff
path: root/emulator.cpp
diff options
context:
space:
mode:
authorOxore <oxore@protonmail.com>2022-08-27 11:53:25 +0300
committerOxore <oxore@protonmail.com>2022-08-27 11:53:25 +0300
commit903b8dbcaad887f6e14cc8cffc22ddda08dc9f85 (patch)
tree01254a3d08791a71dea3e7f987b859ae58921d35 /emulator.cpp
parentc1b9fead37e32be1b2f97d5be2d8254fdc16d307 (diff)
Move to C++ completely
Diffstat (limited to 'emulator.cpp')
-rw-r--r--emulator.cpp102
1 files changed, 102 insertions, 0 deletions
diff --git a/emulator.cpp b/emulator.cpp
new file mode 100644
index 0000000..0e3fb29
--- /dev/null
+++ b/emulator.cpp
@@ -0,0 +1,102 @@
+/* SPDX-License-Identifier: Unlicense
+ */
+
+#include "bus.hpp"
+#include "musashi-m68k/m68k.h"
+
+#include <cstdio>
+#include <cstdlib>
+#include <cstdarg>
+#include <ctime>
+
+#if !defined(DEBUG_TRACE_INSTRUCTIONS)
+# define DEBUG_TRACE_INSTRUCTIONS 0
+#endif
+
+static void exit_error(const char* fmt, ...)
+{
+ va_list args;
+ va_start(args, fmt);
+ vfprintf(stderr, fmt, args);
+ va_end(args);
+ fprintf(stderr, "\n");
+ exit(EXIT_FAILURE);
+}
+
+/* Called when the CPU pulses the RESET line */
+void m68k_reset_callback(void)
+{
+ // TODO
+}
+
+/* Called when the CPU acknowledges an interrupt */
+int m68k_irq_ack(int level)
+{
+ (void) level;
+ // TODO
+ exit_error("IRQ ack");
+ return M68K_INT_ACK_SPURIOUS;
+}
+
+static void make_hex(char* buff, unsigned int pc, unsigned int length)
+{
+ char* ptr = buff;
+
+ for (;length>0;length -= 2)
+ {
+ sprintf(ptr, "%04x", m68k_read_disassembler_16(pc));
+ pc += 2;
+ ptr += 4;
+ if (length > 2)
+ *ptr++ = ' ';
+ }
+}
+
+void m68k_instr_callback(int pc)
+{
+ if (!DEBUG_TRACE_INSTRUCTIONS)
+ return;
+ char buff[100];
+ unsigned int instr_size =
+ m68k_disassemble(buff, pc, M68K_CPU_TYPE_68000);
+ char buff2[100];
+ make_hex(buff2, pc, instr_size);
+ printf("E %08X: %-20s: %s\n", pc, buff2, buff);
+ fflush(stdout);
+}
+
+int main(int argc, char* argv[])
+{
+ if (argc != 2)
+ {
+ printf("Usage: sim <program file>\n");
+ exit(-1);
+ }
+
+ FILE* const fhandle = fopen(argv[1], "rb");
+
+ if (fhandle == NULL)
+ exit_error("Unable to open %s", argv[1]);
+
+ const size_t fread_ret = fread(g_rom, 1, ROM_SIZE, fhandle);
+ if (fread_ret <= 0)
+ exit_error("Error reading %s", argv[1]);
+ printf("Read into ROM %zu bytes\n", fread_ret);
+
+ m68k_init();
+ m68k_set_cpu_type(M68K_CPU_TYPE_68000);
+ m68k_pulse_reset();
+
+ while (1)
+ {
+ // Values to execute determine the interleave rate.
+ // Smaller values allow for more accurate interleaving with multiple
+ // devices/CPUs but is more processor intensive.
+ // 100000 is usually a good value to start at, then work from there.
+
+ // Note that I am not emulating the correct clock speed!
+ m68k_execute(100000);
+ }
+
+ return 0;
+}