TPCCLIB
Loading...
Searching...
No Matches
stringext.c
Go to the documentation of this file.
1
4/*****************************************************************************/
5#include "tpcclibConfig.h"
6/*****************************************************************************/
7#include "tpcextensions.h"
8/*****************************************************************************/
9#include <stdio.h>
10#include <stdlib.h>
11#include <math.h>
12#include <time.h>
13#include <string.h>
14#include <strings.h>
15#include <ctype.h>
16/*****************************************************************************/
17
18/*****************************************************************************/
27 const char *s1,
29 const char *s2
30) {
31 int i=0, n=0;
32 char *cptr;
33 if(s1==NULL || s2==NULL || strnlen(s1, 1)==0 || strnlen(s2, 1)==0) return(0);
34
35 cptr=(char*)s1;
36 do {
37 // pass delimiter characters
38 i=strspn(cptr, s2); cptr+=i;
39 // pass characters between delimiters
40 i=strcspn(cptr, s2); cptr+=i; if(i>0) n++;
41 } while(i>0);
42 return(n);
43}
44/*****************************************************************************/
45
46/*****************************************************************************/
55 const char *s1,
57 const char *s2,
59 int i,
61 char *s3,
63 int count
64) {
65 int j=0, n=0;
66 char *cptr;
67 if(s3!=NULL && count>0) s3[0]=(char)0;
68 if(s1==NULL || s2==NULL || strlen(s1)==0 || strlen(s2)==0) return(0);
69 if(i<1 || s3==NULL || count<2) return(0);
70
71 cptr=(char*)s1;
72 do {
73 // pass delimiter characters
74 j=strspn(cptr, s2); cptr+=j;
75 // pass characters between delimiters
76 j=strcspn(cptr, s2); if(j>0) n++;
77 // if this is the required token nr, then stop here
78 if(n==i) {
79 if(j>count-1) j=count-1;
80 strlcpy(s3, cptr, j+1); //strncpy(s3, cptr, j); s3[j]=(char)0;
81 break;
82 }
83 cptr+=j;
84 } while(j>0);
85 if(n>i) {s3[0]=(char)0; return(0);}
86 return(j);
87}
88/*****************************************************************************/
89
90/*****************************************************************************/
100 const char *s1,
102 const char *s2
103) {
104 unsigned int n=0, i, j;
105 if(s1==NULL || s2==NULL || strlen(s1)==0 || strlen(s2)==0) return (int)n;
106 for(i=0; i<strlen(s1); i++)
107 for(j=0; j<strlen(s2); j++)
108 if(s1[i]==s2[j]) n++;
109 return (int)n;
110}
111/*****************************************************************************/
112
113/*****************************************************************************/
120 const char *s
121) {
122 unsigned int n=0, i;
123 if(s==NULL || strlen(s)==0) return (int)n;
124 for(i=0; i<strlen(s); i++) if(isupper(s[i])) n++;
125 return (int)n;
126}
127/*****************************************************************************/
128
129/*****************************************************************************/
136 char *s,
138 char c1,
140 char c2
141) {
142 char *cptr;
143 if(s==NULL || strlen(s)==0) return;
144 while((cptr=strchr(s, c1))!=NULL) *cptr=c2;
145 return;
146}
147/*****************************************************************************/
148
149/*****************************************************************************/
150#ifndef HAVE_STRCASESTR
157 const char *haystack,
159 const char *needle
160) {
161 if(!*haystack || !*needle) return(0);
162
163 const char *s=haystack, *p=needle;
164 do {
165 if(!*p) return(char*)haystack;
166 if((*p==*s) || (tolower(*p)==tolower(*s))) {
167 p++; s++;
168 } else {
169 p=needle; if(!*s) return(NULL);
170 s=++haystack;
171 }
172 } while(1);
173 return *p ? NULL : (char*)haystack;
174}
175#endif // HAVE_STRCASESTR
176/*****************************************************************************/
177
178/*****************************************************************************/
179#ifndef HAVE_STRDUP
185char *strdup(
187 const char *s
188) {
189 size_t length=strlen(s)+1;
190 void *r;
191 r=calloc(length, sizeof(char)); if(r==NULL) return NULL;
192 return (char*)memcpy(r, s, length);
193}
194#endif // HAVE_STRDUP
195/*****************************************************************************/
196
197/*****************************************************************************/
198#ifndef HAVE_STRNDUP
206 const char *s,
208 size_t n
209) {
210 size_t length=strnlen(s, n);
211 void *r; r=calloc(length+1, sizeof(char)); if(r==NULL) return NULL;
212 return (char*)memcpy(r, s, length);
213}
214#endif // HAVE_STRNDUP
215/*****************************************************************************/
216
217/*****************************************************************************/
226 const char *haystack,
228 const char *needle
229) {
230 if(haystack==NULL) return((char*)NULL);
231 if(needle==NULL) return((char*)haystack);
232
233 size_t i, test_len;
234 int single_quotation=0;
235 int double_quotation=0;
236 char *cptr;
237
238 test_len=strlen(needle); if(test_len<1) return((char*)haystack);
239 for(i=0, cptr=(char*)haystack; i<strlen(haystack); i++, cptr++) {
240 if(*cptr=='\'') {
241 if(single_quotation==0 && strchr(cptr+1, '\'')!=NULL) single_quotation=1;
242 else single_quotation=0;
243 continue;
244 }
245 if(*cptr=='\"') {
246 if(double_quotation==0 && strchr(cptr+1, '\"')!=NULL) double_quotation=1;
247 else double_quotation=0;
248 continue;
249 }
250 if(single_quotation==1 || double_quotation==1) continue;
251 if(strncmp(cptr, needle, test_len)==0) return(cptr);
252 }
253 return((char*)NULL);
254}
255/*****************************************************************************/
256
257/*****************************************************************************/
267 char *s1,
269 const char *s2,
271 int maxlen
272) {
273 if(s1==NULL) return(0);
274 s1[0]=(char)0; if(maxlen<1) return(0);
275 if(maxlen<2) {strcpy(s1, ""); return(0);}
276 if(s2==NULL || strlen(s2)<1) return(0);
277
278 char *cptr;
279 int i;
280
281 cptr=(char*)s2; cptr+=strspn(s2, "\t\n\r ");
282 strlcpy(s1, cptr, maxlen); i=strlen(s1); if(i<1) return(0);
283 cptr=s1+(i-1);
284 while(i>0) {
285 if(*cptr!='\t' && *cptr!='\n' && *cptr!='\r' && *cptr!=' ') break;
286 i--; s1[i]=(char)0; cptr--;
287 }
288 return(i);
289}
290/*****************************************************************************/
291
292/*****************************************************************************/
301 char *s
302) {
303 if(s==NULL) return 0;
304 int len=strlen(s); if(len<0) return 0;
305 char *s2; s2=strdup(s); if(s2==NULL) return(1);
306 int n=strncpyCleanSpaces(s2, s, len+1);
307 if(n<1) strcpy(s, ""); else strcpy(s, s2);
308 free(s2);
309 return 0;
310}
311/*****************************************************************************/
312
313/*****************************************************************************/
323 char *s1,
325 const char *s2,
327 int maxlen
328) {
329 if(s1==NULL) return(0);
330 s1[0]=(char)0; if(maxlen<1) return(0);
331 if(maxlen<2) {strcpy(s1, ""); return(0);}
332 if(s2==NULL || strlen(s2)<1) return(0);
333
334 char *tmp;
335 int i, sqn, dqn, m;
336
337 /* Allocate temp string */
338 tmp=calloc(strlen(s2)+1, sizeof(char));
339
340 /* Trim space characters */
341 i=strncpyCleanSpaces(tmp, s2, strlen(s2)+1);
342 if(i<1) {strcpy(s1, ""); free(tmp); return(0);}
343
344 /* Loop as long as there is something to trim */
345 i=1;
346 while(i) {
347 m=0; // nothing modified so far
348 /* Count quotes */
349 sqn=strChrCount(tmp, "\'");
350 dqn=strChrCount(tmp, "\"");
351 if(sqn==0 && dqn==0) {i=0; break;}
352 /* Trim matching quotation marks */
353 if(dqn>=2 && tmp[0]=='\"' && tmp[strlen(tmp)-1]=='\"') {
354 tmp[0]=' '; tmp[strlen(tmp)-1]=(char)0; dqn-=2; m+=2;
355 }
356 if(sqn>=2 && tmp[0]=='\'' && tmp[strlen(tmp)-1]=='\'') {
357 tmp[0]=' '; tmp[strlen(tmp)-1]=(char)0; sqn-=2; m+=2;
358 }
359 /* Trim orphan quotation marks */
360 if(sqn%2) {
361 if(tmp[0]=='\'') {tmp[0]=' '; sqn--; m++;}
362 else if(tmp[strlen(tmp)-1]=='\'') {tmp[strlen(tmp)-1]=(char)0; sqn--; m++;}
363 }
364 if(dqn%2) {
365 if(tmp[0]=='\"') {tmp[0]=' '; dqn--; m++;}
366 else if(tmp[strlen(tmp)-1]=='\"') {tmp[strlen(tmp)-1]=(char)0; dqn--; m++;}
367 }
368 /* If nothing was modified, then do not continue */
369 if(m==0) {i=0; break;}
370 /* Trim spaces, quit if error encountered */
371 if(strCleanSpaces(tmp)) i=0;
372 }
373
374 strlcpy(s1, tmp, maxlen);
375 free(tmp);
376 return(strlen(s1));
377}
378/*****************************************************************************/
379
380/*****************************************************************************/
390 char *s
391) {
392 if(s==NULL) return 0;
393 int len=strlen(s); if(len<0) return 0;
394 char *s2; s2=calloc(len+1, sizeof(char)); if(s2==NULL) return(1);
395 int n=strncpyClean(s2, s, len+1);
396 if(n<1) strcpy(s, ""); else strcpy(s, s2);
397 free(s2);
398 return 0;
399}
400/*****************************************************************************/
401
402/*****************************************************************************/
414 const char *s1,
416 const char *s2,
418 int *next
419) {
420 if(next!=NULL) *next=0;
421 if(s1==NULL) return NULL;
422
423 char *s3=NULL, *cptr;
424 size_t j;
425
426 /* If no delimiters, then return copy of s1 */
427 if(s2==NULL || strlen(s2)<1) {
428 s3=strdup(s1); if(next!=NULL) *next=strlen(s1);
429 return s3;
430 }
431 /* Pass initial delimiter characters */
432 cptr=(char*)s1; j=strspn(cptr, s2); cptr+=j; if(next!=NULL) *next=j;
433 /* calculate characters between delimiters */
434 j=strcspn(cptr, s2); if(j==0) {return NULL;}
435 if(next!=NULL) *next+=j;
436 /* Allocate space for token */
437 s3=calloc(j+1, sizeof(char)); if(s3==NULL) return NULL;
438 strlcpy(s3, cptr, j+1);
439 return s3;
440}
441/*****************************************************************************/
442
443/*****************************************************************************/
454 char *s
455) {
456 if(s==NULL) return 0;
457 int len=strlen(s); if(len<2) return 0;
458 if(s[0]=='(' && s[len-1]==')') return 1;
459 if(s[0]=='{' && s[len-1]=='}') return 1;
460 if(s[0]=='[' && s[len-1]==']') return 1;
461 return 0;
462}
463/*****************************************************************************/
464
465/*****************************************************************************/
477 char *s
478) {
479 if(s==NULL || strInPars(s)==0) return;
480 int len=strlen(s);
481 s[--len]=(char)0;
482 for(int i=1; i<=len; i++) s[i-1]=s[i];
483 return;
484}
485/*****************************************************************************/
486
487/*****************************************************************************/
496 char *str1,
498 const int n,
502 size_t count
503) {
504 char tmp[128]; sprintf(tmp, "%d", n);
505 return strncat(str1, tmp, count);
506}
507/*****************************************************************************/
508
509/*****************************************************************************/
518 char *str1,
520 const double d,
524 size_t count
525) {
526 char tmp[128]; sprintf(tmp, "%g", d);
527 return strncat(str1, tmp, count);
528}
529/*****************************************************************************/
530
531/*****************************************************************************/
540 char *str1,
542 const int n,
544 const int maxn,
548 size_t count
549) {
550 if(n<0) strncat(str1, "-", count);
551 char tmp[128]; sprintf(tmp, "%d", abs(maxn));
552 int len=strlen(tmp);
553 sprintf(tmp, "%0*d", len, abs(n));
554 return strncat(str1, tmp, count);
555}
556/*****************************************************************************/
557
558/*****************************************************************************/
559#ifndef HAVE_STRNLEN
565size_t strnlen(
567 const char *s,
570 size_t n
571) {
572 char *ps=(char*)s;
573 size_t i=0;
574 while(i<n && *ps!='\0') {i++; ps++;}
575 return(i);
576}
577#endif // HAVE_STRNLEN
578/*****************************************************************************/
579
580/*****************************************************************************/
581#ifndef HAVE_STRLCAT
590size_t strlcat(
592 char *dst,
594 const char *src,
598 size_t dstsize
599) {
600 char *d;
601 const char *s=src;
602 size_t dlen, n;
603
604 /* Find the current length of dst */
605 dlen=strnlen(dst, dstsize);
606 if(s==NULL) return(dlen);
607 n=dstsize-dlen;
608 if(n==0) return(dlen+strlen(s));
609 d=dst+dlen;
610 while(*s!='\0') {
611 if(n!=1) {*d=*s; d++; n--;}
612 s++;
613 }
614 *d='\0';
615 return(dlen+(s-src));
616}
617#endif // HAVE_STRLCAT
618/*****************************************************************************/
619
620/*****************************************************************************/
621#ifndef HAVE_STRLCPY
630size_t strlcpy(
632 char *dst,
634 const char *src,
638 size_t dstsize
639) {
640 if(dstsize>0) dst[0]='\0';
641 if(strlen(src)==0) return(0);
642
643 char *d=dst;
644 const char *s=src;
645 size_t n;
646
647 /* Copy as many chars as allowed */
648 n=dstsize;
649 if(n!=0) while(--n!=0) {*d=*s; if(*d=='\0') {d++; s++; break;} d++; s++;}
650 if(n==0) { // not enough space, add NUL, and check how much space were needed
651 if(dstsize!=0) *d='\0';
652 while(*s++) {}
653 }
654 return(s-src-1);
655}
656#endif // HAVE_STRLCPY
657/*****************************************************************************/
658
659/*****************************************************************************/
671 char *s
672) {
673 if(s==NULL) return(1);
674 int len=strlen(s); if(len<1) return(1);
675 for(int i=0; i<len; i++) if(!isspace(s[i])) return(0);
676 return 1;
677}
678/*****************************************************************************/
679
680/*****************************************************************************/
688 char *s1,
690 const char *s2
691) {
692 if(s1==NULL || s2==NULL) return(s1); //printf("strdelstr('%s', '%s')\n", s1, s2);
693 int n=strlen(s2); if(n<1) return(s1);
694 char *cptr, *rptr;
695 cptr=strcasestr(s1, s2);
696 if(cptr==NULL || *cptr==(char)0) return(s1);
697 rptr=cptr;
698 while(*cptr) {*cptr=cptr[n]; cptr++;}
699 return(rptr);
700}
701/*****************************************************************************/
702
703/*****************************************************************************/
710 char *s,
712 const size_t t
713) {
714 if(s==NULL || t==0) return(s);
715 size_t len=strlen(s); if(len<1) return(s);
716 if(t>=len) {s[0]=(char)0; return(s);}
717 memmove(s, s+t, 1+len-t);
718 return(s);
719}
720/*****************************************************************************/
721
722/*****************************************************************************/
731 const char *s
732) {
733 if(s==NULL) return(NULL);
734 /* Count the characters needing encoding */
735 int n=0;
736 for(size_t i=0; i<strlen(s); i++) {
737 if(s[i]=='&') {n++; continue;}
738 if(s[i]=='\'') {n++; continue;}
739 if(s[i]=='\"') {n++; continue;}
740 if(s[i]=='<') {n++; continue;}
741 if(s[i]=='>') {n++; continue;}
742 }
743 if(n==0) return(NULL);
744 /* Allocate memory for new string (one char to max 6 chars) */
745 n*=5; n+=strlen(s)+1;
746 char *ns=(char*)malloc(n*sizeof(char));
747 if(ns==NULL) return(NULL);
748 /* Process the string */
749 for(int i=0; i<n; i++) ns[i]=(char)0;
750 for(size_t i=0; i<strlen(s); i++) {
751 if(s[i]=='&') {strcat(ns, "&amp;"); continue;}
752 if(s[i]=='\'') {strcat(ns, "&apos;"); continue;}
753 if(s[i]=='\"') {strcat(ns, "&quot;"); continue;}
754 if(s[i]=='<') {strcat(ns, "&lt;"); continue;}
755 if(s[i]=='>') {strcat(ns, "&gt;"); continue;}
756 ns[strlen(ns)]=s[i];
757 }
758 return(ns);
759}
760/*****************************************************************************/
761
762/*****************************************************************************/
769 char *s
770) {
771 if(s==NULL || *s=='\0') return;
772 strReplaceChar(s, '&', '-');
773 strReplaceChar(s, '\'', '-');
774 strReplaceChar(s, '\"', '-');
775 strReplaceChar(s, '<', '-');
776 strReplaceChar(s, '>', '-');
777 return;
778}
779/*****************************************************************************/
780
781/*****************************************************************************/
int strTokenNr(const char *s1, const char *s2)
Definition stringext.c:25
void strReplaceChar(char *s, char c1, char c2)
Definition stringext.c:134
int strInPars(char *s)
Definition stringext.c:452
void strCleanForXML(char *s)
Definition stringext.c:767
char * strstrNoQuotation(const char *haystack, const char *needle)
Definition stringext.c:224
char * strdup(const char *s)
Definition stringext.c:185
char * strncatIntZ(char *str1, const int n, const int maxn, size_t count)
Definition stringext.c:538
int strCleanSpaces(char *s)
Definition stringext.c:299
char * strncatDouble(char *str1, const double d, size_t count)
Definition stringext.c:516
void strCleanPars(char *s)
Definition stringext.c:475
char * strEncodeForXML(const char *s)
Definition stringext.c:729
char * strTrimLeft(char *s, const size_t t)
Definition stringext.c:708
size_t strnlen(const char *s, size_t n)
Definition stringext.c:565
int strncpyCleanSpaces(char *s1, const char *s2, int maxlen)
Definition stringext.c:264
char * strncatInt(char *str1, const int n, size_t count)
Definition stringext.c:494
int strTokenNCpy(const char *s1, const char *s2, int i, char *s3, int count)
Definition stringext.c:53
size_t strlcpy(char *dst, const char *src, size_t dstsize)
Definition stringext.c:630
int strncpyClean(char *s1, const char *s2, int maxlen)
Definition stringext.c:320
int strIsSpaceOnly(char *s)
Definition stringext.c:669
int strChrCount(const char *s1, const char *s2)
Definition stringext.c:98
char * strTokenDup(const char *s1, const char *s2, int *next)
Definition stringext.c:412
char * strdelstr(char *s1, const char *s2)
Definition stringext.c:686
int strClean(char *s)
Definition stringext.c:388
int strUppercaseCount(const char *s)
Definition stringext.c:118
char * strcasestr(const char *haystack, const char *needle)
Definition stringext.c:155
size_t strlcat(char *dst, const char *src, size_t dstsize)
Definition stringext.c:590
char * strndup(const char *s, size_t n)
Definition stringext.c:204
Header file for library libtpcextensions.