home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 22 gnu / 22-gnu.zip / rcs57pc3.zip / diff / quote.c < prev    next >
C/C++ Source or Header  |  1994-10-31  |  3KB  |  120 lines

  1. /* Shell command argument quoting.
  2.    Copyright (C) 1994 Free Software Foundation, Inc.
  3.  
  4. This file is part of GNU DIFF.
  5.  
  6. GNU DIFF is free software; you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation; either version 2, or (at your option)
  9. any later version.
  10.  
  11. GNU DIFF is distributed in the hope that it will be useful,
  12. but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. GNU General Public License for more details.
  15.  
  16. You should have received a copy of the GNU General Public License
  17. along with GNU DIFF; see the file COPYING.  If not, write to
  18. the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  19.  
  20. #include "system.h"
  21.  
  22. /* Place into QUOTED a quoted version of ARG suitable for `system'.
  23.    Return the length of the resulting string (which is not null-terminated).
  24.    If QUOTED is null, return the length without any side effects.  */
  25.  
  26. size_t
  27. system_quote_arg (quoted, arg)
  28.      char *quoted;
  29.      char const *arg;
  30. {
  31.   char const *a = arg;
  32.   size_t len = 0;
  33.  
  34.   /* Scan ARG, copying it to QUOTED if QUOTED is not null,
  35.      looking for shell metacharacters.  */
  36.  
  37.   for (;;)
  38.     {
  39.       char c = *a++;
  40.       switch (c)
  41.     {
  42.     case 0:
  43.       /* ARG has no shell metacharacters.  */
  44.       return len;
  45.  
  46.     case '=':
  47.       if (*arg == '-')
  48.         break;
  49.       /* Fall through.  */
  50.     case '\t': case '\n': case ' ':
  51.     case '!': case '"': case '#': case '$': case '%': case '&': case '\'':
  52.     case '(': case ')': case '*': case ';':
  53.     case '<': case '>': case '?': case '[': case '\\':
  54.     case '^': case '`': case '|': case '~':
  55.       {
  56.         /* ARG has a shell metacharacter.
  57.            Start over, quoting it this time.  */
  58.  
  59.         len = 0;
  60.         c = *arg++;
  61.  
  62.         /* If ARG is an option, quote just its argument.
  63.            This is not necessary, but it looks nicer.  */
  64.         if (c == '-'  &&  arg < a)
  65.           {
  66.         c = *arg++;
  67.  
  68.         if (quoted)
  69.           {
  70.             quoted[len] = '-';
  71.             quoted[len + 1] = c;
  72.           }
  73.         len += 2;
  74.  
  75.         if (c == '-')
  76.           while (arg < a)
  77.             {
  78.               c = *arg++;
  79.               if (quoted)
  80.             quoted[len] = c;
  81.               len++;
  82.               if (c == '=')
  83.             break;
  84.             }
  85.         c = *arg++;
  86.           }
  87.  
  88.         if (quoted)
  89.           quoted[len] = '\'';
  90.         len++;
  91.  
  92.         for (;  c;  c = *arg++)
  93.           {
  94.         if (c == '\'')
  95.           {
  96.             if (quoted)
  97.               {
  98.             quoted[len] = '\'';
  99.             quoted[len + 1] = '\\';
  100.             quoted[len + 2] = '\'';
  101.               }
  102.             len += 3;
  103.           }
  104.         if (quoted)
  105.           quoted[len] = c;
  106.         len++;
  107.           }
  108.  
  109.         if (quoted)
  110.           quoted[len] = '\'';
  111.         return len + 1;
  112.       }
  113.     }
  114.  
  115.       if (quoted)
  116.     quoted[len] = c;
  117.       len++;
  118.     }
  119. }
  120.