2 * Copyright 2008-2009 Katholieke Universiteit Leuven
4 * Use of this software is governed by the GNU LGPLv2.1 license
6 * Written by Sven Verdoolaege, K.U.Leuven, Departement
7 * Computerwetenschappen, Celestijnenlaan 200A, B-3001 Leuven, Belgium
16 static void set_default_choice(struct isl_arg *arg, void *opt)
18 *(unsigned *)(((char *)opt) + arg->offset) = arg->u.choice.default_value;
21 static void set_default_bool(struct isl_arg *arg, void *opt)
23 *(unsigned *)(((char *)opt) + arg->offset) = arg->u.b.default_value;
26 static void set_default_child(struct isl_arg *arg, void *opt)
28 void *child = calloc(1, arg->u.child.size);
31 isl_arg_set_defaults(arg->u.child.child, child);
33 *(void **)(((char *)opt) + arg->offset) = child;
36 void isl_arg_set_defaults(struct isl_arg *arg, void *opt)
40 for (i = 0; arg[i].type != isl_arg_end; ++i) {
41 switch (arg[i].type) {
43 set_default_choice(&arg[i], opt);
46 set_default_bool(&arg[i], opt);
49 set_default_child(&arg[i], opt);
55 static void print_arg_help(struct isl_arg *decl, const char *prefix)
58 printf(" -%c, --", decl->short_name);
62 printf("%s-", prefix);
63 printf("%s", decl->long_name);
66 static void print_choice_help(struct isl_arg *decl, const char *prefix)
70 print_arg_help(decl, prefix);
73 for (i = 0; decl->u.choice.choice[i].name; ++i) {
76 printf("%s", decl->u.choice.choice[i].name);
82 static void print_bool_help(struct isl_arg *decl, const char *prefix)
84 print_arg_help(decl, prefix);
88 static void print_help(struct isl_arg *arg, const char *prefix)
92 for (i = 0; arg[i].type != isl_arg_end; ++i) {
93 switch (arg[i].type) {
95 print_choice_help(&arg[i], prefix);
98 print_bool_help(&arg[i], prefix);
103 for (i = 0; arg[i].type != isl_arg_end; ++i) {
104 if (arg[i].type != isl_arg_child)
108 print_help(arg[i].u.child.child, arg[i].long_name);
112 static void print_help_and_exit(struct isl_arg *arg, const char *prog)
116 slash = strrchr(prog, '/');
118 printf("Usage: %s [OPTION...]\n\n", slash + 1);
120 print_help(arg, NULL);
125 static int parse_choice_option(struct isl_arg *decl, const char *arg,
126 const char *prefix, void *opt)
132 if (strncmp(arg, "--", 2))
136 equal = strchr(name, '=');
141 size_t prefix_len = strlen(prefix);
142 if (strncmp(name, prefix, prefix_len) == 0 &&
143 name[prefix_len] == '-')
144 name += prefix_len + 1;
147 if (strncmp(name, decl->long_name, equal - name))
150 for (i = 0; decl->u.choice.choice[i].name; ++i) {
151 if (strcmp(equal + 1, decl->u.choice.choice[i].name))
154 *(unsigned *)(((char *)opt) + decl->offset) =
155 decl->u.choice.choice[i].value;
163 static int parse_bool_option(struct isl_arg *decl, const char *arg, void *opt)
167 if ((arg[0] == '-' && arg[1] == decl->short_name && arg[2] == '\0') ||
168 (strncmp(arg, "--", 2) == 0 &&
169 strcmp(arg + 2, decl->long_name) == 0)) {
170 *(unsigned *)(((char *)opt) + decl->offset) = 1;
178 static int parse_option(struct isl_arg *decl, const char *arg,
179 const char *prefix, void *opt);
181 static int parse_child_option(struct isl_arg *decl, const char *arg, void *opt)
183 return parse_option(decl->u.child.child, arg, decl->long_name,
184 *(void **)(((char *)opt) + decl->offset));
187 static int parse_option(struct isl_arg *decl, const char *arg,
188 const char *prefix, void *opt)
192 for (i = 0; decl[i].type != isl_arg_end; ++i) {
193 switch (decl[i].type) {
195 if (parse_choice_option(&decl[i], arg, prefix, opt))
199 if (parse_bool_option(&decl[i], arg, opt))
203 if (parse_child_option(&decl[i], arg, opt))
212 static int drop_argument(int argc, char **argv, int drop)
214 for (; drop < argc; ++drop)
215 argv[drop] = argv[drop + 1];
220 int isl_arg_parse(struct isl_arg *arg, int argc, char **argv, void *opt)
225 for (i = 1; i < argc; ++i) {
226 if (strcmp(argv[i], "--help") == 0)
227 print_help_and_exit(arg, argv[0]);
230 while (argc > 1 + skip) {
231 if (parse_option(arg, argv[1 + skip], NULL, opt))
232 argc = drop_argument(argc, argv, 1 + skip);
234 fprintf(stderr, "unrecognized option: %s\n",