118 lines
2.3 KiB
C
118 lines
2.3 KiB
C
#include <stdio.h>
|
|
#include <unistd.h>
|
|
#include <stdlib.h>
|
|
#include <fcntl.h>
|
|
#include <string.h>
|
|
#include "rifle/state.h"
|
|
#include "rifle/parser.h"
|
|
|
|
/* Compiler version */
|
|
#define RIFLE_VERSION "0.0.2"
|
|
|
|
static const char *output_fmt = "elf64";
|
|
static const char *output_file = "a.out";
|
|
static bool asm_only = false;
|
|
|
|
static void
|
|
help(void)
|
|
{
|
|
printf(
|
|
"The Rifle compiler - rack, bang bang\n"
|
|
"------------------------------------\n"
|
|
"[-h] Display this help menu\n"
|
|
"[-v] Display the version\n"
|
|
"[-a] Assembly output\n"
|
|
"[-f] Output format\n"
|
|
"[-o] Output file\n"
|
|
);
|
|
}
|
|
|
|
static void
|
|
version(void)
|
|
{
|
|
printf(
|
|
"The Rifle compiler - rack, bang bang\n"
|
|
"------------------------------------\n"
|
|
"Copyright (c) 2026, Ian Moffett\n"
|
|
"Version v%s\n",
|
|
RIFLE_VERSION
|
|
);
|
|
}
|
|
|
|
static int
|
|
compile(const char *in_path)
|
|
{
|
|
struct rifle_state state;
|
|
char buf[256];
|
|
|
|
if (rifle_state_init(&state, in_path) < 0) {
|
|
return -1;
|
|
}
|
|
|
|
for (int i = 0; i < 2; ++i) {
|
|
if (parser_parse(&state) < 0) {
|
|
rifle_state_destroy(&state);
|
|
return -1;
|
|
}
|
|
}
|
|
|
|
rifle_state_destroy(&state);
|
|
if (!asm_only) {
|
|
snprintf(
|
|
buf,
|
|
sizeof(buf),
|
|
"nasm -f%s %s -o %s",
|
|
output_fmt,
|
|
ASMOUT,
|
|
output_file
|
|
);
|
|
|
|
system(buf);
|
|
remove(ASMOUT);
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
int
|
|
main(int argc, char **argv)
|
|
{
|
|
size_t files_compiled = 0;
|
|
int opt;
|
|
|
|
/* Begin parsing command line options */
|
|
while ((opt = getopt(argc, argv, "hvaf:o:")) != -1) {
|
|
switch (opt) {
|
|
case 'h':
|
|
help();
|
|
return -1;
|
|
case 'v':
|
|
version();
|
|
return -1;
|
|
case 'a':
|
|
asm_only = true;
|
|
break;
|
|
case 'o':
|
|
output_file = strdup(optarg);
|
|
break;
|
|
case 'f':
|
|
output_fmt = strdup(optarg);
|
|
break;
|
|
}
|
|
}
|
|
|
|
while (optind < argc) {
|
|
++files_compiled;
|
|
if (compile(argv[optind++]) < 0) {
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (files_compiled == 0) {
|
|
printf("fatal: no input files\n");
|
|
return -1;
|
|
}
|
|
|
|
return 0;
|
|
}
|