quotearg.c 2.8 KB

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