wmbiff: Remove #define _GNU_SOURCE; already defined in CFLAGS.
[dockapps.git] / wmbiff / wmbiff / charutil.c
blob0f513bac99cb7b9566be560876b068f93bf8fee8
1 /* $Id: charutil.c,v 1.19 2004/04/28 00:19:03 bluehal Exp $ */
2 #ifdef HAVE_CONFIG_H
3 #include <config.h>
4 #endif
6 #include <stdlib.h>
7 #include <stdio.h>
8 #include <string.h>
9 #include <ctype.h>
10 #include <sys/types.h>
11 #include <regex.h>
12 #ifdef USE_DMALLOC
13 #include <dmalloc.h>
14 #endif
15 #include "charutil.h"
17 static __inline__ void LeftTrim(char *psValue)
19 char *psTmp = psValue;
21 while (*psTmp == ' ' || *psTmp == '\t')
22 psTmp++;
24 /* can't use strcpy here, as the strings must not
25 overlap, at least according to spec. */
26 if (psTmp > psValue) {
27 while (*psTmp != '\0') {
28 *(psValue++) = *(psTmp++);
30 *(psValue) = '\0';
34 static __inline__ void RightTrim(char *psValue)
36 long lLength = strlen(psValue) - 1;
38 while ((psValue[lLength] == ' ' || psValue[lLength] == '\t')
39 && *psValue) {
40 lLength--;
43 psValue[++lLength] = '\000';
46 void FullTrim(char *psValue)
48 RightTrim(psValue);
49 LeftTrim(psValue);
52 void Bin2Hex(unsigned char *src, int length, char *dst)
54 static char hex_tbl[] = "0123456789abcdef";
56 int i = 0;
57 char *ptr = dst;
59 if (src && ptr) {
60 for (i = 0; i < length; i++) {
61 *ptr++ = hex_tbl[*src >> 4];
62 *ptr++ = hex_tbl[*src++ & 0xf];
64 *ptr = 0;
69 #define PAD '='
70 char ALPHABET[65] =
71 "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/\000";
73 /* find char in in alphabet, return offset, -1 otherwise */
74 int find_char(char c)
76 char *a = ALPHABET;
78 while (*a)
79 if (*(a++) == c)
80 return a - ALPHABET - 1;
82 return -1;
85 void Encode_Base64(char *src, char *dst)
87 int g = 0;
88 int c = 0;
90 if (!src || !dst)
91 return;
93 while (*src) {
94 g = (g << 8) | *src++;
95 if (c == 2) {
96 *dst++ = ALPHABET[0x3f & (g >> 18)];
97 *dst++ = ALPHABET[0x3f & (g >> 12)];
98 *dst++ = ALPHABET[0x3f & (g >> 6)];
99 *dst++ = ALPHABET[0x3f & g];
101 c = (c + 1) % 3;
104 if (c) {
105 if (c == 1) {
106 *dst++ = ALPHABET[0x3f & (g >> 2)];
107 *dst++ = ALPHABET[0x3f & (g << 4)];
108 *dst++ = PAD;
109 *dst++ = PAD;
110 } else {
111 *dst++ = ALPHABET[0x3f & (g >> 10)];
112 *dst++ = ALPHABET[0x3f & (g >> 4)];
113 *dst++ = ALPHABET[0x3f & (g << 2)];
114 *dst++ = PAD;
117 *dst = 0;
121 void Decode_Base64(char *src, char *dst)
123 int g = 0;
124 int c = 0;
125 int n = 0;
127 if (!src || !dst)
128 return;
130 while (*src) {
131 n = find_char(*src++);
132 if (n < 0)
133 continue;
135 g <<= 6;
136 g |= n;
137 if (c == 3) {
138 *dst++ = g >> 16;
139 *dst++ = g >> 8;
140 *dst++ = g;
141 g = 0;
143 c = (c + 1) % 4;
145 if (c) {
146 if (c == 1) {
147 /* shouldn't happen, but do something anyway */
148 *dst++ = g << 2;
149 } else if (c == 2) {
150 *dst++ = g >> 4;
151 } else {
152 *dst++ = g >> 10;
153 *dst++ = g >> 2;
156 *dst = 0;
159 /* helper function for the configuration line parser */
160 void
161 copy_substring(char *destination,
162 int startidx, int endidx, const char *source)
164 if (startidx > -1) {
165 strncpy(destination, source + startidx, endidx - startidx);
166 destination[endidx - startidx] = '\0';
170 /* common to Pop3 and Imap4 authentication list grabber. */
171 void grab_authList(const char *source, char *destination)
173 int i;
174 /* regex isn't all that helpful for lists of things. */
175 /* but does leave the end of the matched region in regs.end[0] */
176 /* what remains is a list of legal authentication schemes. */
177 if (isalnum(source[0])) {
178 /* copy, while turning caps into lower case */
179 for (i = 0; i < 99 && source[i] != '\0'; i++) {
180 destination[i] = tolower(source[i]);
182 destination[i] = '\0';
183 } else {
184 destination[0] = '\0';
188 #ifdef USE_GNU_REGEX
189 int compile_and_match_regex(const char *regex, const char *str, /*@out@ */
190 struct re_registers *regs)
193 const char *errstr;
194 int matchedchars;
195 struct re_pattern_buffer rpbuf;
197 /* compile the regex pattern */
198 memset(&rpbuf, 0, sizeof(struct re_pattern_buffer));
199 /* posix egrep interprets intervals (eg. {1,32}) nicely */
200 re_syntax_options = RE_SYNTAX_POSIX_EGREP;
201 errstr = re_compile_pattern(regex, strlen(regex), &rpbuf);
202 if (errstr != NULL) {
203 fprintf(stderr, "error in compiling regular expression: %s\n",
204 errstr);
205 return -1;
208 /* match the regex */
209 regs->num_regs = REGS_UNALLOCATED;
210 matchedchars = re_match(&rpbuf, str, strlen(str), 0, regs);
211 /* this can fail (return -1 or 0) without being an error,
212 if we're trying to apply a regex just to see if it
213 matched. */
215 #ifdef undef
216 printf("--\n");
217 for (i = 1; i < 6; i++) {
218 printf("%d %d, (%.*s)\n", regs.start[i], regs.end[i],
219 (regs.end[i] - regs.start[i]),
220 (regs.start[i] >= 0) ? &str[regs.start[i]] : "");
222 #endif
224 regfree(&rpbuf); // added 3 jul 02, appeasing valgrind
225 return matchedchars;
227 #endif
229 /* like perl chomp(); useful for dealing with input from popen */
230 void chomp(char *s)
232 int l = strlen(s) - 1;
233 if (l >= 0 && s[l] == '\n')
234 s[l] = '\0';
237 char *strdup_ordie(const char *c)
239 char *ret = strdup(c);
240 if (ret == NULL) {
241 fprintf(stderr, "ran out of memory\n");
242 exit(EXIT_FAILURE);
244 return (ret);
247 void StripComment(char *buf)
249 char *p;
251 /* Strip comments at beginning of line, or after whitespace.
252 a kludgy way of avoiding problems with #'s in passwords. */
253 if (buf[0] == '#')
254 buf[0] = '\0';
255 for (p = (char *) buf + 1; *p && !(*p == '#' && isspace(*(p - 1)));
256 p++);
257 if (*p) {
258 *p = '\0';
263 /* vim:set ts=4: */
265 * Local Variables:
266 * tab-width: 4
267 * c-indent-level: 4
268 * c-basic-offset: 4
269 * End: