From 1e04a029b7a576cf0a3c71679ae1bbea081acaa6 Mon Sep 17 00:00:00 2001 From: Ben Kurtovic Date: Wed, 9 Jul 2014 21:44:23 -0400 Subject: [PATCH] Standardize error message logging; updates. --- crater.c | 39 ++++++++++++++++++++++----------------- src/errors.c | 13 ------------- src/errors.h | 23 ++++++++++++++++++++++- src/rom.c | 20 ++++++++++++++------ src/rom.h | 7 +++++++ 5 files changed, 65 insertions(+), 37 deletions(-) delete mode 100644 src/errors.c diff --git a/crater.c b/crater.c index b877833..716259a 100644 --- a/crater.c +++ b/crater.c @@ -48,8 +48,7 @@ static void parse_args(int argc, char *argv[]) print_version(); exit(0); } else { - printf("Error: unknown argument: %s\n", argv[i]); - exit(1); + FATAL("unknown argument: %s", argv[i]) } } } @@ -65,7 +64,7 @@ static bool ends_with(char *input, char *suffix) } /* Load all potential ROM files in roms/ into a data structure. */ -static int load_rom_paths(char ***path_ptr) +static int get_rom_paths(char ***path_ptr) { DIR *dirp; struct dirent *entry; @@ -76,19 +75,19 @@ static int load_rom_paths(char ***path_ptr) if (dirp) { paths = malloc(sizeof(char*) * psize); if (!paths) - out_of_memory(); + OUT_OF_MEMORY() while ((entry = readdir(dirp))) { path = entry->d_name; if (ends_with(path, ".gg") || ends_with(path, ".bin")) { if (npaths >= psize) { paths = realloc(paths, sizeof(char*) * (psize *= 2)); if (!paths) - out_of_memory(); + OUT_OF_MEMORY() } paths[npaths] = malloc(sizeof(char*) * (strlen(path) + strlen(ROMS_DIR) + 1)); if (!paths[npaths]) - out_of_memory(); + OUT_OF_MEMORY() strcpy(paths[npaths], ROMS_DIR "/"); strcat(paths[npaths], path); npaths++; @@ -96,18 +95,14 @@ static int load_rom_paths(char ***path_ptr) } closedir(dirp); } else { - if (errno == ENOENT) - printf("Warning: couldn't find roms/ directory.\n"); - else - perror("Warning: couldn't open roms/ directory"); + WARN_ERRNO("couldn't open 'roms/'") } *path_ptr = paths; return npaths; } /* Find all potential ROM files in the roms/ directory, then ask the user which - * one they want to run. - */ + one they want to run. */ static char* get_rom_path_from_user() { char **paths, *path, *input = NULL; @@ -116,7 +111,7 @@ static char* get_rom_path_from_user() size_t size = 0; ssize_t len; - npaths = load_rom_paths(&paths); + npaths = get_rom_paths(&paths); for (i = 0; i < npaths; i++) printf("[%2d] %s\n", i + 1, paths[i]); if (npaths) @@ -126,7 +121,7 @@ static char* get_rom_path_from_user() len = getline(&input, &size, stdin); if (!input) - out_of_memory(); + OUT_OF_MEMORY() if (len > 0 && input[len - 1] == '\n') input[len - 1] = '\0'; index = strtol(input, NULL, 10); @@ -147,14 +142,24 @@ static char* get_rom_path_from_user() int main(int argc, char *argv[]) { char *rom_path; + rom_type *rom; parse_args(argc, argv); + printf("crater: a Sega Game Gear emulator\n\n"); rom_path = argc > 1 ? argv[1] : get_rom_path_from_user(); + if (rom_path[0] == '\0') + FATAL("no image given") - // TODO: main logic hook here - printf("Loading ROM: %s\n", rom_path); - + if (!(rom = open_rom(rom_path))) { + if (errno == ENOMEM) + OUT_OF_MEMORY() + else + FATAL_ERRNO("couldn't load ROM image '%s'", rom_path) + } + printf("Loaded ROM image: %s.\n", rom_path); if (argc <= 1) free(rom_path); + + close_rom(rom); return 0; } diff --git a/src/errors.c b/src/errors.c deleted file mode 100644 index 4d26d34..0000000 --- a/src/errors.c +++ /dev/null @@ -1,13 +0,0 @@ -/* Copyright (C) 2014 Ben Kurtovic - Released under the terms of the MIT License. See LICENSE for details. */ - -#include -#include - -#include "errors.h" - -/* Called after an out-of-memory error. Prints a message and dies. */ -void out_of_memory() { - printf("Error: couldn't allocate memory.\n"); - exit(1); -} diff --git a/src/errors.h b/src/errors.h index a61d03e..aacea74 100644 --- a/src/errors.h +++ b/src/errors.h @@ -3,4 +3,25 @@ #pragma once -void out_of_memory(); +#include +#include +#include + +/* Internal usage only */ + +#define LOG_MSG(level, extra, after, ...) { \ + fprintf(stderr, level ": " __VA_ARGS__); \ + extra; \ + fprintf(stderr, ".\n"); \ + after; \ + } +#define PRINT_ERRNO() fprintf(stderr, ": %s", strerror(errno)) + +/* Public error logging macros */ + +#define FATAL(...) LOG_MSG("Error", {}, exit(EXIT_FAILURE), __VA_ARGS__) +#define FATAL_ERRNO(...) LOG_MSG("Error", PRINT_ERRNO(), exit(EXIT_FAILURE), __VA_ARGS__) +#define WARN(...) LOG_MSG("Warning", {}, {}, __VA_ARGS__) +#define WARN_ERRNO(...) LOG_MSG("Warning", PRINT_ERRNO(), {}, __VA_ARGS__) + +#define OUT_OF_MEMORY() FATAL("couldn't allocate enough memory") diff --git a/src/rom.c b/src/rom.c index 473c1e9..f62e426 100644 --- a/src/rom.c +++ b/src/rom.c @@ -1,22 +1,30 @@ /* Copyright (C) 2014 Ben Kurtovic Released under the terms of the MIT License. See LICENSE for details. */ +#include #include #include "rom.h" -#include "errors.h" -rom_type* load_rom(char *path) +/* Create and return a ROM object located at the given path. Return NULL if + there was an error; errno will be set appropriately. */ +rom_type* open_rom(char *path) { rom_type *rom; + FILE* fp; + + if (!(fp = fopen(path, "r"))) + return NULL; + if (!(rom = malloc(sizeof(rom_type)))) + return NULL; + + // load data from file into a buffer - rom = malloc(sizeof(rom_type)); - if (!rom) - out_of_memory(); return rom; } -void unload_rom(rom_type *rom) +/* Free a ROM object previously created with open_rom(). */ +void close_rom(rom_type *rom) { free(rom); } diff --git a/src/rom.h b/src/rom.h index 8c5867c..63288a1 100644 --- a/src/rom.h +++ b/src/rom.h @@ -3,7 +3,14 @@ #pragma once +/* Structs */ + typedef struct { char* name; char* data; } rom_type; + +/* Functions */ + +rom_type* open_rom(char*); +void close_rom(rom_type*);