diff options
author | delphij <delphij@FreeBSD.org> | 2008-03-07 00:01:19 +0000 |
---|---|---|
committer | delphij <delphij@FreeBSD.org> | 2008-03-07 00:01:19 +0000 |
commit | 6d5f005346f78f0ceca2a2355a7f20af1e6e78da (patch) | |
tree | 7a6a616969e21be00257901673a6a845ecbb005f | |
parent | af9b2bc27f12b3a899199627272d13e24eb6672d (diff) | |
download | FreeBSD-src-6d5f005346f78f0ceca2a2355a7f20af1e6e78da.zip FreeBSD-src-6d5f005346f78f0ceca2a2355a7f20af1e6e78da.tar.gz |
Merge revisions 1.10 and 1.11 from DragonFly:
- Use real getopt() handling instead of the hand-rolled and
IOCCC-worthy "Micro getopt()" macros, plus clean up to the
option handling code:
* Sort the options in the switch statement;
* Plug piddling memory leaks when processing repeated options
by freeing strings before allocating them for a second time;
* Die with a fatal error if the requested report file cannot
be opened for appending;
* Don't call init() before usage() (to prevent the usage
message being mangled by changes to the terminal settings;)
- Clean up the usage message, both in usage() and in the main
program comment, both stylistically (sort and combine options)
and for accuracy (following the manual page, make note of the -s
and -S flags, and use the term 'send' instead of 'say' to reduce
confusion (SAY is the name of a command for output to the user,
not the connection.))
Obtained from: DragonFly
-rw-r--r-- | usr.bin/chat/chat.c | 129 |
1 files changed, 61 insertions, 68 deletions
diff --git a/usr.bin/chat/chat.c b/usr.bin/chat/chat.c index c0afeaf..056af37 100644 --- a/usr.bin/chat/chat.c +++ b/usr.bin/chat/chat.c @@ -105,17 +105,6 @@ __FBSDID("$FreeBSD$"); #define O_NONBLOCK O_NDELAY #endif -/*************** Micro getopt() *********************************************/ -#define OPTION(c,v) (_O&2&&**v?*(*v)++:!c||_O&4?0:(!(_O&1)&& \ - (--c,++v),_O=4,c&&**v=='-'&&v[0][1]?*++*v=='-'\ - &&!v[0][1]?(--c,++v,0):(_O=2,*(*v)++):0)) -#define OPTARG(c,v) (_O&2?**v||(++v,--c)?(_O=1,--c,*v++): \ - (_O=4,(char*)0):(char*)0) -#define ARG(c,v) (c?(--c,*v++):(char*)0) - -static int _O = 0; /* Internal state */ -/*************** Micro getopt() *********************************************/ - #define MAX_ABORTS 50 #define MAX_REPORTS 50 #define DEFAULT_CHAT_TIMEOUT 45 @@ -201,32 +190,44 @@ copy_of(char *s) } /* - * chat [ -v ] [-T number] [-U number] [ -t timeout ] [ -f chat-file ] \ - * [ -r report-file ] \ - * [...[[expect[-say[-expect...]] say expect[-say[-expect]] ...]]] + * chat [-esSvV] [-f chat-file] [-r report-file] [-t timeout] + * [-T phone-number] [-U phone-number2] [chat-script] + * where chat-script has the form: + * [...[[expect[-send[-expect...]] send expect[-send[-expect]] ...]]] * - * Perform a UUCP-dialer-like chat script on stdin and stdout. + * Perform a UUCP-dialer-like chat script on stdin and stdout. */ int main(int argc, char *argv[]) { int option; - char *arg; tzset(); - while ((option = OPTION(argc, argv)) != 0) { + while ((option = getopt(argc, argv, "ef:r:sSt:T:U:vV")) != -1) { switch (option) { case 'e': ++echo; break; - case 'v': - ++verbose; + case 'f': + if (chat_file != NULL) + free(chat_file); + chat_file = copy_of(optarg); break; - case 'V': - ++Verbose; + case 'r': + if (report_fp != NULL) + fclose(report_fp); + if (report_file != NULL) + free(report_file); + report_file = copy_of(optarg); + report_fp = fopen(report_file, "a"); + if (report_fp != NULL) { + if (verbose) + fprintf(report_fp, "Opening \"%s\"...\n", report_file); + } else + fatal(2, "cannot open \"%s\" for appending", report_file); break; case 's': @@ -237,47 +238,28 @@ main(int argc, char *argv[]) to_log = 0; break; - case 'f': - if ((arg = OPTARG(argc, argv)) != NULL) - chat_file = copy_of(arg); - else - usage(); + case 't': + timeout = atoi(optarg); break; - case 't': - if ((arg = OPTARG(argc, argv)) != NULL) - timeout = atoi(arg); - else - usage(); + case 'T': + if (phone_num != NULL) + free(phone_num); + phone_num = copy_of(optarg); break; - case 'r': - arg = OPTARG (argc, argv); - if (arg) { - if (report_fp != NULL) - fclose (report_fp); - report_file = copy_of (arg); - report_fp = fopen (report_file, "a"); - if (report_fp != NULL) { - if (verbose) - fprintf (report_fp, "Opening \"%s\"...\n", - report_file); - } - } + case 'U': + if (phone_num2 != NULL) + free(phone_num2); + phone_num2 = copy_of(optarg); break; - case 'T': - if ((arg = OPTARG(argc, argv)) != NULL) - phone_num = copy_of(arg); - else - usage(); + case 'v': + ++verbose; break; - case 'U': - if ((arg = OPTARG(argc, argv)) != NULL) - phone_num2 = copy_of(arg); - else - usage(); + case 'V': + ++Verbose; break; default: @@ -285,6 +267,10 @@ main(int argc, char *argv[]) break; } } + + argc -= optind; + argv += optind; + /* * Default the report file to the stderr location */ @@ -300,20 +286,25 @@ main(int argc, char *argv[]) setlogmask(LOG_UPTO(LOG_WARNING)); } - init(); - if (chat_file != NULL) { - arg = ARG(argc, argv); - if (arg != NULL) + if (*argv != NULL) usage(); - else - do_file (chat_file); + else { + init(); + do_file(chat_file); + } } else { - while ((arg = ARG(argc, argv)) != NULL) { - chat_expect(arg); - - if ((arg = ARG(argc, argv)) != NULL) - chat_send(arg); + init(); + while (*argv != NULL && argc > 0) { + chat_expect(*argv); + argv++; + argc--; + + if (*argv != NULL && argc > 0) { + chat_send(*argv); + argv++; + argc--; + } } } @@ -397,9 +388,11 @@ do_file(char *chatfile) static void usage(void) { - fprintf(stderr, "\ -Usage: chat [-e] [-v] [-V] [-t timeout] [-r report-file] [-T phone-number]\n\ - [-U phone-number2] {-f chat-file | chat-script}\n"); + fprintf(stderr, + "Usage: chat [-esSvV] [-f chat-file] [-r report-file] [-t timeout]\n" + " [-T phone-number] [-U phone-number2] [chat-script]\n" + "where chat-script has the form:\n" + " [...[[expect[-send[-expect...]] send expect[-send[-expect]] ...]]]\n"); exit(1); } |