1 
2 #include "pl-incl.h"
3 #include "pl-ctype.h"
4 
5 #ifndef HAVE_STRICMP
6 int
stricmp(const char * s1,const char * s2)7 stricmp(const char *s1, const char *s2)
8 { while(*s1 && makeLower(*s1) == makeLower(*s2))
9     s1++, s2++;
10 
11   return makeLower(*s1) - makeLower(*s2);
12 }
13 #endif
14 
15 bool
stripostfix(char * s,char * e)16 stripostfix(char *s, char *e)
17 { int ls = strlen(s);
18   int le = strlen(e);
19 
20   if ( ls >= le )
21     return stricmp(&s[ls-le], e) == 0;
22 
23   return FALSE;
24 }
25 
26 #if !defined(HAVE_MBSCOLL) || !defined(HAVE_MBCASESCOLL)
27 static void
wstolower(wchar_t * w,size_t len)28 wstolower(wchar_t *w, size_t len)
29 { wchar_t *e = &w[len];
30 
31   for( ; w<e; w++ )
32     *w = towlower(*w);
33 }
34 
35 static int
int_mbscoll(const char * s1,const char * s2,int icase)36 int_mbscoll(const char *s1, const char *s2, int icase)
37 { size_t l1 = strlen(s1);
38   size_t l2 = strlen(s2);
39   wchar_t *w1;
40   wchar_t *w2;
41   int ml1, ml2;
42   mbstate_t mbs;
43   int rc;
44 
45   if ( l1 < 1024 && (w1 = alloca(sizeof(wchar_t)*(l1+1))) )
46   { ml1 = FALSE;
47   } else
48   { w1 = PL_malloc(sizeof(wchar_t)*(l1+1));
49     ml1 = TRUE;
50   }
51   if ( l2 < 1024 && (w2 = alloca(sizeof(wchar_t)*(l2+1))) )
52   { ml2 = FALSE;
53   } else
54   { w2 = PL_malloc(sizeof(wchar_t)*(l2+1));
55     ml2 = TRUE;
56   }
57 
58   memset(&mbs, 0, sizeof(mbs));
59   if ( mbsrtowcs(w1, &s1, l1+1, &mbs) == (size_t)-1 )
60   { rc = -2;
61     goto out;
62   }
63   if ( mbsrtowcs(w2, &s2, l2+1, &mbs) == (size_t)-1 )
64   { rc = 2;
65     goto out;
66   }
67   if ( icase )
68   { wstolower(w1, l1);
69     wstolower(w2, l2);
70   }
71 
72   rc = wcscoll(w1, w2);
73 
74 out:
75   if ( ml1 ) PL_free(w1);
76   if ( ml2 ) PL_free(w2);
77 
78   return rc;
79 }
80 #endif
81 
82 
83 #ifndef HAVE_MBSCOLL
84 int
mbscoll(const char * s1,const char * s2)85 mbscoll(const char *s1, const char *s2)
86 { return int_mbscoll(s1, s2, FALSE);
87 }
88 #endif
89 
90 
91 #ifndef HAVE_MBSCASECOLL
92 int
mbscasecoll(const char * s1,const char * s2)93 mbscasecoll(const char *s1, const char *s2)
94 { return int_mbscoll(s1, s2, TRUE);
95 }
96 #endif
97