diff --git a/Makefile b/Makefile index cc2f55d6..59b8d707 100644 --- a/Makefile +++ b/Makefile @@ -15,13 +15,15 @@ PNGCFLAGS := `${PKG_CONFIG} --static --cflags libpng` PNGLDFLAGS := `${PKG_CONFIG} --static --libs-only-L libpng` PNGLDLIBS := `${PKG_CONFIG} --static --libs-only-l libpng` +VERSION_STRING := `git describe --tags --dirty --always 2>/dev/null` + WARNFLAGS := -Wall -Werror # Overridable CFLAGS CFLAGS := -g # Non-overridable CFLAGS REALCFLAGS := ${CFLAGS} ${WARNFLAGS} -std=c99 -D_POSIX_C_SOURCE=200809L \ - -Iinclude + -Iinclude -DBUILD_VERSION_STRING=\"${VERSION_STRING}\" YFLAGS := LFLAGS := --nounistd @@ -49,7 +51,9 @@ rgbasm_obj := \ src/extern/err.o \ src/extern/reallocarray.o \ src/extern/strlcpy.o \ - src/extern/strlcat.o + src/extern/strlcat.o \ + src/extern/version.o + src/asm/asmy.h: src/asm/asmy.c src/asm/locallex.o src/asm/globlex.o src/asm/lexer.o: src/asm/asmy.h @@ -66,20 +70,23 @@ rgblink_obj := \ src/link/parser.o \ src/link/script.o \ src/link/symbol.o \ - src/extern/err.o + src/extern/err.o \ + src/extern/version.o src/link/parser.h: src/link/parser.c src/link/lexer.o: src/link/parser.h rgbfix_obj := \ src/fix/main.o \ - src/extern/err.o + src/extern/err.o \ + src/extern/version.o rgbgfx_obj := \ src/gfx/gb.o \ src/gfx/main.o \ src/gfx/makepng.o \ - src/extern/err.o + src/extern/err.o \ + src/extern/version.o rgbasm: ${rgbasm_obj} $Q${CC} ${REALCFLAGS} -o $@ ${rgbasm_obj} -lm diff --git a/include/extern/version.h b/include/extern/version.h new file mode 100644 index 00000000..998f4652 --- /dev/null +++ b/include/extern/version.h @@ -0,0 +1,21 @@ +/* + * Copyright (C) 2017 Antonio Nino Diaz + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +#define PACKAGE_VERSION_MAJOR (0) +#define PACKAGE_VERSION_MINOR (3) +#define PACKAGE_VERSION_PATCH (2) + +const char * get_package_version_string(void); diff --git a/src/asm/main.c b/src/asm/main.c index c35bf528..2d826ce9 100644 --- a/src/asm/main.c +++ b/src/asm/main.c @@ -12,6 +12,7 @@ #include "asm/main.h" #include "extern/err.h" #include "extern/reallocarray.h" +#include "extern/version.h" int yyparse(void); void setuplex(void); @@ -278,7 +279,7 @@ static void usage(void) { printf( -"Usage: rgbasm [-hvE] [-b chars] [-Dname[=value]] [-g chars] [-i path]\n" +"Usage: rgbasm [-EhVvw] [-b chars] [-Dname[=value]] [-g chars] [-i path]\n" " [-M dependfile] [-o outfile] [-p pad_value] file.asm\n"); exit(1); } @@ -324,7 +325,7 @@ main(int argc, char *argv[]) newopt = CurrentOptions; - while ((ch = getopt(argc, argv, "b:D:g:hi:M:o:p:vEw")) != -1) { + while ((ch = getopt(argc, argv, "b:D:g:hi:M:o:p:EVvw")) != -1) { switch (ch) { case 'b': if (strlen(optarg) == 2) { @@ -338,6 +339,9 @@ main(int argc, char *argv[]) case 'D': opt_AddDefine(optarg); break; + case 'E': + newopt.exportall = true; + break; case 'g': if (strlen(optarg) == 4) { newopt.gbgfx[0] = optarg[1]; @@ -373,17 +377,18 @@ main(int argc, char *argv[]) "between 0 and 0xFF"); } break; + case 'V': + printf("rgbasm %s\n", get_package_version_string()); + exit(0); case 'v': newopt.verbose = true; break; - case 'E': - newopt.exportall = true; - break; case 'w': newopt.warnings = false; break; default: usage(); + /* NOTREACHED */ } } argc -= optind; diff --git a/src/asm/rgbasm.1 b/src/asm/rgbasm.1 index 2d45084e..784e0794 100644 --- a/src/asm/rgbasm.1 +++ b/src/asm/rgbasm.1 @@ -20,7 +20,7 @@ .Nd Game Boy assembler .Sh SYNOPSIS .Nm rgbasm -.Op Fl Ehvw +.Op Fl EhVvw .Op Fl b Ar chars .Op Fl D Ar name Ns Op = Ns Ar value .Op Fl g Ar chars @@ -72,6 +72,8 @@ Write an object file to the given filename. .It Fl p Ar pad_value When padding an image, pad with this value. The default is 0x00. +.It Fl V +Print the version of the program and exit. .It Fl v Be verbose. .It Fl w diff --git a/src/asm/rgbasm.5 b/src/asm/rgbasm.5 index 34b5a501..c9469890 100644 --- a/src/asm/rgbasm.5 +++ b/src/asm/rgbasm.5 @@ -549,6 +549,9 @@ The following symbols are defined by the assembler: .It Ic EQU Ta Ic __UTC_HOUR__ Ta Ta Current hour, 0-23 .It Ic EQU Ta Ic __UTC_MINUTE__ Ta Ta Current minute, 0-59 .It Ic EQU Ta Ic __UTC_SECOND__ Ta Ta Current second, 0-59 +.It Ic EQU Ta Ic __RGBDS_MAJOR__ Ta Ta Major version number of RGBDS. +.It Ic EQU Ta Ic __RGBDS_MINOR__ Ta Ta Minor version number of RGBDS. +.It Ic EQU Ta Ic __RGBDS_PATCH__ Ta Ta Patch version number of RGBDS. .El .Pp .Sh DEFINING DATA @@ -1012,6 +1015,15 @@ machine. .It Sx __ISO_8601_UTC__ .It Sx __LINE__ .It Sx __TIME__ +.It Sx __RGBDS_MAJOR__ +.It Sx __RGBDS_MINOR__ +.It Sx __RGBDS_PATCH__ +.It Sx __UTC_YEAR__ +.It Sx __UTC_MONTH__ +.It Sx __UTC_DAY__ +.It Sx __UTC_HOUR__ +.It Sx __UTC_MINUTE__ +.It Sx __UTC_SECOND__ .It Sx _NARG .It Sx _PI .It Sx _RS diff --git a/src/asm/symbol.c b/src/asm/symbol.c index 43491584..23d59b38 100644 --- a/src/asm/symbol.c +++ b/src/asm/symbol.c @@ -13,6 +13,7 @@ #include "asm/mymath.h" #include "asm/output.h" #include "extern/err.h" +#include "extern/version.h" struct sSymbol *tHashedSymbols[HASHSIZE]; struct sSymbol *pScope = NULL; @@ -848,6 +849,9 @@ sym_PrepPass2(void) sym_AddString("__UTC_HOUR__", SavedHOUR); sym_AddString("__UTC_MINUTE__", SavedMINUTE); sym_AddString("__UTC_SECOND__", SavedSECOND); + sym_AddEqu("__RGBDS_MAJOR__", PACKAGE_VERSION_MAJOR); + sym_AddEqu("__RGBDS_MINOR__", PACKAGE_VERSION_MINOR); + sym_AddEqu("__RGBDS_PATCH__", PACKAGE_VERSION_PATCH); sym_AddSet("_RS", 0); sym_AddEqu("_NARG", 0); diff --git a/src/extern/version.c b/src/extern/version.c new file mode 100644 index 00000000..4a23e562 --- /dev/null +++ b/src/extern/version.c @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2017 Antonio Nino Diaz + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +#include +#include + +#include "extern/version.h" + +const char * get_package_version_string(void) +{ + static char s[50]; + + /* The following conditional should be simplified by the compiler. */ + if (strlen(BUILD_VERSION_STRING) == 0) { + snprintf(s, sizeof(s), "v%d.%d.%d", PACKAGE_VERSION_MAJOR, + PACKAGE_VERSION_MINOR, PACKAGE_VERSION_PATCH); + return s; + } else { + return BUILD_VERSION_STRING; + } +} diff --git a/src/fix/main.c b/src/fix/main.c index f634ce57..05c227f0 100644 --- a/src/fix/main.c +++ b/src/fix/main.c @@ -22,12 +22,13 @@ #include #include "extern/err.h" +#include "extern/version.h" static void usage(void) { printf( -"usage: rgbfix [-Ccjsv] [-i game_id] [-k licensee_str] [-l licensee_id]\n" +"usage: rgbfix [-CcjsVv] [-i game_id] [-k licensee_str] [-l licensee_id]\n" " [-m mbc_type] [-n rom_version] [-p pad_value] [-r ram_size]\n" " [-t title_str] file\n"); exit(1); @@ -69,7 +70,7 @@ main(int argc, char *argv[]) int version; /* mask ROM version number */ int padvalue; /* to pad the rom with if it changes size */ - while ((ch = getopt(argc, argv, "Cci:jk:l:m:n:p:sr:t:v")) != -1) { + while ((ch = getopt(argc, argv, "Cci:jk:l:m:n:p:sr:t:Vv")) != -1) { switch (ch) { case 'C': coloronly = true; @@ -177,6 +178,9 @@ main(int argc, char *argv[]) title = optarg; break; + case 'V': + printf("rgbfix %s\n", get_package_version_string()); + exit(0); case 'v': validate = true; break; diff --git a/src/fix/rgbfix.1 b/src/fix/rgbfix.1 index cbbb3661..7cc39801 100644 --- a/src/fix/rgbfix.1 +++ b/src/fix/rgbfix.1 @@ -20,7 +20,7 @@ .Nd Game Boy checksum fixer .Sh SYNOPSIS .Nm rgbfix -.Op Fl Ccjsv +.Op Fl CcjsVv .Op Fl i Ar game_id .Op Fl k Ar licensee_str .Op Fl l Ar licensee_id @@ -108,6 +108,8 @@ or .Pc . If both this and the game ID are set, the game ID will overwrite the overlapping portion of the title. +.It Fl V +Print the version of the program and exit. .It Fl v Validate the header and fix checksums: the Nintendo character area .Pq Ad 0x104 Ns \(en Ns Ad 0x133 , diff --git a/src/gfx/main.c b/src/gfx/main.c index cc8bca2a..4e13e1fb 100644 --- a/src/gfx/main.c +++ b/src/gfx/main.c @@ -14,17 +14,19 @@ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ -#include #include #include +#include + +#include "extern/version.h" #include "gfx/main.h" static void usage(void) { printf( -"usage: rgbgfx [-DFfhPTuv] [-d #] [-o outfile] [-p palfile] [-t mapfile]\n" -"[-x #] infile\n"); +"usage: rgbgfx [-DFfhPTuVv] [-d #] [-o outfile] [-p palfile] [-t mapfile]\n" +" [-x #] infile\n"); exit(1); } @@ -49,27 +51,30 @@ main(int argc, char *argv[]) depth = 2; - while((ch = getopt(argc, argv, "DvFfd:hx:Tt:uPp:o:")) != -1) { + while((ch = getopt(argc, argv, "Dd:Ffho:Tt:uPp:Vvx:")) != -1) { switch(ch) { case 'D': opts.debug = true; break; - case 'v': - opts.verbose = true; + case 'd': + depth = strtoul(optarg, NULL, 0); break; case 'F': opts.hardfix = true; case 'f': opts.fix = true; break; - case 'd': - depth = strtoul(optarg, NULL, 0); - break; case 'h': opts.horizontal = true; break; - case 'x': - opts.trim = strtoul(optarg, NULL, 0); + case 'o': + opts.outfile = optarg; + break; + case 'P': + opts.palout = true; + break; + case 'p': + opts.palfile = optarg; break; case 'T': opts.mapout = true; @@ -80,17 +85,18 @@ main(int argc, char *argv[]) case 'u': opts.unique = true; break; - case 'P': - opts.palout = true; + case 'V': + printf("rgbgfx %s\n", get_package_version_string()); + exit(0); + case 'v': + opts.verbose = true; break; - case 'p': - opts.palfile = optarg; - break; - case 'o': - opts.outfile = optarg; + case 'x': + opts.trim = strtoul(optarg, NULL, 0); break; default: usage(); + /* NOTREACHED */ } } argc -= optind; diff --git a/src/gfx/rgbgfx.1 b/src/gfx/rgbgfx.1 index 54240c8c..3951e77f 100644 --- a/src/gfx/rgbgfx.1 +++ b/src/gfx/rgbgfx.1 @@ -20,7 +20,7 @@ .Nd Game Boy graphics converter .Sh SYNOPSIS .Nm rgbgfx -.Op Fl DfFhPTv +.Op Fl DfFhPTVv .Op Fl o Ar outfile .Op Fl d Ar depth .Op Fl p Ar palfile @@ -70,6 +70,8 @@ removing the file extension, and appending .Pa .tilemap . .It Fl u Truncate repeated tiles. Useful with tilemaps. +.It Fl V +Print the version of the program and exit. .It Fl v Verbose. Print errors when the command line parameters and the parameters in diff --git a/src/link/main.c b/src/link/main.c index 9e246f2f..3c88e7f3 100644 --- a/src/link/main.c +++ b/src/link/main.c @@ -4,6 +4,7 @@ #include #include "extern/err.h" +#include "extern/version.h" #include "link/object.h" #include "link/output.h" #include "link/assign.h" @@ -33,7 +34,7 @@ static void usage(void) { printf( -"usage: rgblink [-twd] [-l linkerscript] [-m mapfile] [-n symfile] [-O overlay]\n" +"usage: rgblink [-dtVw] [-l linkerscript] [-m mapfile] [-n symfile] [-O overlay]\n" " [-o outfile] [-p pad_value] [-s symbol] file [...]\n"); exit(1); } @@ -52,7 +53,7 @@ main(int argc, char *argv[]) if (argc == 1) usage(); - while ((ch = getopt(argc, argv, "l:m:n:o:O:p:s:twd")) != -1) { + while ((ch = getopt(argc, argv, "dl:m:n:O:o:p:s:tVw")) != -1) { switch (ch) { case 'l': SetLinkerscriptName(optarg); @@ -98,7 +99,7 @@ main(int argc, char *argv[]) * This option implies OPT_CONTWRAM. */ options |= OPT_DMG_MODE; - /* fallthrough */ + /* FALLTHROUGH */ case 'w': /* Set to set WRAM as a single continuous block as on * DMG. All WRAM sections must be WRAM0 as bankable WRAM @@ -106,6 +107,9 @@ main(int argc, char *argv[]) * will raise an error. */ options |= OPT_CONTWRAM; break; + case 'V': + printf("rgblink %s\n", get_package_version_string()); + exit(0); default: usage(); /* NOTREACHED */ diff --git a/src/link/rgblink.1 b/src/link/rgblink.1 index 2f1dc79a..85d8b882 100644 --- a/src/link/rgblink.1 +++ b/src/link/rgblink.1 @@ -20,9 +20,7 @@ .Nd Game Boy linker .Sh SYNOPSIS .Nm rgblink -.Op Fl t -.Op Fl w -.Op Fl d +.Op Fl dtVw .Op Fl m Ar mapfile .Op Fl n Ar symfile .Op Fl O Ar overlayfile @@ -95,6 +93,8 @@ have to be consistent. See .Xr rgblink 5 for more information about its format. +.It Fl V +Print the version of the program and exit. .El .Sh EXAMPLES All you need for a basic ROM is an object file, which can be made into a ROM