Mercurial > hg > toybox
comparison www/code.html @ 674:7e846e281e38
New build infrastructure to generate FLAG_ macros and TT alias, #define FOR_commandname before #including toys.h to trigger it. Rename DEFINE_GLOBALS() to just GLOBALS() (because I could never remember if it was DECLARE_GLOBALS). Convert existing commands to use new infrastructure, and replace optflag constants with FLAG_ macros where appropriate.
author | Rob Landley <rob@landley.net> |
---|---|
date | Mon, 08 Oct 2012 00:02:30 -0500 |
parents | 1a368546afd9 |
children | 43c4f709b9ff |
comparison
equal
deleted
inserted
replaced
673:c102f31a753e | 674:7e846e281e38 |
---|---|
72 <li><a href="#lib_llist">lib/llist.c</a></li> | 72 <li><a href="#lib_llist">lib/llist.c</a></li> |
73 <li><a href="#lib_args">lib/args.c</a></li> | 73 <li><a href="#lib_args">lib/args.c</a></li> |
74 <li><a href="#lib_dirtree">lib/dirtree.c</a></li> | 74 <li><a href="#lib_dirtree">lib/dirtree.c</a></li> |
75 </ul> | 75 </ul> |
76 <li>The <a href="#toys">toys directory</a> contains the C files implementating | 76 <li>The <a href="#toys">toys directory</a> contains the C files implementating |
77 each command.</li> | 77 each command. Currently it contains three subdirectories: |
78 posix, lsb, and other.</li> | |
78 <li>The <a href="#scripts">scripts directory</a> contains the build and | 79 <li>The <a href="#scripts">scripts directory</a> contains the build and |
79 test infrastructure.</li> | 80 test infrastructure.</li> |
80 <li>The <a href="#kconfig">kconfig directory</a> contains the configuration | 81 <li>The <a href="#kconfig">kconfig directory</a> contains the configuration |
81 infrastructure implementing menuconfig (copied from the Linux kernel).</li> | 82 infrastructure implementing menuconfig (copied from the Linux kernel).</li> |
82 <li>The <a href="#generated">generated directory</a> contains intermediate | 83 <li>The <a href="#generated">generated directory</a> contains intermediate |
83 files generated from other parts of the source code.</li> | 84 files generated from other parts of the source code.</li> |
84 </ul> | 85 </ul> |
85 | 86 |
86 <a name="adding" /> | 87 <a name="adding" /> |
87 <p><h1>Adding a new command</h1></p> | 88 <p><h1>Adding a new command</h1></p> |
88 <p>To add a new command to toybox, add a C file implementing that command to | 89 <p>To add a new command to toybox, add a C file implementing that command under |
89 the toys directory. No other files need to be modified; the build extracts | 90 the toys directory. No other files need to be modified; the build extracts |
90 all the information it needs (such as command line arguments) from specially | 91 all the information it needs (such as command line arguments) from specially |
91 formatted comments and macros in the C file. (See the description of the | 92 formatted comments and macros in the C file. (See the description of the |
92 <a href="#generated">"generated" directory</a> for details.)</p> | 93 <a href="#generated">"generated" directory</a> for details.)</p> |
93 | 94 |
94 <p>An easy way to start a new command is copy the file "hello.c" to | 95 <p>Currently there are three subdirectories under "toys", one for commands |
96 defined by the POSIX standard, one for commands defined by the Linux Standard | |
97 Base, and one for all other commands. (This is just for developer convenience | |
98 sorting them, the directories are otherwise functionally identical.)</p> | |
99 | |
100 <p>An easy way to start a new command is copy the file "toys/other/hello.c" to | |
95 the name of the new command, and modify this copy to implement the new command. | 101 the name of the new command, and modify this copy to implement the new command. |
96 This file is an example command meant to be used as a "skeleton" for | 102 This file is an example command meant to be used as a "skeleton" for |
97 new commands (more or less by turning every instance of "hello" into the | 103 new commands (more or less by turning every instance of "hello" into the |
98 name of your command, updating the command line arguments, globals, and | 104 name of your command, updating the command line arguments, globals, and |
99 help data, and then filling out its "main" function with code that does | 105 help data, and then filling out its "main" function with code that does |
102 variables that a "hello world" program doesn't strictly need).</p> | 108 variables that a "hello world" program doesn't strictly need).</p> |
103 | 109 |
104 <p>Here's a checklist of steps to turn hello.c into another command:</p> | 110 <p>Here's a checklist of steps to turn hello.c into another command:</p> |
105 | 111 |
106 <ul> | 112 <ul> |
107 <li><p>First "cd toys" and "cp hello.c yourcommand.c". Note that the name | 113 <li><p>First "cd toys/other" and "cp hello.c yourcommand.c". Note that the name |
108 of this file is significant, it's the name of the new command you're adding | 114 of this file is significant, it's the name of the new command you're adding |
109 to toybox. Open your new file in your favorite editor.</p></li> | 115 to toybox. Open your new file in your favorite editor.</p></li> |
110 | 116 |
111 <li><p>Change the one line comment at the top of the file (currently | 117 <li><p>Change the one line comment at the top of the file (currently |
112 "hello.c - A hello world program") to describe your new file.</p></li> | 118 "hello.c - A hello world program") to describe your new file.</p></li> |
113 | 119 |
114 <li><p>Change the copyright notice to your name, email, and the current | 120 <li><p>Change the copyright notice to your name, email, and the current |
115 year.</p></li> | 121 year.</p></li> |
116 | 122 |
117 <li><p>Give a URL to the relevant standards document, or say "Not in SUSv4" if | 123 <li><p>Give a URL to the relevant standards document, where applicable. |
118 there is no relevant standard. (Currently both lines are there, delete | 124 (Sample links to SUSv4 and LSB are provided, feel free to link to other |
119 whichever is inappropriate.) The existing link goes to the directory of SUSv4 | 125 documentation or standards as appropriate.)</p></li> |
120 command line utility standards on the Open Group's website, where there's often | |
121 a relevant commandname.html file. Feel free to link to other documentation or | |
122 standards as appropriate.</p></li> | |
123 | 126 |
124 <li><p>Update the USE_YOURCOMMAND(NEWTOY(yourcommand,"blah",0)) line. | 127 <li><p>Update the USE_YOURCOMMAND(NEWTOY(yourcommand,"blah",0)) line. |
125 The NEWTOY macro fills out this command's <a href="#toy_list">toy_list</a> | 128 The NEWTOY macro fills out this command's <a href="#toy_list">toy_list</a> |
126 structure. The arguments to the NEWTOY macro are:</p> | 129 structure. The arguments to the NEWTOY macro are:</p> |
127 | 130 |
151 outputs this text, and scripts/config2help.c in the build infrastructure | 154 outputs this text, and scripts/config2help.c in the build infrastructure |
152 collates these usage lines for commands with multiple configuration | 155 collates these usage lines for commands with multiple configuration |
153 options when producing generated/help.h.</p> | 156 options when producing generated/help.h.</p> |
154 </li> | 157 </li> |
155 | 158 |
156 <li><p>Update the DEFINE_GLOBALS() macro to contain your command's global | 159 <li><p>Change the "#define FOR_hello" line to "#define FOR_yourcommand" right |
157 variables, and also change the name "hello" in the #define TT line afterwards | 160 before the "#include <toys.h>". (This selects the appropriate FLAG_ macros and |
158 to the name of your command. If your command has no global variables, delete | 161 does a "#define TT this.yourcommand" so you can access the global variables |
159 this macro (and the #define TT line afterwards). Note that if you specified | 162 out of the space-saving union of structures. If you aren't using any command |
160 two-character command line arguments in NEWTOY(), the first few global | 163 flag bits and aren't defining a GLOBAL block, you can delete this line.)</p></li> |
161 variables will be initialized by the automatic argument parsing logic, and | 164 |
162 the type and order of these variables must correspond to the arguments | 165 <li><p>Update the GLOBALS() macro to contain your command's global |
163 specified in NEWTOY(). See [TODO] for details.</p></li> | 166 variables. If your command has no global variables, delete this macro.</p> |
164 | 167 |
165 <li><p>If you didn't delete the DEFINE_GLOBALS macro, change the "#define TT | 168 <p>Variables in the GLOBALS() block are are stored in a space saving |
166 this.hello" line to use your command name in place of the "hello". This is a | 169 <a href="#toy_union">union of structures</a> format, which may be accessed |
167 shortcut to access your global variables as if they were members of the global | 170 using the TT macro as if TT were a global structure (so TT.membername). |
168 struct "TT". (Access these members with a period ".", not a right arrow | 171 If you specified two-character command line arguments in |
169 "->".)</p></li> | 172 NEWTOY(), the first few global variables will be initialized by the automatic |
173 argument parsing logic, and the type and order of these variables must | |
174 correspond to the arguments specified in NEWTOY(). | |
175 (See <a href="#lib_args">lib/args.c</a> for details.)</p></li> | |
170 | 176 |
171 <li><p>Rename hello_main() to yourcommand_main(). This is the main() function | 177 <li><p>Rename hello_main() to yourcommand_main(). This is the main() function |
172 where execution of your command starts. See [TODO] to figure out what | 178 where execution of your command starts. Your command line options are |
173 happened to your command line arguments and how to access them.</p></li> | 179 already sorted into this.optflags, this.optargs, this.optc, and the GLOBALS() |
180 as appropriate by the time this function is called. (See | |
181 <a href="#lib_args">get_optflags()</a> for details.</p></li> | |
174 </ul> | 182 </ul> |
175 | 183 |
176 <p><a name="top" /><h2>Top level directory.</h2></p> | 184 <p><a name="top" /><h2>Top level directory.</h2></p> |
177 | 185 |
178 <p>This directory contains global infrastructure.</p> | 186 <p>This directory contains global infrastructure.</p> |
179 | 187 |
180 <h3>toys.h</h3> | 188 <h3>toys.h</h3> |
181 <p>Each command #includes "toys.h" as part of its standard prolog.</p> | 189 <p>Each command #includes "toys.h" as part of its standard prolog. It |
190 may "#define FOR_commandname" before doing so to get some extra entries | |
191 specific to this command.</p> | |
182 | 192 |
183 <p>This file sucks in most of the commonly used standard #includes, so | 193 <p>This file sucks in most of the commonly used standard #includes, so |
184 individual files can just #include "toys.h" and not have to worry about | 194 individual files can just #include "toys.h" and not have to worry about |
185 stdargs.h and so on. Individual commands still need to #include | 195 stdargs.h and so on. Individual commands still need to #include |
186 special-purpose headers that may not be present on all systems (and thus would | 196 special-purpose headers that may not be present on all systems (and thus would |
231 <li><p>char *<b>name</b> - the name of this command.</p></li> | 241 <li><p>char *<b>name</b> - the name of this command.</p></li> |
232 <li><p>void (*<b>toy_main</b>)(void) - function pointer to run this | 242 <li><p>void (*<b>toy_main</b>)(void) - function pointer to run this |
233 command.</p></li> | 243 command.</p></li> |
234 <li><p>char *<b>options</b> - command line option string (used by | 244 <li><p>char *<b>options</b> - command line option string (used by |
235 get_optflags() in lib/args.c to intialize toys.optflags, toys.optargs, and | 245 get_optflags() in lib/args.c to intialize toys.optflags, toys.optargs, and |
236 entries in the toy's DEFINE_GLOBALS struct). When this is NULL, no option | 246 entries in the toy's GLOBALS struct). When this is NULL, no option |
237 parsing is done before calling toy_main().</p></li> | 247 parsing is done before calling toy_main().</p></li> |
238 <li><p>int <b>flags</b> - Behavior flags for this command. The following flags are currently understood:</p> | 248 <li><p>int <b>flags</b> - Behavior flags for this command. The following flags are currently understood:</p> |
239 | 249 |
240 <ul> | 250 <ul> |
241 <li><b>TOYFLAG_USR</b> - Install this command under /usr</li> | 251 <li><b>TOYFLAG_USR</b> - Install this command under /usr</li> |
267 <li><p>char **<b>argv</b> - "raw" command line options, I.E. the original | 277 <li><p>char **<b>argv</b> - "raw" command line options, I.E. the original |
268 unmodified string array passed in to main(). Note that modifying this changes | 278 unmodified string array passed in to main(). Note that modifying this changes |
269 "ps" output, and is not recommended. This array is null terminated; a NULL | 279 "ps" output, and is not recommended. This array is null terminated; a NULL |
270 entry indicates the end of the array.</p> | 280 entry indicates the end of the array.</p> |
271 <p>Most commands don't use this field, instead the use optargs, optflags, | 281 <p>Most commands don't use this field, instead the use optargs, optflags, |
272 and the fields in the DEFINE_GLOBALS struct initialized by get_optflags().</p> | 282 and the fields in the GLOBALS struct initialized by get_optflags().</p> |
273 </li> | 283 </li> |
274 <li><p>unsigned <b>optflags</b> - Command line option flags, set by | 284 <li><p>unsigned <b>optflags</b> - Command line option flags, set by |
275 <a href="#lib_args">get_optflags()</a>. Indicates which of the command line options listed in | 285 <a href="#lib_args">get_optflags()</a>. Indicates which of the command line options listed in |
276 toys->which.options occurred this time.</p> | 286 toys->which.options occurred this time.</p> |
277 | 287 |
280 order the binary digits would be listed if typed out as a string. For example, | 290 order the binary digits would be listed if typed out as a string. For example, |
281 the option string "abcd" would parse the command line "-c" to set optflags to 2, | 291 the option string "abcd" would parse the command line "-c" to set optflags to 2, |
282 "-a" would set optflags to 8, and "-bd" would set optflags to 6 (4|2).</p> | 292 "-a" would set optflags to 8, and "-bd" would set optflags to 6 (4|2).</p> |
283 | 293 |
284 <p>Only letters are relevant to optflags. In the string "a*b:c#d", d=1, c=2, | 294 <p>Only letters are relevant to optflags. In the string "a*b:c#d", d=1, c=2, |
285 b=4, a=8. The punctuation after a letter initializes global variables | 295 b=4, a=8. Punctuation after a letter initializes global variables at the |
286 (see [TODO] DECLARE_GLOBALS() for details).</p> | 296 start of the GLOBALS() block (see <a href="#toy_union">union toy_union this</a> |
297 for details).</p> | |
298 | |
299 <p>The build infrastructure creates FLAG_ macros for each option letter, | |
300 corresponding to the bit position, so you can check (toys.optflags & FLAG_x) | |
301 to see if a flag was specified. (The correct set of FLAG_ macros is selected | |
302 by defining FOR_mycommand before #including toys.h. The macros live in | |
303 toys/globals.h which is generated by scripts/make.sh.)</p> | |
287 | 304 |
288 <p>For more information on option parsing, see <a href="#lib_args">get_optflags()</a>.</p> | 305 <p>For more information on option parsing, see <a href="#lib_args">get_optflags()</a>.</p> |
289 | 306 |
290 </li> | 307 </li> |
291 <li><p>char **<b>optargs</b> - Null terminated array of arguments left over | 308 <li><p>char **<b>optargs</b> - Null terminated array of arguments left over |
297 <li><p>int <b>exithelp</b> - Whether error_exit() should print a usage message | 314 <li><p>int <b>exithelp</b> - Whether error_exit() should print a usage message |
298 via help_main() before exiting. (True during option parsing, defaults to | 315 via help_main() before exiting. (True during option parsing, defaults to |
299 false afterwards.)</p></li> | 316 false afterwards.)</p></li> |
300 </ul> | 317 </ul> |
301 | 318 |
319 <a name="toy_union" /> | |
302 <li><p><b>union toy_union this</b> - Union of structures containing each | 320 <li><p><b>union toy_union this</b> - Union of structures containing each |
303 command's global variables.</p> | 321 command's global variables.</p> |
304 | 322 |
305 <p>Global variables are useful: they reduce the overhead of passing extra | 323 <p>Global variables are useful: they reduce the overhead of passing extra |
306 command line arguments between functions, they conveniently start prezeroed to | 324 command line arguments between functions, they conveniently start prezeroed to |
311 space for global variables belonging to other commands you aren't currently | 329 space for global variables belonging to other commands you aren't currently |
312 running would be wasteful.</p> | 330 running would be wasteful.</p> |
313 | 331 |
314 <p>Toybox handles this by encapsulating each command's global variables in | 332 <p>Toybox handles this by encapsulating each command's global variables in |
315 a structure, and declaring a union of those structures with a single global | 333 a structure, and declaring a union of those structures with a single global |
316 instance (called "this"). The DEFINE_GLOBALS() macro contains the global | 334 instance (called "this"). The GLOBALS() macro contains the global |
317 variables that should go in the current command's global structure. Each | 335 variables that should go in the current command's global structure. Each |
318 variable can then be accessed as "this.commandname.varname". | 336 variable can then be accessed as "this.commandname.varname". |
319 Generally, the macro TT is #defined to this.commandname so the variable | 337 If you #defined FOR_commandname before including toys.h, the macro TT is |
320 can then be accessed as "TT.variable". See toys/hello.c for an example.</p> | 338 #defined to this.commandname so the variable can then be accessed as |
339 "TT.variable". See toys/hello.c for an example.</p> | |
321 | 340 |
322 <p>A command that needs global variables should declare a structure to | 341 <p>A command that needs global variables should declare a structure to |
323 contain them all, and add that structure to this union. A command should never | 342 contain them all, and add that structure to this union. A command should never |
324 declare global variables outside of this, because such global variables would | 343 declare global variables outside of this, because such global variables would |
325 allocate memory when running other commands that don't use those global | 344 allocate memory when running other commands that don't use those global |
662 </ul> | 681 </ul> |
663 | 682 |
664 <p>If the command's globals are:</p> | 683 <p>If the command's globals are:</p> |
665 | 684 |
666 <blockquote><pre> | 685 <blockquote><pre> |
667 DECLARE_GLOBALS( | 686 GLOBALS( |
668 char *c; | 687 char *c; |
669 char *b; | 688 char *b; |
670 long a; | 689 long a; |
671 ) | 690 ) |
672 #define TT this.command | |
673 </pre></blockquote> | 691 </pre></blockquote> |
674 <p>That would mean TT.c == NULL, TT.b == "fruit", and TT.a == 42. (Remember, | 692 <p>That would mean TT.c == NULL, TT.b == "fruit", and TT.a == 42. (Remember, |
675 each entry that receives an argument must be a long or pointer, to line up | 693 each entry that receives an argument must be a long or pointer, to line up |
676 with the array position. Right to left in the optflags string corresponds to | 694 with the array position. Right to left in the optflags string corresponds to |
677 top to bottom in DECLARE_GLOBALS().</p> | 695 top to bottom in GLOBALS().</p> |
678 | 696 |
679 <p><b>long toys.optflags</b></p> | 697 <p><b>long toys.optflags</b></p> |
680 | 698 |
681 <p>Each option in the optflags string corresponds to a bit position in | 699 <p>Each option in the optflags string corresponds to a bit position in |
682 toys.optflags, with the same value as a corresponding binary digit. The | 700 toys.optflags, with the same value as a corresponding binary digit. The |
938 <b>DIRTREE_RECURSE</b> from the callback, instead calling <b>dirtree_recurse</b>() manually | 956 <b>DIRTREE_RECURSE</b> from the callback, instead calling <b>dirtree_recurse</b>() manually |
939 from elsewhere in the program. This gives ls -lR manual control | 957 from elsewhere in the program. This gives ls -lR manual control |
940 of traversal order, which is neither depth first nor breadth first but | 958 of traversal order, which is neither depth first nor breadth first but |
941 instead a sort of FIFO order requried by the ls standard.</p> | 959 instead a sort of FIFO order requried by the ls standard.</p> |
942 | 960 |
961 <a name="#toys"> | |
962 <h2>Directory toys/</h2> | |
963 | |
964 <p>This directory contains command implementations. Each command is a single | |
965 self-contained file. Adding a new command involves adding a single | |
966 file, and removing a command involves removing that file. Commands use | |
967 shared infrastructure from the lib/ and generated/ directories.</p> | |
968 | |
969 <p>Currently there are three subdirectories under "toys/" containing commands | |
970 described in POSIX-2008, the Linux Standard Base 4.1, or "other". The only | |
971 difference this makes is which menu the command shows up in during "make | |
972 menuconfig", the directories are otherwise identical. Note that they commands | |
973 exist within a single namespace at runtime, so you can't have the same | |
974 command in multiple subdirectories.</p> | |
975 | |
976 <p>(There are actually four sub-menus in "make menuconfig", the fourth | |
977 contains global configuration options for toybox, and lives in Config.in at | |
978 the top level.)</p> | |
979 | |
980 <p>See <a href="#adding">adding a new command</a> for details on the | |
981 layout of a command file.</p> | |
982 | |
943 <h2>Directory scripts/</h2> | 983 <h2>Directory scripts/</h2> |
944 | 984 |
945 <h3>scripts/cfg2files.sh</h3> | 985 <h3>scripts/cfg2files.sh</h3> |
946 | 986 |
947 <p>Run .config through this filter to get a list of enabled commands, which | 987 <p>Run .config through this filter to get a list of enabled commands, which |