]> pd.if.org Git - zpackage/blob - src/quote.c
rework zpm-add
[zpackage] / src / quote.c
1 #define _POSIX_C_SOURCE 2
2
3 #include <stdlib.h>
4 #include <stdio.h>
5 #include <string.h>
6 #include <unistd.h>
7
8 /* for quoting against the shell replace ' with '\'' and surround with
9  * single quotes
10  */
11
12 char *quote(char *s, int chi, char *repl, int addquotes) {
13         size_t size = 0, rsize = 0;
14         char *d, *q, *r;
15         char ch = chi;
16
17         if (!s) return NULL;
18         if (!repl) return NULL;
19
20         rsize = strlen(repl);
21
22         for (d = s; *d; d++) {
23                 if (*d == ch) {
24                         size += rsize-1;
25                 }
26                 size++;
27         }
28
29         if (addquotes) {
30                 size += 2;
31         }
32
33         d = q = malloc(size+1);
34
35         if (q) {
36                 if (addquotes) {
37                         *d++ = ch;
38                 }
39
40                 while (*s) {
41                         if (*s == ch) {
42                                 r = repl;
43                                 while (*r) {
44                                         *d++ = *r++;
45                                 }
46                                 s++;
47                         } else {
48                                 *d++ = *s++;
49                         }
50                         *d = 0;
51                 }
52
53                 if (addquotes) {
54                         *d++ = ch;
55                 }
56                 *d = 0;
57         }
58
59         return q;
60 }
61
62 int main(int ac, char **av) {
63         char *quoted;
64         int i;
65         int ch = '\'';
66         int opt, shellmode = 0, addquotes = 0, ident = 0;
67         char *repl = "''";
68         int count = 0;
69         char *separator = "\n";
70
71         while ((opt = getopt(ac, av, "sqid:")) != -1) {
72                 switch (opt) {
73                         case 's': shellmode = 1; break;
74                         case 'q': addquotes = 1; break;
75                         case 'i': ident = 1; break;
76                         case 'd': separator = optarg; break;
77                         default:
78                                   exit(EXIT_FAILURE);
79                                   break;
80                 }
81         }
82         int argn = optind;
83
84         if (shellmode) {
85                 repl = "'\\''";
86         } else if (ident) {
87                 ch = '"';
88                 repl = "\"\"";
89         }
90
91         count = 0;
92         for (i=argn;i<ac;i++) {
93                 quoted = quote(av[i], ch, repl, addquotes);
94                 printf("%s%s", count > 0 ? separator : "", quoted);
95                 free(quoted);
96                 count++;
97         }
98         if (count > 0) {
99                 printf("\n");
100         }
101         return 0;
102 }