Posted on | January 8, 2008 | 6 Comments
The GNU operating system is full of easter eggs hidden in plain view. Depending on what repositories you elect to tell your packager about, you could spend an entire day discovering useful things that you never knew existed. Many of these trinkets are part of (or work with) the GNU build system.
I’ve known about a program named gengetopt for a few years, its a neat tool to generate GNU-kosher C code that parses all of your command line arguments and displays help. It even generates a function to parse options from a configuration file. I’ve been meaning to use it for a while because it plays nicely with autotools, but kept forgetting about it. Its been around since (at least) 2003, but many people don’t know that its there, so here’s a little blurb about what it does and how to use it. Read on, it will save you hours.
I’m not sure how you do it, but I like to plan the scope of my program well in advance of getting started. I’ll typically write my usage() function first while thinking about just how everything should work. Once I’m satisfied, its easy to start writing the rest and I’m less likely to wander off into more functionality than I really need once I begin. With gengetopt, Its simple to do this in a plain text file.
The program itself is very simple. You define your options, the type each argument should be (string, flag, double, long, etc), if its required, its initial value and its short/long switch options. My dummy file is below, more or less the same as the example given in the man page which I named test.ggo:
purpose "To play with gengetopt"
option "larry" s "Larry Stooge" string no
option "moe" m "Moe Stooge" int no
option "curly" i "Curly Stooge" int yes
option "shemp" - "Shemp? Sometimes" flag off
option "stooge" F "The Stooges" no
option "nyuk" - "Perhaps nyuks should float?" long no
option "funny" - "Stooges are funny!" string default="Yes" no
Since I was playing with it, I wanted to generate code that I could just compile and run on its own, so my command to produce everything would be a little different than common use:
gengetopt --file-name=cmds --conf-parser --unamed-opts \
--func-name=main < test.ggo
This generated cmds.c and cmds.h, specifying that I wanted the function that parsed the arguments to be named main() (so it could be run without writing a dummy program to include it). I also passed –unamed-opts so that the generated code could handle a list of files and –conf-parser to make a function to deal with a configuration file.
The end result was perfect. All of the code (including printed help) was created, easily compiled and ready for me to finish and adjust. 500 lines of code done in less than a second, you can’t beat that!
The output is well done, all of your options are stored in a structure and the proper autotools hooks are present. The manual page is complete enough to get going quickly, more options (such as option grouping) are explained in the included HTML documentation.
The only thing it does not do is allow an auto-insertion of an option to parse the configuration file. A –parse-cfgfile-option would be neat, or syntax for it in the input file. A switch to specify tabs or spaces for indenting would be neat, but I’m not going to nitpick.
The output of gengetopt is not copyrighted or licensed, its released to the public domain. gengetopt itself is GPL, but there are no restrictions on the output. As such, you aren’t required to license whatever uses the generated code under the GPL.
I’m glad that I finally remembered that this existed, I have to re-write a bunch of daemons done in perl and PHP to C. This will save quite a few hours In the past couple of years, many companies have opted to hire system integrators who have at least a (basic) knowledge of C so that they can write stuff on the fly to just make something work. Tools like this save a ton of time for anyone in such a position.
Even though its been around for a while, if you’ve never really used it .. its new to you Hopefully this blurb saves others some time, too.