Annotation of 43BSDReno/contrib/emacs-18.55/gdb/command.c, revision 1.1

1.1     ! root        1: /* Library for reading command lines and decoding commands.
        !             2:    Copyright (C) 1986 Free Software Foundation, Inc.
        !             3: 
        !             4:                       NO WARRANTY
        !             5: 
        !             6:   BECAUSE THIS PROGRAM IS LICENSED FREE OF CHARGE, WE PROVIDE ABSOLUTELY
        !             7: NO WARRANTY, TO THE EXTENT PERMITTED BY APPLICABLE STATE LAW.  EXCEPT
        !             8: WHEN OTHERWISE STATED IN WRITING, FREE SOFTWARE FOUNDATION, INC,
        !             9: RICHARD M. STALLMAN AND/OR OTHER PARTIES PROVIDE THIS PROGRAM "AS IS"
        !            10: WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
        !            11: BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
        !            12: FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS TO THE QUALITY
        !            13: AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE PROGRAM PROVE
        !            14: DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR
        !            15: CORRECTION.
        !            16: 
        !            17:  IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW WILL RICHARD M.
        !            18: STALLMAN, THE FREE SOFTWARE FOUNDATION, INC., AND/OR ANY OTHER PARTY
        !            19: WHO MAY MODIFY AND REDISTRIBUTE THIS PROGRAM AS PERMITTED BELOW, BE
        !            20: LIABLE TO YOU FOR DAMAGES, INCLUDING ANY LOST PROFITS, LOST MONIES, OR
        !            21: OTHER SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
        !            22: USE OR INABILITY TO USE (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR
        !            23: DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY THIRD PARTIES OR
        !            24: A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS) THIS
        !            25: PROGRAM, EVEN IF YOU HAVE BEEN ADVISED OF THE POSSIBILITY OF SUCH
        !            26: DAMAGES, OR FOR ANY CLAIM BY ANY OTHER PARTY.
        !            27: 
        !            28:                GENERAL PUBLIC LICENSE TO COPY
        !            29: 
        !            30:   1. You may copy and distribute verbatim copies of this source file
        !            31: as you receive it, in any medium, provided that you conspicuously and
        !            32: appropriately publish on each copy a valid copyright notice "Copyright
        !            33: (C) 1986 Free Software Foundation, Inc."; and include following the
        !            34: copyright notice a verbatim copy of the above disclaimer of warranty
        !            35: and of this License.  You may charge a distribution fee for the
        !            36: physical act of transferring a copy.
        !            37: 
        !            38:   2. You may modify your copy or copies of this source file or
        !            39: any portion of it, and copy and distribute such modifications under
        !            40: the terms of Paragraph 1 above, provided that you also do the following:
        !            41: 
        !            42:     a) cause the modified files to carry prominent notices stating
        !            43:     that you changed the files and the date of any change; and
        !            44: 
        !            45:     b) cause the whole of any work that you distribute or publish,
        !            46:     that in whole or in part contains or is a derivative of this
        !            47:     program or any part thereof, to be licensed at no charge to all
        !            48:     third parties on terms identical to those contained in this
        !            49:     License Agreement (except that you may choose to grant more extensive
        !            50:     warranty protection to some or all third parties, at your option).
        !            51: 
        !            52:     c) You may charge a distribution fee for the physical act of
        !            53:     transferring a copy, and you may at your option offer warranty
        !            54:     protection in exchange for a fee.
        !            55: 
        !            56: Mere aggregation of another unrelated program with this program (or its
        !            57: derivative) on a volume of a storage or distribution medium does not bring
        !            58: the other program under the scope of these terms.
        !            59: 
        !            60:   3. You may copy and distribute this program (or a portion or derivative
        !            61: of it, under Paragraph 2) in object code or executable form under the terms
        !            62: of Paragraphs 1 and 2 above provided that you also do one of the following:
        !            63: 
        !            64:     a) accompany it with the complete corresponding machine-readable
        !            65:     source code, which must be distributed under the terms of
        !            66:     Paragraphs 1 and 2 above; or,
        !            67: 
        !            68:     b) accompany it with a written offer, valid for at least three
        !            69:     years, to give any third party free (except for a nominal
        !            70:     shipping charge) a complete machine-readable copy of the
        !            71:     corresponding source code, to be distributed under the terms of
        !            72:     Paragraphs 1 and 2 above; or,
        !            73: 
        !            74:     c) accompany it with the information you received as to where the
        !            75:     corresponding source code may be obtained.  (This alternative is
        !            76:     allowed only for noncommercial distribution and only if you
        !            77:     received the program in object code or executable form alone.)
        !            78: 
        !            79: For an executable file, complete source code means all the source code for
        !            80: all modules it contains; but, as a special exception, it need not include
        !            81: source code for modules which are standard libraries that accompany the
        !            82: operating system on which the executable file runs.
        !            83: 
        !            84:   4. You may not copy, sublicense, distribute or transfer this program
        !            85: except as expressly provided under this License Agreement.  Any attempt
        !            86: otherwise to copy, sublicense, distribute or transfer this program is void and
        !            87: your rights to use the program under this License agreement shall be
        !            88: automatically terminated.  However, parties who have received computer
        !            89: software programs from you with this License Agreement will not have
        !            90: their licenses terminated so long as such parties remain in full compliance.
        !            91: 
        !            92:   5. If you wish to incorporate parts of this program into other free
        !            93: programs whose distribution conditions are different, write to the Free
        !            94: Software Foundation at 675 Mass Ave, Cambridge, MA 02139.  We have not yet
        !            95: worked out a simple rule that can be stated here, but we will often permit
        !            96: this.  We will be guided by the two goals of preserving the free status of
        !            97: all derivatives of our free software and of promoting the sharing and reuse of
        !            98: software.
        !            99: 
        !           100: 
        !           101: In other words, you are welcome to use, share and improve this program.
        !           102: You are forbidden to forbid anyone else to use, share and improve
        !           103: what you give them.   Help stamp out software-hoarding!  */
        !           104: 
        !           105: 
        !           106: #include "command.h"
        !           107: #include <stdio.h>
        !           108: 
        !           109: extern char *xmalloc ();
        !           110: 
        !           111: static char *savestring ();
        !           112: 
        !           113: /* Add element named NAME to command list *LIST.
        !           114:    FUN should be the function to execute the command;
        !           115:    it will get a character string as argument, with leading
        !           116:    and trailing blanks already eliminated.
        !           117: 
        !           118:    DOC is a documentation string for the command.
        !           119:    Its first line should be a complete sentence.
        !           120:    It should start with ? for a command that is an abbreviation
        !           121:    or with * for a command that most users don't need to know about.  */
        !           122: 
        !           123: struct cmd_list_element *
        !           124: add_cmd (name, class, fun, doc, list)
        !           125:      char *name;
        !           126:      int class;
        !           127:      void (*fun) ();
        !           128:      char *doc;
        !           129:      struct cmd_list_element **list;
        !           130: {
        !           131:   register struct cmd_list_element *c
        !           132:     = (struct cmd_list_element *) xmalloc (sizeof (struct cmd_list_element));
        !           133: 
        !           134:   delete_cmd (name, list);
        !           135:   c->next = *list;
        !           136:   c->name = savestring (name, strlen (name));
        !           137:   c->class = class;
        !           138:   c->function = fun;
        !           139:   c->doc = doc;
        !           140:   c->prefixlist = 0;
        !           141:   c->allow_unknown = 0;
        !           142:   c->abbrev_flag = 0;
        !           143:   c->aux = 0;
        !           144:   *list = c;
        !           145:   return c;
        !           146: }
        !           147: 
        !           148: struct cmd_list_element *
        !           149: add_alias_cmd (name, oldname, class, abbrev_flag, list)
        !           150:      char *name;
        !           151:      char *oldname;
        !           152:      int class;
        !           153:      int abbrev_flag;
        !           154:      struct cmd_list_element **list;
        !           155: {
        !           156:   /* Must do this since lookup_cmd tries to side-effect its first arg */
        !           157:   char *copied_name;
        !           158:   register struct cmd_list_element *old;
        !           159:   register struct cmd_list_element *c;
        !           160:   copied_name = (char *) alloca (strlen (oldname) + 1);
        !           161:   strcpy (copied_name, oldname);
        !           162:   old  = lookup_cmd (&copied_name, *list, 0, 1);
        !           163: 
        !           164:   if (old == 0)
        !           165:     {
        !           166:       delete_cmd (name, list);
        !           167:       return 0;
        !           168:     }
        !           169: 
        !           170:   c = add_cmd (name, class, old->function, old->doc, list);
        !           171:   c->prefixlist = old->prefixlist;
        !           172:   c->prefixname = old->prefixname;
        !           173:   c->allow_unknown = old->allow_unknown;
        !           174:   c->abbrev_flag = abbrev_flag;
        !           175:   c->aux = old->aux;
        !           176:   return c;
        !           177: }
        !           178: 
        !           179: /* Like add_prefix_cmd but adds an element for a command prefix:
        !           180:    a name that should be followed by a subcommand to be looked up
        !           181:    in another command list.  PREFIXLIST should be the address
        !           182:    of the variable containing that list.  */
        !           183: 
        !           184: struct cmd_list_element *
        !           185: add_prefix_cmd (name, class, fun, doc, prefixlist, prefixname,
        !           186:                allow_unknown, list)
        !           187:      char *name;
        !           188:      int class;
        !           189:      void (*fun) ();
        !           190:      char *doc;
        !           191:      struct cmd_list_element **prefixlist;
        !           192:      char *prefixname;
        !           193:      int allow_unknown;
        !           194:      struct cmd_list_element **list;
        !           195: {
        !           196:   register struct cmd_list_element *c = add_cmd (name, class, fun, doc, list);
        !           197:   c->prefixlist = prefixlist;
        !           198:   c->prefixname = prefixname;
        !           199:   c->allow_unknown = allow_unknown;
        !           200:   return c;
        !           201: }
        !           202: 
        !           203: /* Remove the command named NAME from the command list.  */
        !           204: 
        !           205: void
        !           206: delete_cmd (name, list)
        !           207:      char *name;
        !           208:      struct cmd_list_element **list;
        !           209: {
        !           210:   register struct cmd_list_element *c;
        !           211: 
        !           212:   while (*list && !strcmp ((*list)->name, name))
        !           213:     {
        !           214:       *list = (*list)->next;
        !           215:     }
        !           216: 
        !           217:   if (*list)
        !           218:     for (c = *list; c->next;)
        !           219:       {
        !           220:        if (!strcmp (c->next->name, name))
        !           221:          c->next = c->next->next;
        !           222:        else
        !           223:          c = c->next;
        !           224:       }
        !           225: }
        !           226: 
        !           227: /* Implement a help command on command list LIST.
        !           228:    COMMAND is the argument given (a command from the list to document)
        !           229:    or zero for no arg (describe briefly all the commands in the list).
        !           230:    CMDTYPE is a string to use in the error message if command COMMAND
        !           231:    is not found in the list.  */
        !           232: 
        !           233: /* CLASS should be -1 to list all commands in LIST,
        !           234:    or a nonnegative class number value to list just commands in that class,
        !           235:    or -2 to list the classes themselves.  */
        !           236: 
        !           237: void
        !           238: help_cmd (command, list, cmdtype, class, stream)
        !           239:      char *command;
        !           240:      struct cmd_list_element *list;
        !           241:      char *cmdtype;
        !           242:      int class;
        !           243:      FILE *stream;
        !           244: {
        !           245:   register struct cmd_list_element *c;
        !           246:   register char *p;
        !           247:   register int ncmds;
        !           248:   struct cmdvec { struct cmd_list_element *cmd; int class; };
        !           249:   register struct cmdvec *cmdvec;
        !           250:   char *cmdtype1, *cmdtype2;
        !           251:   int len;
        !           252: 
        !           253:   if (command)
        !           254:     {
        !           255:       c = lookup_cmd (&command, list, cmdtype, 0);
        !           256:       if (c == 0)
        !           257:        return;
        !           258: 
        !           259:       /* There are three cases here.
        !           260:         If c->prefixlist is nonzer, we have a prefix command.
        !           261:         Print its documentation, then list its subcommands.
        !           262: 
        !           263:         If c->function is nonzero, we really have a command.
        !           264:         Print its documentation and return.
        !           265: 
        !           266:         If c->function is zero, we have a class name.
        !           267:         Print its documentation (as if it were a command)
        !           268:         and then set class to he number of this class
        !           269:         so that the commands in the class will be listed.  */
        !           270: 
        !           271:       p = c->doc;
        !           272:       fprintf (stream, "%s\n", p);
        !           273:       if (c->function != 0 && c->prefixlist == 0)
        !           274:        return;
        !           275:       fputc ('\n', stream);
        !           276:       if (c->prefixlist)
        !           277:        {
        !           278:          list = *c->prefixlist;
        !           279:          class = 0;
        !           280:          cmdtype = c->prefixname;
        !           281:        }
        !           282:       else
        !           283:        class = c->class;
        !           284:     }
        !           285: 
        !           286:   /* If CMDTYPE is "foo ", CMDTYPE1 gets " foo" and CMDTYPE2 gets "foo sub"  */
        !           287:   len = strlen (cmdtype);
        !           288:   cmdtype1 = (char *) alloca (len + 1);
        !           289:   cmdtype1[0] = 0;
        !           290:   cmdtype2 = (char *) alloca (len + 4);
        !           291:   cmdtype2[0] = 0;
        !           292:   if (len)
        !           293:     {
        !           294:       cmdtype1[0] = ' ';
        !           295:       strncpy (cmdtype1 + 1, cmdtype, len - 1);
        !           296:       cmdtype1[len] = 0;
        !           297:       strncpy (cmdtype2, cmdtype, len - 1);
        !           298:       strcpy (cmdtype2 + len - 1, " sub");
        !           299:     }
        !           300: 
        !           301:   if (class == -2)
        !           302:     fprintf (stream, "List of classes of %scommands:\n\n", cmdtype2);
        !           303:   else
        !           304:     fprintf (stream, "List of %scommands:\n\n", cmdtype2);
        !           305: 
        !           306:   for (c = list; c; c = c->next)
        !           307:     {
        !           308:       if (c->abbrev_flag == 0
        !           309:          && (class == -1       /* Listing all */
        !           310:              || (c->class == class && c->function != 0) /* Listing one class */
        !           311:              || (class == -2 && c->function == 0)))    /* Listing the classes */
        !           312:        {
        !           313:          fprintf (stream, "%s -- ", c->name);
        !           314:          /* Print just first line of documentation.  */
        !           315:          p = c->doc;
        !           316:          while (*p && *p != '\n') p++;
        !           317:          fwrite (c->doc, 1, p - c->doc, stream);
        !           318:          fputc ('\n', stream);
        !           319:        }
        !           320:     }
        !           321: 
        !           322:   if (class == -2)
        !           323:     fprintf (stream, "\n\
        !           324: Type \"help%s\" followed by a class name for a list of commands in that class.",
        !           325:             cmdtype1);
        !           326: 
        !           327:   fprintf (stream, "\n\
        !           328: Type \"help%s\" followed by %scommand name for full documentation.\n\
        !           329: Command name abbreviations are allowed if unambiguous.\n",
        !           330:           cmdtype1, cmdtype2);
        !           331: }
        !           332: 
        !           333: /* Look up the contents of *LINE as a command in the command list LIST.
        !           334:    LIST is a chain of struct cmd_list_element's.
        !           335:    If it is found, return the struct cmd_list_element for that command
        !           336:    and update *LINE to point after the command name, at the first argument.
        !           337:    If not found, call error if ALLOW_UNKNOWN is zero
        !           338:    otherwise (or if error returns) return zero.
        !           339:    Call error if specified command is ambiguous,
        !           340:    unless ALLOW_UNKNOWN is negative.
        !           341:    CMDTYPE precedes the word "command" in the error message.  */
        !           342: 
        !           343: struct cmd_list_element *
        !           344: lookup_cmd (line, list, cmdtype, allow_unknown)
        !           345:      char **line;
        !           346:      struct cmd_list_element *list;
        !           347:      char *cmdtype;
        !           348:      int allow_unknown;
        !           349: {
        !           350:   register char *p;
        !           351:   register struct cmd_list_element *c, *found;
        !           352:   int nfound;
        !           353:   char ambbuf[100];
        !           354: 
        !           355:   /* Skip leading whitespace.  */
        !           356: 
        !           357:   while (**line == ' ' || **line == '\t')
        !           358:     (*line)++;
        !           359: 
        !           360:   /* Clear out trailing whitespace.  */
        !           361: 
        !           362:   p = *line + strlen (*line);
        !           363:   while (p != *line && (p[-1] == ' ' || p[-1] == '\t'))
        !           364:     p--;
        !           365:   *p = 0;
        !           366: 
        !           367:   /* Find end of command name.  */
        !           368: 
        !           369:   p = *line;
        !           370:   while (*p == '-'
        !           371:         || (*p >= 'a' && *p <= 'z')
        !           372:         || (*p >= 'A' && *p <= 'Z')
        !           373:         || (*p >= '0' && *p <= '9'))
        !           374:     {
        !           375:       if (*p >= 'A' && *p <= 'Z')
        !           376:        *p += 'a' - 'A';
        !           377:       p++;
        !           378:     }
        !           379: 
        !           380:   /* Look up the command name.
        !           381:      If exact match, keep that.
        !           382:      Otherwise, take command abbreviated, if unique.  */
        !           383: 
        !           384:   found = 0;
        !           385:   nfound = 0;
        !           386:   for (c = list; c; c = c->next)
        !           387:     {
        !           388:       if (!strncmp (*line, c->name, p - *line))
        !           389:        {
        !           390:          found = c;
        !           391:          nfound++;
        !           392:          if (c->name[p - *line] == 0)
        !           393:            {
        !           394:              nfound = 1;
        !           395:              break;
        !           396:            }
        !           397:        }
        !           398:     }
        !           399: 
        !           400:   /* Report error for undefined command name.  */
        !           401: 
        !           402:   if (nfound != 1)
        !           403:     {
        !           404:       if (nfound > 1 && allow_unknown >= 0)
        !           405:        {
        !           406:          *p = 0;
        !           407:          ambbuf[0] = 0;
        !           408:          for (c = list; c; c = c->next)
        !           409:            if (!strncmp (*line, c->name, p - *line))
        !           410:              {
        !           411:                if (strlen (ambbuf) + strlen (c->name) + 6 < sizeof ambbuf)
        !           412:                  {
        !           413:                    if (strlen (ambbuf))
        !           414:                      strcat (ambbuf, ", ");
        !           415:                    strcat (ambbuf, c->name);
        !           416:                  }
        !           417:                else
        !           418:                  {
        !           419:                    strcat (ambbuf, "..");
        !           420:                    break;
        !           421:                  }
        !           422:              }
        !           423:          error ("Ambiguous %scommand \"%s\": %s.", cmdtype, *line, ambbuf);
        !           424:        }
        !           425:       else if (!allow_unknown)
        !           426:        {
        !           427:          *p = 0;
        !           428:          error ("Undefined %scommand: \"%s\".", cmdtype, *line);
        !           429:        }
        !           430:       return 0;
        !           431:     }
        !           432: 
        !           433:   /* Skip whitespace before the argument.  */
        !           434: 
        !           435:   while (*p == ' ' || *p == '\t') p++;
        !           436:   *line = p;
        !           437: 
        !           438:   if (found->prefixlist && *p)
        !           439:     {
        !           440:       c = lookup_cmd (line, *found->prefixlist, found->prefixname,
        !           441:                      found->allow_unknown);
        !           442:       if (c)
        !           443:        return c;
        !           444:     }
        !           445: 
        !           446:   return found;
        !           447: }
        !           448: 
        !           449: /* Make a copy of the string at PTR with SIZE characters
        !           450:    (and add a null character at the end in the copy).
        !           451:    Uses malloc to get the space.  Returns the address of the copy.  */
        !           452: 
        !           453: static char *
        !           454: savestring (ptr, size)
        !           455:      char *ptr;
        !           456:      int size;
        !           457: {
        !           458:   register char *p = (char *) xmalloc (size + 1);
        !           459:   bcopy (ptr, p, size);
        !           460:   p[size] = 0;
        !           461:   return p;
        !           462: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.