xref: /freebsd/contrib/tcsh/tc.str.c (revision 6990ffd8a95caaba6858ad44ff1b3157d1efba8f)
1 /* $Header: /src/pub/tcsh/tc.str.c,v 3.9 1996/04/26 19:21:42 christos Exp $ */
2 /*
3  * tc.str.c: Short string package
4  * 	     This has been a lesson of how to write buggy code!
5  */
6 /*-
7  * Copyright (c) 1980, 1991 The Regents of the University of California.
8  * All rights reserved.
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in the
17  *    documentation and/or other materials provided with the distribution.
18  * 3. All advertising materials mentioning features or use of this software
19  *    must display the following acknowledgement:
20  *	This product includes software developed by the University of
21  *	California, Berkeley and its contributors.
22  * 4. Neither the name of the University nor the names of its contributors
23  *    may be used to endorse or promote products derived from this software
24  *    without specific prior written permission.
25  *
26  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
27  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
30  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36  * SUCH DAMAGE.
37  */
38 #include "sh.h"
39 
40 RCSID("$Id: tc.str.c,v 3.9 1996/04/26 19:21:42 christos Exp $")
41 
42 #define MALLOC_INCR	128
43 
44 #ifdef SHORT_STRINGS
45 Char  **
46 blk2short(src)
47     register char **src;
48 {
49     size_t     n;
50     register Char **sdst, **dst;
51 
52     /*
53      * Count
54      */
55     for (n = 0; src[n] != NULL; n++)
56 	continue;
57     sdst = dst = (Char **) xmalloc((size_t) ((n + 1) * sizeof(Char *)));
58 
59     for (; *src != NULL; src++)
60 	*dst++ = SAVE(*src);
61     *dst = NULL;
62     return (sdst);
63 }
64 
65 char  **
66 short2blk(src)
67     register Char **src;
68 {
69     size_t     n;
70     register char **sdst, **dst;
71 
72     /*
73      * Count
74      */
75     for (n = 0; src[n] != NULL; n++)
76 	continue;
77     sdst = dst = (char **) xmalloc((size_t) ((n + 1) * sizeof(char *)));
78 
79     for (; *src != NULL; src++)
80 	*dst++ = strsave(short2str(*src));
81     *dst = NULL;
82     return (sdst);
83 }
84 
85 Char   *
86 str2short(src)
87     register const char *src;
88 {
89     static Char *sdst;
90     static size_t dstsize = 0;
91     register Char *dst, *edst;
92 
93     if (src == NULL)
94 	return (NULL);
95 
96     if (sdst == (NULL)) {
97 	dstsize = MALLOC_INCR;
98 	sdst = (Char *) xmalloc((size_t) (dstsize * sizeof(Char)));
99     }
100 
101     dst = sdst;
102     edst = &dst[dstsize];
103     while ((unsigned char) *src) {
104 	*dst++ = (Char) ((unsigned char) *src++);
105 	if (dst == edst) {
106 	    dstsize += MALLOC_INCR;
107 	    sdst = (Char *) xrealloc((ptr_t) sdst,
108 				     (size_t) (dstsize * sizeof(Char)));
109 	    edst = &sdst[dstsize];
110 	    dst = &edst[-MALLOC_INCR];
111 	}
112     }
113     *dst = 0;
114     return (sdst);
115 }
116 
117 char   *
118 short2str(src)
119     register const Char *src;
120 {
121     static char *sdst = NULL;
122     static size_t dstsize = 0;
123     register char *dst, *edst;
124 
125     if (src == NULL)
126 	return (NULL);
127 
128     if (sdst == NULL) {
129 	dstsize = MALLOC_INCR;
130 	sdst = (char *) xmalloc((size_t) (dstsize * sizeof(char)));
131     }
132     dst = sdst;
133     edst = &dst[dstsize];
134     while (*src) {
135 	*dst++ = (char) *src++;
136 	if (dst == edst) {
137 	    dstsize += MALLOC_INCR;
138 	    sdst = (char *) xrealloc((ptr_t) sdst,
139 				     (size_t) (dstsize * sizeof(char)));
140 	    edst = &sdst[dstsize];
141 	    dst = &edst[-MALLOC_INCR];
142 	}
143     }
144     *dst = 0;
145     return (sdst);
146 }
147 
148 Char   *
149 s_strcpy(dst, src)
150     register Char *dst;
151     register const Char *src;
152 {
153     register Char *sdst;
154 
155     sdst = dst;
156     while ((*dst++ = *src++) != '\0')
157 	continue;
158     return (sdst);
159 }
160 
161 Char   *
162 s_strncpy(dst, src, n)
163     register Char *dst;
164     register const Char *src;
165     register size_t n;
166 {
167     register Char *sdst;
168 
169     if (n == 0)
170 	return(dst);
171 
172     sdst = dst;
173     do
174 	if ((*dst++ = *src++) == '\0') {
175 	    while (--n != 0)
176 		*dst++ = '\0';
177 	    return(sdst);
178 	}
179     while (--n != 0);
180     return (sdst);
181 }
182 
183 Char   *
184 s_strcat(dst, src)
185     register Char *dst;
186     register const Char *src;
187 {
188     register short *sdst;
189 
190     sdst = dst;
191     while (*dst++)
192 	continue;
193     --dst;
194     while ((*dst++ = *src++) != '\0')
195 	continue;
196     return (sdst);
197 }
198 
199 #ifdef NOTUSED
200 Char   *
201 s_strncat(dst, src, n)
202     register Char *dst;
203     register const Char *src;
204     register size_t n;
205 {
206     register Char *sdst;
207 
208     if (n == 0)
209 	return (dst);
210 
211     sdst = dst;
212 
213     while (*dst++)
214 	continue;
215     --dst;
216 
217     do
218 	if ((*dst++ = *src++) == '\0')
219 	    return(sdst);
220     while (--n != 0)
221 	continue;
222 
223     *dst = '\0';
224     return (sdst);
225 }
226 
227 #endif
228 
229 Char   *
230 s_strchr(str, ch)
231     register const Char *str;
232     int ch;
233 {
234     do
235 	if (*str == ch)
236 	    return ((Char *) str);
237     while (*str++);
238     return (NULL);
239 }
240 
241 Char   *
242 s_strrchr(str, ch)
243     register const Char *str;
244     int ch;
245 {
246     register const Char *rstr;
247 
248     rstr = NULL;
249     do
250 	if (*str == ch)
251 	    rstr = str;
252     while (*str++);
253     return ((Char *) rstr);
254 }
255 
256 size_t
257 s_strlen(str)
258     register const Char *str;
259 {
260     register size_t n;
261 
262     for (n = 0; *str++; n++)
263 	continue;
264     return (n);
265 }
266 
267 int
268 s_strcmp(str1, str2)
269     register const Char *str1, *str2;
270 {
271     for (; *str1 && *str1 == *str2; str1++, str2++)
272 	continue;
273     /*
274      * The following case analysis is necessary so that characters which look
275      * negative collate low against normal characters but high against the
276      * end-of-string NUL.
277      */
278     if (*str1 == '\0' && *str2 == '\0')
279 	return (0);
280     else if (*str1 == '\0')
281 	return (-1);
282     else if (*str2 == '\0')
283 	return (1);
284     else
285 	return (*str1 - *str2);
286 }
287 
288 int
289 s_strncmp(str1, str2, n)
290     register const Char *str1, *str2;
291     register size_t n;
292 {
293     if (n == 0)
294 	return (0);
295     do {
296 	if (*str1 != *str2) {
297 	    /*
298 	     * The following case analysis is necessary so that characters
299 	     * which look negative collate low against normal characters
300 	     * but high against the end-of-string NUL.
301 	     */
302 	    if (*str1 == '\0')
303 		return (-1);
304 	    else if (*str2 == '\0')
305 		return (1);
306 	    else
307 		return (*str1 - *str2);
308 	}
309         if (*str1 == '\0')
310 	    return(0);
311 	str1++, str2++;
312     } while (--n != 0);
313     return(0);
314 }
315 
316 Char   *
317 s_strsave(s)
318     register const Char *s;
319 {
320     Char   *n;
321     register Char *p;
322 
323     if (s == 0)
324 	s = STRNULL;
325     for (p = (Char *) s; *p++;)
326 	continue;
327     n = p = (Char *) xmalloc((size_t)
328 			     ((((const Char *) p) - s) * sizeof(Char)));
329     while ((*p++ = *s++) != '\0')
330 	continue;
331     return (n);
332 }
333 
334 Char   *
335 s_strspl(cp, dp)
336     const Char   *cp, *dp;
337 {
338     Char   *ep;
339     register Char *p, *q;
340 
341     if (!cp)
342 	cp = STRNULL;
343     if (!dp)
344 	dp = STRNULL;
345     for (p = (Char *) cp; *p++;)
346 	continue;
347     for (q = (Char *) dp; *q++;)
348 	continue;
349     ep = (Char *) xmalloc((size_t)
350 			  (((((const Char *) p) - cp) +
351 			    (((const Char *) q) - dp) - 1) * sizeof(Char)));
352     for (p = ep, q = (Char*) cp; (*p++ = *q++) != '\0';)
353 	continue;
354     for (p--, q = (Char *) dp; (*p++ = *q++) != '\0';)
355 	continue;
356     return (ep);
357 }
358 
359 Char   *
360 s_strend(cp)
361     register const Char *cp;
362 {
363     if (!cp)
364 	return ((Char *) cp);
365     while (*cp)
366 	cp++;
367     return ((Char *) cp);
368 }
369 
370 Char   *
371 s_strstr(s, t)
372     register const Char *s, *t;
373 {
374     do {
375 	register const Char *ss = s;
376 	register const Char *tt = t;
377 
378 	do
379 	    if (*tt == '\0')
380 		return ((Char *) s);
381 	while (*ss++ == *tt++);
382     } while (*s++ != '\0');
383     return (NULL);
384 }
385 
386 #endif				/* SHORT_STRINGS */
387 
388 char   *
389 short2qstr(src)
390     register const Char *src;
391 {
392     static char *sdst = NULL;
393     static size_t dstsize = 0;
394     register char *dst, *edst;
395 
396     if (src == NULL)
397 	return (NULL);
398 
399     if (sdst == NULL) {
400 	dstsize = MALLOC_INCR;
401 	sdst = (char *) xmalloc((size_t) (dstsize * sizeof(char)));
402     }
403     dst = sdst;
404     edst = &dst[dstsize];
405     while (*src) {
406 	if (*src & QUOTE) {
407 	    *dst++ = '\\';
408 	    if (dst == edst) {
409 		dstsize += MALLOC_INCR;
410 		sdst = (char *) xrealloc((ptr_t) sdst,
411 					 (size_t) (dstsize * sizeof(char)));
412 		edst = &sdst[dstsize];
413 		dst = &edst[-MALLOC_INCR];
414 	    }
415 	}
416 	*dst++ = (char) *src++;
417 	if (dst == edst) {
418 	    dstsize += MALLOC_INCR;
419 	    sdst = (char *) xrealloc((ptr_t) sdst,
420 				     (size_t) (dstsize * sizeof(char)));
421 	    edst = &sdst[dstsize];
422 	    dst = &edst[-MALLOC_INCR];
423 	}
424     }
425     *dst = 0;
426     return (sdst);
427 }
428