Add long options

This commit is contained in:
ISSOtm
2019-11-03 22:11:04 +01:00
parent 072c965ba5
commit 0649e6d65f
7 changed files with 205 additions and 27 deletions

View File

@@ -67,6 +67,7 @@ rgbasm_obj := \
src/asm/symbol.o \ src/asm/symbol.o \
src/asm/util.o \ src/asm/util.o \
src/extern/err.o \ src/extern/err.o \
src/extern/getopt.o \
src/extern/utf8decoder.o \ src/extern/utf8decoder.o \
src/version.o src/version.o
@@ -82,12 +83,14 @@ rgblink_obj := \
src/link/section.o \ src/link/section.o \
src/link/symbol.o \ src/link/symbol.o \
src/extern/err.o \ src/extern/err.o \
src/extern/getopt.o \
src/hashmap.o \ src/hashmap.o \
src/version.o src/version.o
rgbfix_obj := \ rgbfix_obj := \
src/fix/main.o \ src/fix/main.o \
src/extern/err.o \ src/extern/err.o \
src/extern/getopt.o \
src/version.o src/version.o
rgbgfx_obj := \ rgbgfx_obj := \
@@ -95,6 +98,7 @@ rgbgfx_obj := \
src/gfx/main.o \ src/gfx/main.o \
src/gfx/makepng.o \ src/gfx/makepng.o \
src/extern/err.o \ src/extern/err.o \
src/extern/getopt.o \
src/version.o src/version.o
rgbasm: ${rgbasm_obj} rgbasm: ${rgbasm_obj}

View File

@@ -1,11 +1,31 @@
/*
* Copyright © 2005-2019 Rich Felker, et al.
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
/* This implementation was taken from musl and modified for RGBDS */
#ifndef _GETOPT_H #ifndef _GETOPT_H
#define _GETOPT_H #define _GETOPT_H
#ifdef __cplusplus
extern "C" {
#endif
int getopt(int, char * const [], const char *);
extern char *optarg; extern char *optarg;
extern int optind, opterr, optopt, optreset; extern int optind, opterr, optopt, optreset;
@@ -16,15 +36,10 @@ struct option {
int val; int val;
}; };
int getopt_long(int, char *const *, const char *, const struct option *, int *);
int getopt_long_only(int, char *const *, const char *, const struct option *, int *); int getopt_long_only(int, char *const *, const char *, const struct option *, int *);
#define no_argument 0 #define no_argument 0
#define required_argument 1 #define required_argument 1
#define optional_argument 2 #define optional_argument 2
#ifdef __cplusplus
}
#endif
#endif #endif

View File

@@ -14,7 +14,6 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <time.h> #include <time.h>
#include <unistd.h>
#include "asm/symbol.h" #include "asm/symbol.h"
#include "asm/fstack.h" #include "asm/fstack.h"
@@ -24,6 +23,7 @@
#include "asm/charmap.h" #include "asm/charmap.h"
#include "extern/err.h" #include "extern/err.h"
#include "extern/getopt.h"
#include "helpers.h" #include "helpers.h"
#include "version.h" #include "version.h"
@@ -287,6 +287,37 @@ void warning(const char *fmt, ...)
va_end(args); va_end(args);
} }
/* Short options */
static char const *optstring = "b:D:Eg:hi:LM:o:p:r:Vvw";
/*
* Equivalent long options
* Please keep in the same order as short opts
*
* Also, make sure long opts don't create ambiguity:
* A long opt's name should start with the same letter as its short opt,
* except if it doesn't create any ambiguity (`verbose` versus `version`).
* This is because long opt matching, even to a single char, is prioritized
* over short opt matching
*/
static struct option const longopts[] = {
{ "binary-digits", required_argument, NULL, 'b' },
{ "define", required_argument, NULL, 'D' },
{ "export-all", no_argument, NULL, 'E' },
{ "gfx-chars", required_argument, NULL, 'g' },
{ "halt-without-nop", no_argument, NULL, 'h' },
{ "include", required_argument, NULL, 'i' },
{ "preserve-ld", no_argument, NULL, 'L' },
{ "dependfile", required_argument, NULL, 'M' },
{ "output", required_argument, NULL, 'o' },
{ "pad-value", required_argument, NULL, 'p' },
{ "recursion-depth", required_argument, NULL, 'r' },
{ "version", no_argument, NULL, 'V' },
{ "verbose", no_argument, NULL, 'v' },
{ "warning", no_argument, NULL, 'w' },
{ NULL, no_argument, NULL, 0 }
};
static void print_usage(void) static void print_usage(void)
{ {
printf( printf(
@@ -338,7 +369,8 @@ int main(int argc, char *argv[])
newopt = CurrentOptions; newopt = CurrentOptions;
while ((ch = getopt(argc, argv, "b:D:Eg:hi:LM:o:p:r:Vvw")) != -1) { while ((ch = getopt_long_only(argc, argv, optstring, longopts,
NULL)) != -1) {
switch (ch) { switch (ch) {
case 'b': case 'b':
if (strlen(optarg) == 2) { if (strlen(optarg) == 2) {

46
src/extern/getopt.c vendored
View File

@@ -1,13 +1,46 @@
#define _GNU_SOURCE /*
* Copyright © 2005-2019 Rich Felker, et al.
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
/* This implementation was taken from musl and modified for RGBDS */
#include <stddef.h> #include <stddef.h>
#include <stdlib.h> #include <stdlib.h>
#include <limits.h> #include <limits.h>
#include <getopt.h> #include <unistd.h>
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#include "stdio_impl.h" #include "extern/getopt.h"
extern int __optpos, __optreset; int __optpos, __optreset;
void __getopt_msg(const char *a, const char *b, const char *c, size_t l)
{
FILE *f = stderr;
(void)(fputs(a, f)>=0
&& fwrite(b, strlen(b), 1, f)
&& fwrite(c, 1, l, f)==l
&& putc('\n', f));
}
static void permute(char *const *argv, int dest, int src) static void permute(char *const *argv, int dest, int src)
{ {
@@ -137,11 +170,6 @@ static int __getopt_long_core(int argc, char *const *argv, const char *optstring
return getopt(argc, argv, optstring); return getopt(argc, argv, optstring);
} }
int getopt_long(int argc, char *const *argv, const char *optstring, const struct option *longopts, int *idx)
{
return __getopt_long(argc, argv, optstring, longopts, idx, 0);
}
int getopt_long_only(int argc, char *const *argv, const char *optstring, const struct option *longopts, int *idx) int getopt_long_only(int argc, char *const *argv, const char *optstring, const struct option *longopts, int *idx)
{ {
return __getopt_long(argc, argv, optstring, longopts, idx, 1); return __getopt_long(argc, argv, optstring, longopts, idx, 1);

View File

@@ -11,12 +11,44 @@
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <unistd.h>
#include "extern/err.h" #include "extern/err.h"
#include "extern/getopt.h"
#include "version.h" #include "version.h"
/* Shoft options */
static char const *optstring = "Ccf:i:jk:l:m:n:p:sr:t:Vv";
/*
* Equivalent long options
* Please keep in the same order as short opts
*
* Also, make sure long opts don't create ambiguity:
* A long opt's name should start with the same letter as its short opt,
* except if it doesn't create any ambiguity (`verbose` versus `version`).
* This is because long opt matching, even to a single char, is prioritized
* over short opt matching
*/
static struct option const longopts[] = {
{ "color-only", no_argument, NULL, 'C' },
{ "color-compatible", no_argument, NULL, 'c' },
{ "fix-spec", required_argument, NULL, 'f' },
{ "game-id", required_argument, NULL, 'i' },
{ "non-japanese", no_argument, NULL, 'j' },
{ "new-licensee", required_argument, NULL, 'k' },
{ "old-licensee", required_argument, NULL, 'l' },
{ "mbc-type", required_argument, NULL, 'm' },
{ "rom-version", required_argument, NULL, 'n' },
{ "pad-value", required_argument, NULL, 'p' },
{ "ram-size", required_argument, NULL, 'r' },
{ "sgb-compatible", no_argument, NULL, 's' },
{ "title", required_argument, NULL, 't' },
{ "version", no_argument, NULL, 'V' },
{ "verbose", no_argument, NULL, 'v' },
{ NULL, no_argument, NULL, 0 }
};
static void print_usage(void) static void print_usage(void)
{ {
printf( printf(
@@ -66,7 +98,8 @@ int main(int argc, char *argv[])
int version = 0; /* mask ROM version number */ int version = 0; /* mask ROM version number */
int padvalue = 0; /* to pad the rom with if it changes size */ int padvalue = 0; /* to pad the rom with if it changes size */
while ((ch = getopt(argc, argv, "Ccf:i:jk:l:m:n:p:sr:t:Vv")) != -1) { while ((ch = getopt_long_only(argc, argv, optstring, longopts,
NULL)) != -1) {
switch (ch) { switch (ch) {
case 'C': case 'C':
coloronly = true; coloronly = true;

View File

@@ -9,12 +9,47 @@
#include <png.h> #include <png.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <unistd.h>
#include "gfx/main.h" #include "gfx/main.h"
#include "extern/getopt.h"
#include "version.h" #include "version.h"
/* Short options */
static char const *optstring = "Aa:CDd:Ffhmo:Pp:Tt:uVvx:";
/*
* Equivalent long options
* Please keep in the same order as short opts
*
* Also, make sure long opts don't create ambiguity:
* A long opt's name should start with the same letter as its short opt,
* except if it doesn't create any ambiguity (`verbose` versus `version`).
* This is because long opt matching, even to a single char, is prioritized
* over short opt matching
*/
static struct option const longopts[] = {
{ "output-attr-map", no_argument, NULL, 'A' },
{ "attr-map", required_argument, NULL, 'a' },
{ "color-curve", no_argument, NULL, 'C' },
{ "debug", no_argument, NULL, 'D' },
{ "depth", required_argument, NULL, 'd' },
{ "fix", no_argument, NULL, 'f' },
{ "fix-and-save", no_argument, NULL, 'F' },
{ "horizontal", no_argument, NULL, 'h' },
{ "mirror-tiles", no_argument, NULL, 'm' },
{ "output", required_argument, NULL, 'o' },
{ "output-palette", no_argument, NULL, 'P' },
{ "palette", required_argument, NULL, 'p' },
{ "output-tilemap", no_argument, NULL, 'T' },
{ "tilemap", required_argument, NULL, 't' },
{ "unique-tiles", no_argument, NULL, 'u' },
{ "version", no_argument, NULL, 'V' },
{ "verbose", no_argument, NULL, 'v' },
{ "trim-end", required_argument, NULL, 'x' },
{ NULL, no_argument, NULL, 0 }
};
static void print_usage(void) static void print_usage(void)
{ {
printf( printf(
@@ -45,7 +80,8 @@ int main(int argc, char *argv[])
depth = 2; depth = 2;
while ((ch = getopt(argc, argv, "Aa:CDd:Ffhmo:Tt:uPp:Vvx:")) != -1) { while ((ch = getopt_long_only(argc, argv, optstring, longopts,
NULL)) != -1) {
switch (ch) { switch (ch) {
case 'A': case 'A':
opts.attrmapout = true; opts.attrmapout = true;

View File

@@ -8,7 +8,6 @@
#include <sys/types.h> #include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <unistd.h>
#include <stdio.h> #include <stdio.h>
#include <stdbool.h> #include <stdbool.h>
#include <stdint.h> #include <stdint.h>
@@ -22,6 +21,7 @@
#include "link/output.h" #include "link/output.h"
#include "extern/err.h" #include "extern/err.h"
#include "extern/getopt.h"
#include "version.h" #include "version.h"
bool isDmgMode; /* -d */ bool isDmgMode; /* -d */
@@ -48,6 +48,35 @@ FILE *openFile(char const *fileName, char const *mode)
return file; return file;
} }
/* Short options */
static char const *optstring = "dl:m:n:O:o:p:s:tVvw";
/*
* Equivalent long options
* Please keep in the same order as short opts
*
* Also, make sure long opts don't create ambiguity:
* A long opt's name should start with the same letter as its short opt,
* except if it doesn't create any ambiguity (`verbose` versus `version`).
* This is because long opt matching, even to a single char, is prioritized
* over short opt matching
*/
static struct option const longopts[] = {
{ "dmg", no_argument, NULL, 'd' },
{ "linkerscript", required_argument, NULL, 'l' },
{ "map", required_argument, NULL, 'm' },
{ "sym", required_argument, NULL, 'n' },
{ "overlay", required_argument, NULL, 'O' },
{ "output", required_argument, NULL, 'o' },
{ "pad", required_argument, NULL, 'p' },
{ "smart", required_argument, NULL, 's' },
{ "tiny", no_argument, NULL, 't' },
{ "version", no_argument, NULL, 'V' },
{ "verbose", no_argument, NULL, 'v' },
{ "wramx", no_argument, NULL, 'w' },
{ NULL, no_argument, NULL, 0 }
};
/** /**
* Prints the program's usage to stdout. * Prints the program's usage to stdout.
*/ */
@@ -73,7 +102,8 @@ int main(int argc, char *argv[])
unsigned long value; /* For storing `strtoul`'s return value */ unsigned long value; /* For storing `strtoul`'s return value */
/* Parse options */ /* Parse options */
while ((optionChar = getopt(argc, argv, "dl:m:n:O:o:p:s:tVvw")) != -1) { while ((optionChar = getopt_long_only(argc, argv, optstring, longopts,
NULL)) != -1) {
switch (optionChar) { switch (optionChar) {
case 'd': case 'd':
isDmgMode = true; isDmgMode = true;