1 /* $Id$ 2 * Provide extra set of functions to operate with strings. 3 * 4 * HUSKYLIB: common defines, types and functions for HUSKY 5 * 6 * This is part of The HUSKY Fidonet Software project: 7 * see http://husky.sourceforge.net for details 8 * 9 * 10 * HUSKYLIB is free software; you can redistribute it and/or 11 * modify it under the terms of the GNU Lesser General Public 12 * License as published by the Free Software Foundation; either 13 * version 2 of the License, or (at your option) any later version. 14 * 15 * HUSKYLIB is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 18 * General Public License for more details. 19 * 20 * You should have received a copy of the GNU Lesser General Public 21 * License along with this library; see file COPYING. If not, write to the 22 * Free Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 23 * 24 * See also http://www.gnu.org, license may be found here. 25 */ 26 27 #ifndef HUSKY_STREXT_H__ 28 #define HUSKY_STREXT_H__ 29 30 /* huskylib: compiler.h */ 31 #include "compiler.h" 32 33 /* huskylib headers */ 34 #include "huskyext.h" /* compiler see directory of this .h file */ 35 36 #ifdef __cplusplus 37 extern "C" { 38 #endif 39 40 /* Replace last char with '\0' if last char is strip-char 41 */ 42 HUSKYEXT char *_fast Strip_Trailing(char *str, char strip); 43 44 /* Add add-char to end of string (size of the str is not checked!!!) 45 */ 46 HUSKYEXT char *_fast Add_Trailing(char *str, char add); 47 48 /* Copy src to dst; return src 49 */ 50 HUSKYEXT char *_fast strocpy(char *dst, const char *src); 51 52 /* Return pointer to 1st char of specified word in string (by word number) 53 */ 54 HUSKYEXT char* _fast firstchar(const char *strng, const char *delim, int findword); 55 56 57 HUSKYEXT char *strrstr(const char *HAYSTACK, const char *NEEDLE); 58 59 /*DOC 60 Input: two constant null-terminated strings 61 Output: NULL or the point to a null-terminated string 62 FZ: finds the LAST occurence of NEEDLE in HAYSTACK 63 (same as strstr but last occurence 64 */ 65 66 HUSKYEXT char *fc_stristr(const char *str, const char *find); 67 /* 68 * Find the first occurrence of find in s ignoring case 69 */ 70 71 HUSKYEXT char *stripLeadingChars(char *str, const char *chr); 72 /*DOC 73 Input: str is a \0-terminated string 74 chr contains a list of characters. 75 Output: stripLeadingChars returns a pointer to a string 76 FZ: all leading characters which are in chr are deleted. 77 str is changed and returned. 78 */ 79 80 81 /*DOC 82 Input: str is a \0-terminated string 83 chr contains a list of characters. 84 Output: stripTrailingChars returns a pointer to a string 85 FZ: all trailing characters which are in chr are deleted. 86 str is changed and returned (not reallocated, simply shorted). 87 */ 88 HUSKYEXT char *stripTrailingChars(char *str, const char *chr); 89 90 91 #define stripRoundingChars(str,chrs) (stripTrailingChars(stripLeadingChars((str),(chrs)),(chrs))) 92 93 94 HUSKYEXT char *strUpper(char *str); 95 /*DOC 96 Input: str is a \0 terminated string 97 Output: str 98 FZ: strUpper converts the string from lower case to upper case. 99 */ 100 101 HUSKYEXT char *strLower(char *str); 102 /*DOC 103 Input: str is a \0 terminated string 104 Output: str 105 FZ: strLower converts the string from upper case to lower case. 106 */ 107 108 HUSKYEXT char *sstrdup(const char *src); 109 110 /* safe strdup for line part */ 111 #define sstrndup(src,len) strncpy(smalloc(len),src,len) 112 113 /* safe strlen: if src==NULL return 0 */ 114 #define sstrlen(src) ( src ? strlen(src) : 0 ) 115 116 /* safe strcpy: if src==NULL or dst==NULL don't copy and return NULL */ 117 #define sstrcpy(dst,src) ( (src)&&(dst) ? strcpy(dst,src) : NULL ) 118 119 /* safe strncpy: if src==NULL or dst==NULL don't copy and return NULL */ 120 #define sstrncpy(dst,src,len) ( (src)&&(dst) ? strncpy(dst,src,len) : NULL ) 121 122 /* Copyes not more than len chars from src into dst, but, unlike strncpy(), 123 * it appends '\0' even if src is longer than len. 124 * Return dst 125 * Prevent memory faults: 126 * - if dst is NULL doing nothing and return NULL 127 * - if src is NULL and dst not NULL store '\0' into dst[0] and return it. 128 */ 129 HUSKYEXT char *strnzcpy (char *dst, const char *src, size_t len); 130 131 /* Concantenates not more than len chars from src into dst, but, unlike 132 * strncat(), it appends '\0' even if src is longer than len. 133 * Return dst 134 * Prevent memory faults: 135 * - if dst is NULL doing nothing and return NULL 136 * - if src is NULL doing nothing and return dst. 137 */ 138 HUSKYEXT char *strnzcat (char *dst, const char *src, size_t len); 139 140 /* safe strstr: if str==NULL or find==NULL return NULL */ 141 #define sstrstr(str,find) ( (str)&&(find) ? strstr(str,find) : NULL ) 142 143 /* safe stristr: if str==NULL or find==NULL return NULL */ 144 #define sstristr(str,find) ( (str)&&(find) ? fc_stristr(str,find) : NULL ) 145 146 /* safe strcmp */ 147 HUSKYEXT int sstrcmp(const char *str1, const char *str2); 148 149 /* safe strncmp */ 150 HUSKYEXT int sstrncmp(const char *str1, const char *str2, size_t length); 151 152 /* safe stricmp (case-insencitive) */ 153 HUSKYEXT int sstricmp(const char *str1, const char *str2); 154 155 /* safety strnicmp (case-insencitive) */ 156 HUSKYEXT int sstrnicmp(const char *str1, const char *str2, size_t length); 157 158 /* safety string envelope (use this in functions calls) */ 159 #define sstr(ss) ( ss ? ss : "" ) 160 161 162 HUSKYEXT char *strseparate(register char **stringp, register const char *delim); 163 164 /* Extract contents from CVS/RCS keyvords (like $Revision$) 165 * Return malloc'ed string 166 */ 167 HUSKYEXT char *extract_CVS_keyword(char *str); 168 169 /* Convert char to integer with range checking 170 */ 171 HUSKYEXT int ctoi(const char *s); 172 173 /* Copy string from str to (*pmem), allocating memory as needed 174 NOTE! *pmem must be NULL, if not NULL, it will be free(). 175 */ 176 HUSKYEXT int copyString(char *str, char **pmem); 177 178 /* Copy chars from str to (*dest) until one of the chars in seps appears 179 * memory is allocated as needed 180 * *dest will be freed if non-NULL 181 * returns number of chars copied 182 */ 183 HUSKYEXT int copyStringUntilSep(char *str, char *seps, char **dest); 184 185 /* Structures for compact storage of array of NUL-terminated strings of 186 * various length. 187 * s_str_array is just one memory allocation and contains no pointers, 188 * so it can be freed by single free() and copied with memcpy() 189 * Use for nonmutable collections of (short) strings. 190 */ 191 typedef union str_mess { 192 int offsets[1]; /* offsets in bytes from start of union, used as index for strings[] */ 193 char strings[1]; /* NUL-terminated strings */ 194 } u_str_mess; 195 196 typedef struct str_array { 197 int count; /* Number of entries in data.offset array */ 198 u_str_mess data; 199 } s_str_array; 200 201 /* Get an address of n-th string in s_str_array *a */ 202 #define STR_N(a,n) &((a)->data.strings[(a)->data.offsets[n]]) 203 204 /* Offset of a byte just after last allocated byte (after last '\0') */ 205 #define STR_A_OFFSET_END(a) (a->data.offsets[a->count-1] + \ 206 strlen(STR_N(a, a->count-1)) + 1) 207 208 /* Calculate used memory size for s_str_array *a */ 209 #define STR_A_SIZE(a) (offsetof(s_str_array, data) + \ 210 STR_A_OFFSET_END(a)) 211 212 /* Calculate memory size used for strings in s_str_array->data.strings[] */ 213 #define STR_A_SSIZE(a) (STR_A_OFFSET_END(a) - \ 214 a->data.offsets[0]) 215 216 /* Get an index of 'find' in ss 217 * Case insensitive full match is used 218 * -1 if no match */ 219 HUSKYEXT int findInStrArray(s_str_array const *ss, char const *find); 220 221 HUSKYEXT s_str_array *copyStrArray(s_str_array *ss); 222 223 /* Parse strings like "token1, token2,token3 token4" into s_str_array */ 224 HUSKYEXT s_str_array *makeStrArray(char *token); 225 226 HUSKYEXT char *StrArray2String(s_str_array *ss); 227 228 #ifdef __cplusplus 229 } 230 #endif 231 232 #endif 233