1 /* $Id: mstring.c,v 1.7 2016/12/02 17:57:21 tom Exp $ */
10 /* parameters about string length. HEAD is the starting size and
11 ** HEAD+TAIL should be a power of two */
18 static size_t buf_len
;
21 msprintf(struct mstring
*s
, const char *fmt
,...)
34 buf_ptr
= malloc(buf_len
= 4096);
45 len
= (size_t) vsnprintf(buf_ptr
, buf_len
, fmt
, args
);
47 if ((changed
= (len
> buf_len
)) != 0)
49 char *new_ptr
= realloc(buf_ptr
, (buf_len
* 3) / 2);
62 len
= (size_t) vsprintf(buf_ptr
, fmt
, args
);
68 if (len
> (size_t) (s
->end
- s
->ptr
))
71 size_t cp
= (size_t) (s
->ptr
- s
->base
);
72 size_t cl
= (size_t) (s
->end
- s
->base
);
74 while (len
> (nl
- cp
))
76 if ((new_base
= realloc(s
->base
, nl
)))
79 s
->ptr
= s
->base
+ cp
;
80 s
->end
= s
->base
+ nl
;
91 memcpy(s
->ptr
, buf_ptr
, len
);
97 mputchar(struct mstring
*s
, int ch
)
101 if (s
->ptr
== s
->end
)
103 size_t len
= (size_t) (s
->end
- s
->base
);
104 if ((s
->base
= realloc(s
->base
, len
+ len
+ TAIL
)))
106 s
->ptr
= s
->base
+ len
;
107 s
->end
= s
->base
+ len
+ len
+ TAIL
;
115 *s
->ptr
++ = (char)ch
;
122 struct mstring
*n
= TMALLOC(struct mstring
, 1);
126 if ((n
->base
= n
->ptr
= MALLOC(HEAD
)) != 0)
128 n
->end
= n
->base
+ HEAD
;
140 msdone(struct mstring
*s
)
152 #if defined(YYBTYACC)
153 /* compare two strings, ignoring whitespace, except between two letters or
154 ** digits (and treat all of these as equal) */
156 strnscmp(const char *a
, const char *b
)
160 while (isspace(UCH(*a
)))
162 while (isspace(UCH(*b
)))
164 while (*a
&& *a
== *b
)
166 if (isspace(UCH(*a
)))
168 if (isalnum(UCH(a
[-1])) && isalnum(UCH(*b
)))
171 else if (isspace(UCH(*b
)))
173 if (isalnum(UCH(b
[-1])) && isalnum(UCH(*a
)))
183 strnshash(const char *s
)
189 if (!isspace(UCH(*s
)))
190 h
= (h
<< 5) - h
+ (unsigned char)*s
;
201 #if defined(YYBTYACC)