blob: 30837709f1c5c5a35e9da35b1988896df05e6dad [file] [log] [blame]
Eitan Isaacson109996e2008-12-20 14:52:53 +00001/* liblouis Braille Translation and Back-Translation Library
2
3 Based on BRLTTY, copyright (C) 1999-2006 by
4 The BRLTTY Team
5
Christian Egli08d96a72009-10-08 08:49:13 +00006 Copyright (C) 2004, 2005, 2006, 2009
7 ViewPlus Technologies, Inc. www.viewplus.com and
Eitan Isaacson109996e2008-12-20 14:52:53 +00008 JJB Software, Inc. www.jjb-software.com
9
Christian Egli08d96a72009-10-08 08:49:13 +000010 This program is free software: you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation, either version 3 of the License, or
13 (at your option) any later version.
14
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
19
Eitan Isaacson109996e2008-12-20 14:52:53 +000020 You should have received a copy of the GNU General Public License
Christian Egli08d96a72009-10-08 08:49:13 +000021 along with this program. If not, see <http://www.gnu.org/licenses/>.
Eitan Isaacson109996e2008-12-20 14:52:53 +000022
Eitan Isaacson109996e2008-12-20 14:52:53 +000023 */
24
Christian Egli31ef6ff2015-06-05 11:22:36 +020025# include <config.h>
Eitan Isaacson109996e2008-12-20 14:52:53 +000026#include <stdio.h>
27#include <string.h>
28#include <stdlib.h>
29#include "louis.h"
Christian Eglibe149002009-10-09 09:09:07 +000030#include <getopt.h>
31#include "progname.h"
32#include "version-etc.h"
33
34static const struct option longopts[] =
35{
36 { "help", no_argument, NULL, 'h' },
37 { "version", no_argument, NULL, 'v' },
38 { NULL, 0, NULL, 0 }
39};
40
41const char version_etc_copyright[] =
42 "Copyright %s %d ViewPlus Technologies, Inc. and JJB Software, Inc.";
43
44#define AUTHORS "John J. Boyer"
45
46static void
47print_help (void)
48{
49 printf ("\
Christian Eglibaefdb22012-12-19 09:48:54 +000050Usage: %s [OPTIONS] TABLE[,TABLE,...]\n", program_name);
Christian Eglibe149002009-10-09 09:09:07 +000051
52 fputs ("\
53Examine and debug Braille translation tables. This program allows you\n\
54to inspect liblouis translation tables and gather information about\n\
55them, such as forward and backward rules, characters and dot patterns,\n\
56specific opcodes, the size of a table, whether a hyphenation\n\
57table is used, how many passes the translation takes and much\n\
58more.\n\n", stdout);
59
60 fputs ("\
61 -h, --help display this help and exit\n\
62 -v, --version display version information and exit\n", stdout);
63
64 printf ("\n");
Christian Eglidc50af92012-09-27 13:10:51 +000065 printf ("Report bugs to %s.\n", PACKAGE_BUGREPORT);
66
67#ifdef PACKAGE_PACKAGER_BUG_REPORTS
68 printf ("Report %s bugs to: %s\n", PACKAGE_PACKAGER, PACKAGE_PACKAGER_BUG_REPORTS);
69#endif
70#ifdef PACKAGE_URL
71 printf ("%s home page: <%s>\n", PACKAGE_NAME, PACKAGE_URL);
72#endif
Christian Eglibe149002009-10-09 09:09:07 +000073}
74
Eitan Isaacson109996e2008-12-20 14:52:53 +000075#define BUFSIZE 256
76
John Boyer16689ac2009-01-12 15:11:39 +000077static const TranslationTableHeader *table;
Eitan Isaacson109996e2008-12-20 14:52:53 +000078static char inputBuffer[BUFSIZE];
79
80static int
Eitan Isaacson109996e2008-12-20 14:52:53 +000081getInput (void)
82{
John Boyer16689ac2009-01-12 15:11:39 +000083 int inputLength;
84 inputBuffer[0] = 0;
Eitan Isaacson109996e2008-12-20 14:52:53 +000085 fgets (inputBuffer, sizeof (inputBuffer), stdin);
John Boyer16689ac2009-01-12 15:11:39 +000086 inputLength = strlen (inputBuffer) - 1;
87 if (inputLength < 0) /*EOF on script */
88 exit (0);
89 inputBuffer[inputLength] = 0;
90 return inputLength;
Eitan Isaacson109996e2008-12-20 14:52:53 +000091}
92
93static int
John Boyer16689ac2009-01-12 15:11:39 +000094printRule (TranslationTableRule * thisRule, int mode)
95{
96 printf ("Rule: ");
97 printf ("opcode=%s, ", findOpcodeName (thisRule->opcode));
98 if (thisRule->before)
99 printf ("before=%x, ", thisRule->before);
100 if (thisRule->after)
101 printf ("after=%x, ", thisRule->after);
102 switch (thisRule->opcode)
103 {
104 case CTO_Context:
105 case CTO_Correct:
106 case CTO_SwapCd:
107 case CTO_SwapDd:
108 case CTO_Pass2:
109 case CTO_Pass3:
110 case CTO_Pass4:
111 printf ("code=%s ", showString (thisRule->charsdots, thisRule->charslen
112 + thisRule->dotslen));
113 break;
114 default:
115 if (mode == 0)
116 {
117 printf ("chars=%s, ", showString (thisRule->charsdots,
118 thisRule->charslen));
119 printf ("dots=%s, ",
120 showDots (&thisRule->charsdots[thisRule->charslen],
121 thisRule->dotslen));
122 }
123 else
124 {
125 printf ("dots=%s, ",
126 showDots (&thisRule->charsdots[thisRule->charslen],
127 thisRule->dotslen));
128 printf ("chars=%s, ", showString (thisRule->charsdots,
129 thisRule->charslen));
130 }
131 break;
132 }
133 return 1;
134}
135
136static int
137printCharacter (TranslationTableCharacter * thisChar, int mode)
138{
139 TranslationTableRule *thisRule;
140 TranslationTableOffset nextRule;
141 if (mode == 0)
142 {
143 printf ("Char: ");
144 printf ("real=%s, ", showString (&thisChar->realchar, 1));
145 printf ("upper=%s, ", showString (&thisChar->uppercase, 1));
146 printf ("lower=%s, ", showString (&thisChar->lowercase, 1));
147 }
148 else
149 printf ("Dots: real=%s, ", showDots (&thisChar->realchar, 1));
150 printf ("attr=%s, ", showAttributes (thisChar->attributes));
151 nextRule = thisChar->otherRules;
152 while (nextRule)
153 {
154 thisRule = (TranslationTableRule *) & table->ruleArea[nextRule];
John Boyerc675d7a2009-01-15 14:32:20 +0000155 if (nextRule == thisChar->definitionRule)
John Boyer16689ac2009-01-12 15:11:39 +0000156 printf ("definition ");
157 printRule (thisRule, mode);
158 printf ("\n");
159 if (mode == 0)
160 nextRule = thisRule->charsnext;
161 else
162 nextRule = thisRule->dotsnext;
163 }
164 return 1;
165}
166
167static int
168show_characters (int startHash)
169{
170 int k;
171 TranslationTableCharacter *thisChar;
172 TranslationTableOffset nextChar;
173 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
174 if (startHash < 0)
175 k = 0;
176 else
177 k = startHash;
178 for (; k < HASHNUM; k++)
179 if (table->characters[k])
180 {
181 printf ("Hash=%d\n", k);
182 nextChar = table->characters[k];
183 while (nextChar)
184 {
185 thisChar =
186 (TranslationTableCharacter *) & table->ruleArea[nextChar];
187 printCharacter (thisChar, 0);
188 printf ("=> ");
189 getInput ();
190 if (*inputBuffer == 'h')
191 break;
192 if (*inputBuffer == 'e')
193 return 1;
194 nextChar = thisChar->next;
195 }
196 }
197 return 1;
198}
199
200static int
201show_dots (int startHash)
202{
203 int k;
204 TranslationTableCharacter *thisDots;
205 TranslationTableOffset nextDots;
206 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
207 if (startHash < 0)
208 k = 0;
209 else
210 k = startHash;
211 for (; k < HASHNUM; k++)
212 if (table->dots[k])
213 {
214 printf ("Hash=%d\n", k);
215 nextDots = table->dots[k];
216 while (nextDots)
217 {
218 thisDots =
219 (TranslationTableCharacter *) & table->ruleArea[nextDots];
220 printCharacter (thisDots, 1);
221 printf ("=> ");
222 getInput ();
223 if (*inputBuffer == 'h')
224 break;
225 if (*inputBuffer == 'e')
226 return 1;
227 nextDots = thisDots->next;
228 }
229 }
230 return 1;
231}
232
233static int
234show_forRules (int startHash)
235{
236 int k;
237 TranslationTableRule *thisRule;
238 TranslationTableOffset nextRule;
239 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
240 if (startHash < 0)
241 k = 0;
242 else
243 k = startHash;
244 for (; k < HASHNUM; k++)
245 if (table->forRules[k])
246 {
247 printf ("Hash=%d\n", k);
248 nextRule = table->forRules[k];
249 while (nextRule)
250 {
251 thisRule = (TranslationTableRule *) & table->ruleArea[nextRule];
252 printRule (thisRule, 0);
253 printf ("=> ");
254 getInput ();
255 if (*inputBuffer == 'h')
256 break;
257 if (*inputBuffer == 'e')
258 return 1;
259 nextRule = thisRule->charsnext;
260 }
261 }
262 return 1;
263}
264
265static int
266show_backRules (int startHash)
267{
268 int k;
269 TranslationTableRule *thisRule;
270 TranslationTableOffset nextRule;
271 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
272 if (startHash < 0)
273 k = 0;
274 else
275 k = startHash;
276 for (; k < HASHNUM; k++)
277 if (table->backRules[k])
278 {
279 printf ("Hash=%d\n", k);
280 nextRule = table->backRules[k];
281 while (nextRule)
282 {
283 thisRule = (TranslationTableRule *) & table->ruleArea[nextRule];
284 printRule (thisRule, 1);
285 printf ("=> ");
286 getInput ();
287 if (*inputBuffer == 'h')
288 break;
289 if (*inputBuffer == 'e')
290 return 1;
291 nextRule = thisRule->dotsnext;
292 }
293 }
294 return 1;
295}
296
297static int
298print_brailleIndicator (TranslationTableOffset offset, char *opcode)
299{
300 TranslationTableRule *thisRule;
301 if (!offset)
302 return 0;
303 thisRule = (TranslationTableRule *) & table->ruleArea[offset];
304 printf ("%s %s\n", opcode,
305 showDots (&thisRule->charsdots[0], thisRule->dotslen));
306 return 1;
307}
308
309static int
310print_phraseLength (TranslationTableOffset offset, char *opcode)
311{
312 if (!offset)
313 return 0;
314 printf ("%s %d\n", opcode, offset);
Christian Eglifbfea8b2009-08-11 11:24:40 +0000315 return 1;
John Boyer16689ac2009-01-12 15:11:39 +0000316}
317
318static int
319show_brailleIndicators (void)
320{
Davy Kager68004042016-01-26 12:50:22 +0100321 // FIXME: update to include all UEB opcodes.
322 print_brailleIndicator (table->singleLetterCaps, "capsletter");
323 print_brailleIndicator (table->firstLetterCaps, "begcaps");
324 print_brailleIndicator (table->lastLetterCaps, "endcaps");
John Boyer16689ac2009-01-12 15:11:39 +0000325 print_brailleIndicator (table->firstWordCaps, "firstwordcaps");
Davy Kager1f3d2f32015-12-08 09:46:35 +0100326 print_brailleIndicator (table->lastWordCapsAfter, "lastwordcapsafter");
John Boyer16689ac2009-01-12 15:11:39 +0000327 print_phraseLength (table->lenCapsPhrase, "lencapsphrase");
328 print_brailleIndicator (table->letterSign, "letsign");
329 print_brailleIndicator (table->numberSign, "numsign");
330 print_brailleIndicator (table->firstWordItal, "firstwordital");
331 print_brailleIndicator (table->lastWordItalBefore, "lastworditalbefore");
332 print_brailleIndicator (table->lastWordItalAfter, "lastworditalafter");
333 print_brailleIndicator (table->firstLetterItal, "firstletterital");
334 print_brailleIndicator (table->lastLetterItal, "lastletterital");
335 print_brailleIndicator (table->singleLetterItal, "singleletterital");
336 print_brailleIndicator (table->italWord, "italword");
337 print_phraseLength (table->lenItalPhrase, "lenitalphrase");
338 print_brailleIndicator (table->firstWordBold, "firstwordbold");
339 print_brailleIndicator (table->lastWordBoldBefore, "lastwordboldbefore");
340 print_brailleIndicator (table->lastWordBoldAfter, "lastwordboldafter");
341 print_brailleIndicator (table->firstLetterBold, "firstletterbold");
342 print_brailleIndicator (table->lastLetterBold, "lastletterbold");
343 print_brailleIndicator (table->singleLetterBold, "singleletterbold");
344 print_brailleIndicator (table->boldWord, "boldword");
345 print_phraseLength (table->lenBoldPhrase, "lenboldphrase");
346 print_brailleIndicator (table->firstWordUnder, "firstwordunder");
347 print_brailleIndicator (table->lastWordUnderBefore, "lastwordunderbefore");
348 print_brailleIndicator (table->lastWordUnderAfter, "lastwordunderafter");
349 print_brailleIndicator (table->firstLetterUnder, "firstletterunder");
350 print_brailleIndicator (table->lastLetterUnder, "lastletterunder");
351 print_brailleIndicator (table->singleLetterUnder, "singleletterunder");
352 print_brailleIndicator (table->underWord, "underword");
353 print_phraseLength (table->lenUnderPhrase, "lenunderphrase");
354 print_brailleIndicator (table->begComp, "begcomp");
355 print_brailleIndicator (table->compBegEmph1, "compbegemph1");
356 print_brailleIndicator (table->compEndEmph1, "compendemph1");
357 print_brailleIndicator (table->compBegEmph2, "compbegemph2");
358 print_brailleIndicator (table->compEndEmph2, "compendemph2");
359 print_brailleIndicator (table->compBegEmph3, "compbegemph3");
360 print_brailleIndicator (table->compEndEmph3, "compendemph3");
361 print_brailleIndicator (table->compCapSign, "compcapsign");
362 print_brailleIndicator (table->compBegCaps, "compbegcaps");
363 print_brailleIndicator (table->compEndCaps, "compendcaps");
364 print_brailleIndicator (table->endComp, "endcomp");
365 return 1;
366}
367
368static char *
369pickYN (int a)
370{
371 if (!a)
372 return "no";
373 return "yes";
374}
375
376static int
377show_misc (void)
378{
379 printf ("Table size: %d\n", table->tableSize);
380 printf ("Bytes used: %d\n", table->bytesUsed);
381 printf ("Number of passes: %d\n", table->numPasses);
Christian Egli5e8c3892009-01-15 16:30:59 +0000382 printf ("'correct' opcodes: %s\n", pickYN (table->corrections));
John Boyer16689ac2009-01-12 15:11:39 +0000383 printf ("'syllable' opcodes: %s\n", pickYN (table->syllables));
384 printf ("'capsnocont' opcode: %s\n", pickYN (table->capsNoCont));
385 printf ("Hyphenation table: %s\n", pickYN (table->hyphenStatesArray));
386 printf ("noletsignbefore %s\n", showString (&table->noLetsignBefore[0],
387 table->noLetsignBeforeCount));
388 printf ("noletsign %s\n", showString (&table->noLetsign[0],
389 table->noLetsignCount));
390 printf ("noletsignafter %s\n", showString (&table->noLetsignAfter[0],
391 table->noLetsignAfterCount));
Christian Eglifbfea8b2009-08-11 11:24:40 +0000392 return 1;
John Boyer16689ac2009-01-12 15:11:39 +0000393}
394
395static int
396show_charMap (int startHash)
397{
398 int k;
399 CharOrDots *thisChar;
400 TranslationTableOffset nextChar;
401 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
402 if (startHash < 0)
403 k = 0;
404 else
405 k = startHash;
406 for (; k < HASHNUM; k++)
407 if (table->charToDots[k])
408 {
409 printf ("Hash=%d\n", k);
410 nextChar = table->charToDots[k];
411 while (nextChar)
412 {
413 thisChar = (CharOrDots *) & table->ruleArea[nextChar];
414 printf ("Char: %s ", showString (&thisChar->lookFor, 1));
415 printf ("dots=%s\n", showDots (&thisChar->found, 1));
416 printf ("=> ");
417 getInput ();
418 if (*inputBuffer == 'h')
419 break;
420 if (*inputBuffer == 'e')
421 return 1;
422 nextChar = thisChar->next;
423 }
424 }
425 return 1;
426}
427
428static int
429show_dotsMap (int startHash)
430{
431 int k;
432 CharOrDots *thisDots;
433 TranslationTableOffset nextDots;
434 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
435 if (startHash < 0)
436 k = 0;
437 else
438 k = startHash;
439 for (; k < HASHNUM; k++)
440 if (table->dotsToChar[k])
441 {
442 printf ("Hash=%d\n", k);
443 nextDots = table->dotsToChar[k];
444 while (nextDots)
445 {
446 thisDots = (CharOrDots *) & table->ruleArea[nextDots];
447 printf ("Dots: %s ", showDots (&thisDots->lookFor, 1));
448 printf ("char=%s\n", showString (&thisDots->found, 1));
449 printf ("=> ");
450 getInput ();
451 if (*inputBuffer == 'h')
452 break;
453 if (*inputBuffer == 'e')
454 return 1;
455 nextDots = thisDots->next;
456 }
457 }
458 return 1;
459}
460
461static int
462show_compDots (int startChar)
463{
464 widechar k;
465 printf ("Press enter for next or (e)xit, next-(h)ash, then enter\n");
466 if (startChar < 0)
467 k = 0;
468 else
469 k = startChar;
470 for (; k < 256; k++)
471 if (table->compdotsPattern[k])
472 {
473 TranslationTableRule *thisRule = (TranslationTableRule *)
474 & table->ruleArea[table->compdotsPattern[k]];
475 printf ("Char: %s ", showString (&k, 1));
476 printf ("dots=%s\n",
477 showDots (&thisRule->charsdots[1], thisRule->dotslen));
478 printf ("=> ");
479 getInput ();
480 if (*inputBuffer == 'e')
481 return 1;
482 }
483 return 1;
484}
485
486static void
487part_paramLetters ()
488{
489 printf ("show particular hash chains.\n");
490 printf
491 ("show-(f)orward-rules, show-(b)ackward-rules, show-(c)haracters, \n");
492 printf ("show-(d)ot-patterns, show-(C)har-to-dots, show-(D)ots-tochar\n");
493 printf ("(z)-compdots, (h)elp, e(x)it\n");
494}
495
496static void
497particularHelp (void)
498{
499 part_paramLetters ();
500}
501
502static int
503particular (void)
504{
505 int startHash;
506 widechar parsed[BUFSIZE];
507 part_paramLetters ();
508 do
509 {
510 printf ("particular: ");
511 getInput ();
512 switch (inputBuffer[0])
513 {
514 case 0:
515 break;
516 case 'h':
517 particularHelp ();
518 break;
519 case 'c':
520 printf ("-> ");
521 getInput ();
522 if (!extParseChars (inputBuffer, parsed))
523 break;
524 startHash = charHash (*parsed);
525 if (table->characters[startHash] == 0)
526 {
527 printf ("Character not in table.\n");
528 break;
529 }
530 show_characters (startHash);
531 break;
532 case 'd':
533 printf ("-> ");
534 getInput ();
535 if (!extParseDots (inputBuffer, parsed))
536 break;
537 startHash = charHash (*parsed);
538 if (table->dots[startHash] == 0)
539 {
540 printf ("Dot pattern not in table.\n");
541 break;
542 }
543 show_dots (startHash);
544 break;
545 case 'C':
546 printf ("-> ");
547 getInput ();
548 if (!extParseChars (inputBuffer, parsed))
549 break;
550 startHash = charHash (*parsed);
551 if (table->charToDots[startHash] == 0)
552 {
553 printf ("Character not in table.\n");
554 break;
555 }
556 show_charMap (startHash);
557 break;
558 case 'D':
559 printf ("-> ");
560 getInput ();
561 if (!extParseDots (inputBuffer, parsed))
562 break;
563 startHash = charHash (*parsed);
564 if (table->dotsToChar[startHash] == 0)
565 {
566 printf ("Dot pattern not in table.\n");
567 break;
568 }
569 show_dotsMap (startHash);
570 break;
571 case 'f':
572 printf ("-> ");
573 getInput ();
574 if (!extParseChars (inputBuffer, parsed))
575 break;
576 startHash = stringHash (parsed);
577 if (table->forRules[startHash] == 0)
578 {
579 printf ("Character string not in table.\n");
580 break;
581 }
582 show_forRules (startHash);
583 break;
584 case 'b':
585 printf ("-> ");
586 getInput ();
587 if (!extParseDots (inputBuffer, parsed))
588 break;
589 startHash = stringHash (parsed);
590 if (table->backRules[startHash] == 0)
591 {
592 printf ("Dot pattern not in table.\n");
593 break;
594 }
595 show_backRules (startHash);
596 break;
597 case 'z':
598 printf ("-> ");
599 getInput ();
600 if (!extParseChars (inputBuffer, parsed))
601 break;
602 startHash = charHash (*parsed);
603 if (*parsed > 255 || table->compdotsPattern[startHash] == 0)
604 {
605 printf ("Character not in table.\n");
606 break;
607 }
608 show_compDots (startHash);
609 break;
610 case 'x':
611 return 1;
612 default:
613 printf ("Bad choice.\n");
614 break;
615 }
616 }
617 while (inputBuffer[0] != 'x');
618 return 1;
619}
620
Eitan Isaacson109996e2008-12-20 14:52:53 +0000621static void
622paramLetters (void)
623{
John Boyer16689ac2009-01-12 15:11:39 +0000624 printf ("Press one of the letters in parentheses, then enter.\n");
625 printf
626 ("show-(f)orward-rules, show-(b)ackward-rules, show-(c)haracters, \n");
627 printf ("show-(d)ot-patterns, show-(C)har-to-dots, show-(D)ots-tochar\n");
628 printf ("show-(m)isc, show-(z)-compdots\n");
629 printf ("show-(p)articulars, (h)elp, (q)uit\n");
630}
631
632static void
633commandHelp (void)
634{
635 paramLetters ();
Eitan Isaacson109996e2008-12-20 14:52:53 +0000636}
637
638static int
639getCommands (void)
640{
641 paramLetters ();
642 do
643 {
644 printf ("Command: ");
645 getInput ();
646 switch (inputBuffer[0])
647 {
648 case 0:
649 break;
John Boyer16689ac2009-01-12 15:11:39 +0000650 case 'h':
651 commandHelp ();
652 break;
653 case 'C':
654 show_charMap (-1);
655 break;
656 case 'D':
657 show_dotsMap (-1);
658 break;
659 case 'z':
660 show_compDots (-1);
661 break;
662 case 'c':
663 show_characters (-1);
664 break;
665 case 'd':
666 show_dots (-1);
667 break;
668 case 'f':
669 show_forRules (-1);
670 break;
671 case 'b':
672 show_backRules (-1);
673 break;
674 case 'i':
675 show_brailleIndicators ();
676 break;
677 case 'm':
678 show_misc ();
679 break;
680 case 'p':
681 particular ();
682 break;
683 case 'q':
684 return 1;
Eitan Isaacson109996e2008-12-20 14:52:53 +0000685 default:
686 printf ("Bad choice.\n");
687 break;
688 }
689 }
John Boyer16689ac2009-01-12 15:11:39 +0000690 while (inputBuffer[0] != 'q');
Eitan Isaacson109996e2008-12-20 14:52:53 +0000691 return 1;
692}
693
694int
695main (int argc, char **argv)
696{
Christian Eglibe149002009-10-09 09:09:07 +0000697 int optc;
698
699 set_program_name (argv[0]);
700
701 while ((optc = getopt_long (argc, argv, "hv", longopts, NULL)) != -1)
702 switch (optc)
703 {
704 /* --help and --version exit immediately, per GNU coding standards. */
705 case 'v':
706 version_etc (stdout, program_name, PACKAGE_NAME, VERSION, AUTHORS, (char *) NULL);
707 exit (EXIT_SUCCESS);
708 break;
709 case 'h':
710 print_help ();
711 exit (EXIT_SUCCESS);
712 break;
713 default:
714 fprintf (stderr, "Try `%s --help' for more information.\n",
715 program_name);
716 exit (EXIT_FAILURE);
717 break;
718 }
719
720 if (optind != argc - 1)
Eitan Isaacson109996e2008-12-20 14:52:53 +0000721 {
Christian Eglibe149002009-10-09 09:09:07 +0000722 /* Print error message and exit. */
723 if (optind < argc - 1)
724 fprintf (stderr, "%s: extra operand: %s\n",
725 program_name, argv[optind + 1]);
726 else
727 fprintf (stderr, "%s: no table specified\n",
728 program_name);
729 fprintf (stderr, "Try `%s --help' for more information.\n",
730 program_name);
731 exit (EXIT_FAILURE);
Eitan Isaacson109996e2008-12-20 14:52:53 +0000732 }
Christian Eglibe149002009-10-09 09:09:07 +0000733
734 if (!(table = lou_getTable (argv[optind])))
John Boyer16689ac2009-01-12 15:11:39 +0000735 {
736 lou_free ();
Christian Eglibe149002009-10-09 09:09:07 +0000737 exit (EXIT_FAILURE);
John Boyer16689ac2009-01-12 15:11:39 +0000738 }
739 getCommands ();
Eitan Isaacson109996e2008-12-20 14:52:53 +0000740 lou_free ();
Christian Eglibe149002009-10-09 09:09:07 +0000741 exit (EXIT_SUCCESS);
Eitan Isaacson109996e2008-12-20 14:52:53 +0000742}