| quote.c - 9base - revived minimalist port of Plan 9 userland to Unix | |
| git clone git://git.suckless.org/9base | |
| Log | |
| Files | |
| Refs | |
| README | |
| LICENSE | |
| --- | |
| quote.c (2271B) | |
| --- | |
| 1 #include <u.h> | |
| 2 #include <libc.h> | |
| 3 | |
| 4 | |
| 5 /* in libfmt */ | |
| 6 extern int (*doquote)(int); | |
| 7 extern int __needsquotes(char*, int*); | |
| 8 extern int __runeneedsquotes(Rune*, int*); | |
| 9 | |
| 10 char* | |
| 11 unquotestrdup(char *s) | |
| 12 { | |
| 13 char *t, *ret; | |
| 14 int quoting; | |
| 15 | |
| 16 ret = s = strdup(s); /* return unquoted copy */ | |
| 17 if(ret == nil) | |
| 18 return ret; | |
| 19 quoting = 0; | |
| 20 t = s; /* s is output string, t is input string */ | |
| 21 while(*t!='\0' && (quoting || (*t!=' ' && *t!='\t'))){ | |
| 22 if(*t != '\''){ | |
| 23 *s++ = *t++; | |
| 24 continue; | |
| 25 } | |
| 26 /* *t is a quote */ | |
| 27 if(!quoting){ | |
| 28 quoting = 1; | |
| 29 t++; | |
| 30 continue; | |
| 31 } | |
| 32 /* quoting and we're on a quote */ | |
| 33 if(t[1] != '\''){ | |
| 34 /* end of quoted section; absorb closing quote */ | |
| 35 t++; | |
| 36 quoting = 0; | |
| 37 continue; | |
| 38 } | |
| 39 /* doubled quote; fold one quote into two */ | |
| 40 t++; | |
| 41 *s++ = *t++; | |
| 42 } | |
| 43 if(t != s) | |
| 44 memmove(s, t, strlen(t)+1); | |
| 45 return ret; | |
| 46 } | |
| 47 | |
| 48 Rune* | |
| 49 unquoterunestrdup(Rune *s) | |
| 50 { | |
| 51 Rune *t, *ret; | |
| 52 int quoting; | |
| 53 | |
| 54 ret = s = runestrdup(s); /* return unquoted copy */ | |
| 55 if(ret == nil) | |
| 56 return ret; | |
| 57 quoting = 0; | |
| 58 t = s; /* s is output string, t is input string */ | |
| 59 while(*t!='\0' && (quoting || (*t!=' ' && *t!='\t'))){ | |
| 60 if(*t != '\''){ | |
| 61 *s++ = *t++; | |
| 62 continue; | |
| 63 } | |
| 64 /* *t is a quote */ | |
| 65 if(!quoting){ | |
| 66 quoting = 1; | |
| 67 t++; | |
| 68 continue; | |
| 69 } | |
| 70 /* quoting and we're on a quote */ | |
| 71 if(t[1] != '\''){ | |
| 72 /* end of quoted section; absorb closing quote */ | |
| 73 t++; | |
| 74 quoting = 0; | |
| 75 continue; | |
| 76 } | |
| 77 /* doubled quote; fold one quote into two */ | |
| 78 t++; | |
| 79 *s++ = *t++; | |
| 80 } | |
| 81 if(t != s) | |
| 82 memmove(s, t, (runestrlen(t)+1)*sizeof(Rune)); | |
| 83 return ret; | |
| 84 } | |
| 85 | |
| 86 char* | |
| 87 quotestrdup(char *s) | |
| 88 { | |
| 89 char *t, *u, *ret; | |
| 90 int quotelen; | |
| 91 Rune r; | |
| 92 | |
| 93 if(__needsquotes(s, "elen) == 0) | |
| 94 return strdup(s); | |
| 95 | |
| 96 ret = malloc(quotelen+1); | |
| 97 if(ret == nil) | |
| 98 return nil; | |
| 99 u = ret; | |
| 100 *u++ = '\''; | |
| 101 for(t=s; *t; t++){ | |
| 102 r = *t; | |
| 103 if(r == '\'') | |
| 104 *u++ = r; /* double the quote */ | |
| 105 *u++ = r; | |
| 106 } | |
| 107 *u++ = '\''; | |
| 108 *u = '\0'; | |
| 109 return ret; | |
| 110 } | |
| 111 | |
| 112 Rune* | |
| 113 quoterunestrdup(Rune *s) | |
| 114 { | |
| 115 Rune *t, *u, *ret; | |
| 116 int quotelen; | |
| 117 Rune r; | |
| 118 | |
| 119 if(__runeneedsquotes(s, "elen) == 0) | |
| 120 return runestrdup(s); | |
| 121 | |
| 122 ret = malloc((quotelen+1)*sizeof(Rune)); | |
| 123 if(ret == nil) | |
| 124 return nil; | |
| 125 u = ret; | |
| 126 *u++ = '\''; | |
| 127 for(t=s; *t; t++){ | |
| 128 r = *t; | |
| 129 if(r == '\'') | |
| 130 *u++ = r; /* double the quote */ | |
| 131 *u++ = r; | |
| 132 } | |
| 133 *u++ = '\''; | |
| 134 *u = '\0'; | |
| 135 return ret; | |
| 136 } |