1
0
mirror of https://github.com/pevans/erc-c.git synced 2024-06-11 20:29:26 +00:00
erc-c/src/main.c

139 lines
3.1 KiB
C
Raw Permalink Normal View History

2017-12-09 04:12:31 +00:00
/*
* main.c
*
* Here we define the main entry point for the program; we also define a
* couple of functions to run when we start (init) and finish
* (...finish).
*/
2017-11-22 05:24:51 +00:00
#include <stdio.h>
#include <stdlib.h>
2017-12-08 23:06:21 +00:00
#include <string.h>
#include <unistd.h>
2017-11-22 05:24:51 +00:00
#include "apple2/apple2.h"
#include "apple2/draw.h"
2018-04-07 05:33:40 +00:00
#include "apple2/event.h"
2017-11-22 05:24:51 +00:00
#include "log.h"
2017-12-08 23:06:21 +00:00
#include "option.h"
#include "vm_di.h"
#include "vm_screen.h"
2017-11-22 05:24:51 +00:00
2017-12-06 22:43:30 +00:00
/*
* This function will establish the base environment that we want to use
* while we execute.
*/
2017-11-22 05:24:51 +00:00
static void
2017-12-08 23:06:21 +00:00
init(int argc, char **argv)
2017-11-22 05:24:51 +00:00
{
2017-12-08 23:06:21 +00:00
int options_ok;
// If the option_parse() function returns zero, that means that it's
// signaled to us that we should stop now. Whether that means we are
// stopping in _error_ (bad input), or just because you asked for
// --help, is not really specified. We exit with a non-zero error
// code in any case.
options_ok = option_parse(argc, argv);
if (options_ok == 0) {
const char *err = option_get_error();
if (strlen(err) > 0) {
fprintf(stderr, "%s\n", err);
option_print_help();
}
exit(1);
}
vm_di_set(VM_OUTPUT, stdout);
2018-03-30 02:42:38 +00:00
FILE *stream = fopen(LOG_FILENAME, "w");
if (stream == NULL) {
perror("Can't open log file");
}
log_open(stream);
if (vm_screen_init() != OK) {
fprintf(stderr, "Couldn't initialize video\n");
exit(1);
}
2017-11-22 05:24:51 +00:00
}
2017-12-06 22:43:30 +00:00
/*
* And this is the teardown function.
*/
2017-11-22 05:24:51 +00:00
static void
finish()
{
FILE *stream[3];
2017-12-08 23:09:58 +00:00
stream[0] = (FILE *)vm_di_get(VM_DISK1);
stream[1] = (FILE *)vm_di_get(VM_DISK2);
stream[2] = (FILE *)vm_di_get(VM_DISASM_LOG);
for (int i = 0; i < 3; i++) {
if (stream[i]) {
fclose(stream[i]);
2017-12-08 23:09:58 +00:00
}
}
2017-11-22 05:24:51 +00:00
log_close();
vm_screen_finish();
2017-11-22 05:24:51 +00:00
}
2017-12-06 22:43:30 +00:00
/*
* This is what will run when the program begins, if you were new to how
* C works.
*/
2017-11-22 05:24:51 +00:00
int
main(int argc, char **argv)
{
apple2 *mach;
2017-12-17 22:42:05 +00:00
vm_screen *screen;
int err;
2017-12-08 23:06:21 +00:00
init(argc, argv);
2017-11-22 05:24:51 +00:00
2017-12-06 22:43:30 +00:00
// When we exit, we want to wrap up a few loose ends. This syscall
// will ensure that `finish()` runs whether we return from main
// successfully or if we run `exit()` from elsewhere in the program.
2017-11-22 05:24:51 +00:00
atexit(finish);
int *width = (int *)vm_di_get(VM_WIDTH);
int *height = (int *)vm_di_get(VM_HEIGHT);
// Let's build the basic machine, using the width and height
// indicated by the user.
mach = apple2_create(*width, *height);
vm_di_set(VM_MACHINE, mach);
// FIXME: eh; what if we have a machine which doesn't define the cpu
// field? Alternatively, we could require all implemented machines
// _to_ define a cpu field.
vm_di_set(VM_CPU, mach->cpu);
apple2_event_init();
// Ok, it's time to boot this up!
err = apple2_boot(mach);
if (err != OK) {
fprintf(stderr, "Bootup failed!\n");
exit(1);
}
apple2_draw_40col(mach);
// This will run for as long as we want to hang out in the emulated
// machine.
apple2_run_loop(mach);
// We're all done, so let's tear everything down.
apple2_free(mach);
2017-12-06 22:43:30 +00:00
// ha ha ha ha #nervous #laughter
2017-12-06 22:45:16 +00:00
printf("Hello, world\n");
2017-11-22 05:24:51 +00:00
}