Skip to content

Commit

Permalink
C support working
Browse files Browse the repository at this point in the history
  • Loading branch information
eriknyquist committed Oct 21, 2023
1 parent e0693af commit 9a2f1f1
Showing 1 changed file with 78 additions and 6 deletions.
84 changes: 78 additions & 6 deletions duckargs/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,12 @@ def main():
int main(int argc, char *argv[])
{{
if (argc < 2)
{{
print_usage();
return -1;
}}
int ret = parse_args(argc, argv);
if (0 != ret)
{{
Expand Down Expand Up @@ -414,6 +420,19 @@ def _generate_c_getopt_code(processed_args, getopt_string, opts, positionals, ha

if positionals:
# Has both positionals and opts
ret += f" if (argc < (optind + {len(positionals)}))\n"
ret += f" {{\n"
ret += f" printf(\"Missing positional arguments\\n\");\n"
ret += f" return -1;\n"
ret += f" }}\n\n"

for i in range(len(positionals)):
arg = positionals[i]
desc = f"Positional argument #{i + 1} ({arg.var_name})"
optarg = f"argv[optind]"
ret += '\n'.join([" " + x for x in _generate_c_opt_lines(arg, desc, optarg)])
ret += "\n optind++;\n\n"

pass

elif positionals:
Expand Down Expand Up @@ -462,26 +481,68 @@ def _generate_c_print_code(processed_args):
def _generate_c_usage_code(processed_args):
lines = []
positionals = []
has_opts = False
opts = []

for arg in processed_args:
if arg.is_positional():
positionals.append(arg)
continue
else:
has_opts = True
opts.append(arg)

lines.append("")

line = "program_name"
if has_opts:
if opts:
line += " [OPTIONS]"

if positionals:
positional_names = ' '.join([x.var_name for x in positionals])
line += f" {positional_names}"

lines.append(line + "\\n\\n")
lines.append(line + "\\n")

if opts:
longest_left_col = 0
usage_lines = []

for opt in opts:
left_col = opt.opt
if opt.longopt is not None:
left_col += " " + opt.longopt

arg = None
right_col = ""
if opt.is_flag():
right_col = "A flag"
else:
if ArgType.INT == opt.type:
right_col = "An int value"
arg = " [int]"
elif ArgType.FLOAT == opt.type:
right_col = "A float value"
arg = " [float]"
elif ArgType.STRING == opt.type:
right_col = "A string value"
arg = " [string]"
elif ArgType.FILE == opt.type:
right_col = "A filename"
arg = " FILE"

if arg is not None:
left_col += arg

if len(left_col) > longest_left_col:
longest_left_col = len(left_col)

return '\n'.join([f" printf(\"{line}\");" for line in lines])
usage_lines.append((left_col, right_col))

for leftcol, rightcol in usage_lines:
num_spaces = (longest_left_col + 2) - len(leftcol)
lines.append(leftcol + (" " * num_spaces) + rightcol)

lines.append("")

return '\n'.join([f" printf(\"{line}\\n\");" for line in lines])

def generate_c_code(argv=sys.argv):
"""
Expand Down Expand Up @@ -548,6 +609,17 @@ def generate_c_code(argv=sys.argv):
decls += "\n {NULL, 0, NULL, 0}\n};\n"

comment_header = ""
env_comment = os.environ.get("DUCKARGS_COMMENT", 1)
try:
env_comment_int = int(env_comment)
except ValueError:
raise RuntimeError("DUCKARGS_COMMENT must be an integer")

if env_comment_int > 0:
comment_header = (f"// Generated by duckargs, invoked with the following arguments:\n// " +
' '.join(argv[1:]) + "\n\n")

CmdlineOpt.positional_count = 0

if has_flags:
comment_header += "#include <stdbool.h>\n"
Expand Down

0 comments on commit 9a2f1f1

Please sign in to comment.