1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/cx/string.h Mon Aug 29 20:54:42 2022 +0200 1.3 @@ -0,0 +1,771 @@ 1.4 +/* 1.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 1.6 + * 1.7 + * Copyright 2021 Mike Becker, Olaf Wintermann All rights reserved. 1.8 + * 1.9 + * Redistribution and use in source and binary forms, with or without 1.10 + * modification, are permitted provided that the following conditions are met: 1.11 + * 1.12 + * 1. Redistributions of source code must retain the above copyright 1.13 + * notice, this list of conditions and the following disclaimer. 1.14 + * 1.15 + * 2. Redistributions in binary form must reproduce the above copyright 1.16 + * notice, this list of conditions and the following disclaimer in the 1.17 + * documentation and/or other materials provided with the distribution. 1.18 + * 1.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 1.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 1.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 1.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 1.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 1.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 1.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 1.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 1.29 + * POSSIBILITY OF SUCH DAMAGE. 1.30 + */ 1.31 +/** 1.32 + * \file string.h 1.33 + * \brief Strings that know their length. 1.34 + * \author Mike Becker 1.35 + * \author Olaf Wintermann 1.36 + * \version 3.0 1.37 + * \copyright 2-Clause BSD License 1.38 + */ 1.39 + 1.40 +#ifndef UCX_STRING_H 1.41 +#define UCX_STRING_H 1.42 + 1.43 +#include "common.h" 1.44 +#include "allocator.h" 1.45 + 1.46 +/** 1.47 + * The UCX string structure. 1.48 + */ 1.49 +struct { 1.50 + /** 1.51 + * A pointer to the string. 1.52 + * \note The string is not necessarily \c NULL terminated. 1.53 + * Always use the length. 1.54 + */ 1.55 + char *ptr; 1.56 + /** The length of the string */ 1.57 + size_t length; 1.58 +} cx_mutstr_s; 1.59 + 1.60 +/** 1.61 + * A mutable string. 1.62 + */ 1.63 +typedef struct cx_mutstr_s cxmutstr; 1.64 + 1.65 +/** 1.66 + * The UCX string structure for immutable (constant) strings. 1.67 + */ 1.68 +struct { 1.69 + /** 1.70 + * A pointer to the immutable string. 1.71 + * \note The string is not necessarily \c NULL terminated. 1.72 + * Always use the length. 1.73 + */ 1.74 + char const *ptr; 1.75 + /** The length of the string */ 1.76 + size_t length; 1.77 +} cx_string_s; 1.78 + 1.79 +/** 1.80 + * An immutable string. 1.81 + */ 1.82 +typedef struct cx_string_s cxstring; 1.83 + 1.84 +#ifdef __cplusplus 1.85 +extern "C" { 1.86 +#endif 1.87 + 1.88 + 1.89 +/** 1.90 + * Wraps a mutable string that must be zero-terminated. 1.91 + * 1.92 + * The length is implicitly inferred by using a call to \c strlen(). 1.93 + * As a special case, a \c NULL argument is treated like an empty string. 1.94 + * 1.95 + * \note the wrapped string will share the specified pointer to the string. 1.96 + * If you do want a copy, use cx_strdup() on the return value of this function. 1.97 + * 1.98 + * If you need to wrap a constant string, use cx_str(). 1.99 + * 1.100 + * @param cstring the string to wrap, must be zero-terminated (or \c NULL) 1.101 + * @return the wrapped string 1.102 + * 1.103 + * @see cx_mutstrn() 1.104 + */ 1.105 +__attribute__((__warn_unused_result__)) 1.106 +cxmutstr cx_mutstr(char *cstring); 1.107 + 1.108 +/** 1.109 + * Wraps a string that does not need to be zero-terminated. 1.110 + * 1.111 + * The argument may be \c NULL if the length is zero. 1.112 + * 1.113 + * \note the wrapped string will share the specified pointer to the string. 1.114 + * If you do want a copy, use cx_strdup() on the return value of this function. 1.115 + * 1.116 + * If you need to wrap a constant string, use cx_strn(). 1.117 + * 1.118 + * @param cstring the string to wrap (or \c NULL, if the length is zero) 1.119 + * @param length the length of the string 1.120 + * @return the wrapped string 1.121 + * 1.122 + * @see cx_mutstr() 1.123 + */ 1.124 +__attribute__((__warn_unused_result__)) 1.125 +cxmutstr cx_mutstrn( 1.126 + char *cstring, 1.127 + size_t length 1.128 +); 1.129 + 1.130 +/** 1.131 + * Wraps a string that must be zero-terminated. 1.132 + * 1.133 + * The length is implicitly inferred by using a call to \c strlen(). 1.134 + * As a special case, a \c NULL argument is treated like an empty string. 1.135 + * 1.136 + * \note the wrapped string will share the specified pointer to the string. 1.137 + * If you do want a copy, use cx_strdup() on the return value of this function. 1.138 + * 1.139 + * If you need to wrap a non-constant string, use cx_mutstr(). 1.140 + * 1.141 + * @param cstring the string to wrap, must be zero-terminated (or \c NULL) 1.142 + * @return the wrapped string 1.143 + * 1.144 + * @see cx_strn() 1.145 + */ 1.146 +__attribute__((__warn_unused_result__)) 1.147 +cxstring cx_str(char const *cstring); 1.148 + 1.149 + 1.150 +/** 1.151 + * Wraps a string that does not need to be zero-terminated. 1.152 + * 1.153 + * The argument may be \c NULL if the length is zero. 1.154 + * 1.155 + * \note the wrapped string will share the specified pointer to the string. 1.156 + * If you do want a copy, use cx_strdup() on the return value of this function. 1.157 + * 1.158 + * If you need to wrap a non-constant string, use cx_mutstrn(). 1.159 + * 1.160 + * @param cstring the string to wrap (or \c NULL, if the length is zero) 1.161 + * @param length the length of the string 1.162 + * @return the wrapped string 1.163 + * 1.164 + * @see cx_str() 1.165 + */ 1.166 +__attribute__((__warn_unused_result__)) 1.167 +cxstring cx_strn( 1.168 + char const *cstring, 1.169 + size_t length 1.170 +); 1.171 + 1.172 +/** 1.173 +* Casts a mutable string to an immutable string. 1.174 +* 1.175 +* \note This is not seriously a cast. Instead you get a copy 1.176 +* of the struct with the desired pointer type. Both structs still 1.177 +* point to the same location, though! 1.178 +* 1.179 +* @param str the mutable string to cast 1.180 +* @return an immutable copy of the string pointer 1.181 +*/ 1.182 +__attribute__((__warn_unused_result__)) 1.183 +cxstring cx_strcast(cxmutstr str); 1.184 + 1.185 +/** 1.186 + * Passes the pointer in this string to \c free(). 1.187 + * 1.188 + * The pointer in the struct is set to \c NULL and the length is set to zero. 1.189 + * 1.190 + * \note There is no implementation for cxstring, because it is unlikely that 1.191 + * you ever have a \c char \c const* you are really supposed to free. If you 1.192 + * encounter such situation, you should double-check your code. 1.193 + * 1.194 + * @param str the string to free 1.195 + */ 1.196 +void cx_strfree(cxmutstr *str); 1.197 + 1.198 +/** 1.199 + * Returns the accumulated length of all specified strings. 1.200 + * 1.201 + * \attention if the count argument is larger than the number of the 1.202 + * specified strings, the behavior is undefined. 1.203 + * 1.204 + * @param count the total number of specified strings 1.205 + * @param ... all strings 1.206 + * @return the accumulated length of all strings 1.207 + */ 1.208 +__attribute__((__warn_unused_result__)) 1.209 +size_t cx_strlen( 1.210 + size_t count, 1.211 + ... 1.212 +); 1.213 + 1.214 +/** 1.215 + * Concatenates two or more strings. 1.216 + * 1.217 + * The resulting string will be allocated by the specified allocator. 1.218 + * So developers \em must pass the return value to cx_strfree() eventually. 1.219 + * 1.220 + * \note It is guaranteed that there is only one allocation. 1.221 + * 1.222 + * @param alloc the allocator to use 1.223 + * @param count the total number of strings to concatenate 1.224 + * @param ... all strings 1.225 + * @return the concatenated string 1.226 + */ 1.227 +__attribute__((__warn_unused_result__, __nonnull__)) 1.228 +cxmutstr cx_strcat_a( 1.229 + CxAllocator *alloc, 1.230 + size_t count, 1.231 + ... 1.232 +); 1.233 + 1.234 +/** 1.235 + * Concatenates two or more strings. 1.236 + * 1.237 + * The resulting string will be allocated by standard \c malloc(). 1.238 + * So developers \em must pass the return value to cx_strfree() eventually. 1.239 + * 1.240 + * @param count the total number of strings to concatenate 1.241 + * @param ... all strings 1.242 + * @return the concatenated string 1.243 + */ 1.244 +#define cx_strcat(count, ...) \ 1.245 +cx_strcat_a(cxDefaultAllocator, count, __VA_ARGS__) 1.246 + 1.247 +/** 1.248 + * Returns a substring starting at the specified location. 1.249 + * 1.250 + * \attention the new string references the same memory area as the 1.251 + * input string and is usually \em not zero-terminated. 1.252 + * Use cx_strdup() to get a copy. 1.253 + * 1.254 + * @param string input string 1.255 + * @param start start location of the substring 1.256 + * @return a substring of \p string starting at \p start 1.257 + * 1.258 + * @see cx_strsubsl() 1.259 + * @see cx_strsubs_m() 1.260 + * @see cx_strsubsl_m() 1.261 + */ 1.262 +__attribute__((__warn_unused_result__)) 1.263 +cxstring cx_strsubs( 1.264 + cxstring string, 1.265 + size_t start 1.266 +); 1.267 + 1.268 +/** 1.269 + * Returns a substring starting at the specified location. 1.270 + * 1.271 + * The returned string will be limited to \p length bytes or the number 1.272 + * of bytes available in \p string, whichever is smaller. 1.273 + * 1.274 + * \attention the new string references the same memory area as the 1.275 + * input string and is usually \em not zero-terminated. 1.276 + * Use cx_strdup() to get a copy. 1.277 + * 1.278 + * @param string input string 1.279 + * @param start start location of the substring 1.280 + * @param length the maximum length of the returned string 1.281 + * @return a substring of \p string starting at \p start 1.282 + * 1.283 + * @see cx_strsubs() 1.284 + * @see cx_strsubs_m() 1.285 + * @see cx_strsubsl_m() 1.286 + */ 1.287 +__attribute__((__warn_unused_result__)) 1.288 +cxstring cx_strsubsl( 1.289 + cxstring string, 1.290 + size_t start, 1.291 + size_t length 1.292 +); 1.293 + 1.294 +/** 1.295 + * Returns a substring starting at the specified location. 1.296 + * 1.297 + * \attention the new string references the same memory area as the 1.298 + * input string and is usually \em not zero-terminated. 1.299 + * Use cx_strdup() to get a copy. 1.300 + * 1.301 + * @param string input string 1.302 + * @param start start location of the substring 1.303 + * @return a substring of \p string starting at \p start 1.304 + * 1.305 + * @see cx_strsubsl_m() 1.306 + * @see cx_strsubs() 1.307 + * @see cx_strsubsl() 1.308 + */ 1.309 +__attribute__((__warn_unused_result__)) 1.310 +cxmutstr cx_strsubs_m( 1.311 + cxmutstr string, 1.312 + size_t start 1.313 +); 1.314 + 1.315 +/** 1.316 + * Returns a substring starting at the specified location. 1.317 + * 1.318 + * The returned string will be limited to \p length bytes or the number 1.319 + * of bytes available in \p string, whichever is smaller. 1.320 + * 1.321 + * \attention the new string references the same memory area as the 1.322 + * input string and is usually \em not zero-terminated. 1.323 + * Use cx_strdup() to get a copy. 1.324 + * 1.325 + * @param string input string 1.326 + * @param start start location of the substring 1.327 + * @param length the maximum length of the returned string 1.328 + * @return a substring of \p string starting at \p start 1.329 + * 1.330 + * @see cx_strsubs_m() 1.331 + * @see cx_strsubs() 1.332 + * @see cx_strsubsl() 1.333 + */ 1.334 +__attribute__((__warn_unused_result__)) 1.335 +cxmutstr cx_strsubsl_m( 1.336 + cxmutstr string, 1.337 + size_t start, 1.338 + size_t length 1.339 +); 1.340 + 1.341 +/** 1.342 + * Returns a substring starting at the location of the first occurrence of the 1.343 + * specified character. 1.344 + * 1.345 + * If the string does not contain the character, an empty string is returned. 1.346 + * 1.347 + * @param string the string where to locate the character 1.348 + * @param chr the character to locate 1.349 + * @return a substring starting at the first location of \p chr 1.350 + * 1.351 + * @see cx_strchr_m() 1.352 + */ 1.353 +__attribute__((__warn_unused_result__)) 1.354 +cxstring cx_strchr( 1.355 + cxstring string, 1.356 + int chr 1.357 +); 1.358 + 1.359 +/** 1.360 + * Returns a substring starting at the location of the first occurrence of the 1.361 + * specified character. 1.362 + * 1.363 + * If the string does not contain the character, an empty string is returned. 1.364 + * 1.365 + * @param string the string where to locate the character 1.366 + * @param chr the character to locate 1.367 + * @return a substring starting at the first location of \p chr 1.368 + * 1.369 + * @see cx_strchr() 1.370 + */ 1.371 +__attribute__((__warn_unused_result__)) 1.372 +cxmutstr cx_strchr_m( 1.373 + cxmutstr string, 1.374 + int chr 1.375 +); 1.376 + 1.377 +/** 1.378 + * Returns a substring starting at the location of the last occurrence of the 1.379 + * specified character. 1.380 + * 1.381 + * If the string does not contain the character, an empty string is returned. 1.382 + * 1.383 + * @param string the string where to locate the character 1.384 + * @param chr the character to locate 1.385 + * @return a substring starting at the last location of \p chr 1.386 + * 1.387 + * @see cx_strrchr_m() 1.388 + */ 1.389 +__attribute__((__warn_unused_result__)) 1.390 +cxstring cx_strrchr( 1.391 + cxstring string, 1.392 + int chr 1.393 +); 1.394 + 1.395 +/** 1.396 + * Returns a substring starting at the location of the last occurrence of the 1.397 + * specified character. 1.398 + * 1.399 + * If the string does not contain the character, an empty string is returned. 1.400 + * 1.401 + * @param string the string where to locate the character 1.402 + * @param chr the character to locate 1.403 + * @return a substring starting at the last location of \p chr 1.404 + * 1.405 + * @see cx_strrchr() 1.406 + */ 1.407 +__attribute__((__warn_unused_result__)) 1.408 +cxmutstr cx_strrchr_m( 1.409 + cxmutstr string, 1.410 + int chr 1.411 +); 1.412 + 1.413 +/** 1.414 + * Returns a substring starting at the location of the first occurrence of the 1.415 + * specified string. 1.416 + * 1.417 + * If \p haystack does not contain \p needle, an empty string is returned. 1.418 + * 1.419 + * If \p needle is an empty string, the complete \p haystack is 1.420 + * returned. 1.421 + * 1.422 + * @param haystack the string to be scanned 1.423 + * @param needle string containing the sequence of characters to match 1.424 + * @return a substring starting at the first occurrence of 1.425 + * \p needle, or an empty string, if the sequence is not 1.426 + * contained 1.427 + * @see cx_strstr_m() 1.428 + */ 1.429 +__attribute__((__warn_unused_result__)) 1.430 +cxstring cx_strstr( 1.431 + cxstring haystack, 1.432 + cxstring needle 1.433 +); 1.434 + 1.435 +/** 1.436 + * Returns a substring starting at the location of the first occurrence of the 1.437 + * specified string. 1.438 + * 1.439 + * If \p haystack does not contain \p needle, an empty string is returned. 1.440 + * 1.441 + * If \p needle is an empty string, the complete \p haystack is 1.442 + * returned. 1.443 + * 1.444 + * @param haystack the string to be scanned 1.445 + * @param needle string containing the sequence of characters to match 1.446 + * @return a substring starting at the first occurrence of 1.447 + * \p needle, or an empty string, if the sequence is not 1.448 + * contained 1.449 + * @see cx_strstr() 1.450 + */ 1.451 +__attribute__((__warn_unused_result__)) 1.452 +cxmutstr cx_strstr_m( 1.453 + cxmutstr haystack, 1.454 + cxstring needle 1.455 +); 1.456 + 1.457 +/** 1.458 + * Splits a given string using a delimiter string. 1.459 + * 1.460 + * \note The resulting array contains strings that point to the source 1.461 + * \p string. Use cx_strdup() to get copies. 1.462 + * 1.463 + * @param string the string to split 1.464 + * @param delim the delimiter 1.465 + * @param limit the maximum number of split items 1.466 + * @param output a pre-allocated array of at least \p limit length 1.467 + * @return the actual number of split items 1.468 + */ 1.469 +__attribute__((__warn_unused_result__, __nonnull__)) 1.470 +size_t cx_strsplit( 1.471 + cxstring string, 1.472 + cxstring delim, 1.473 + size_t limit, 1.474 + cxstring *output 1.475 +); 1.476 + 1.477 +/** 1.478 + * Splits a given string using a delimiter string. 1.479 + * 1.480 + * The array pointed to by \p output will be allocated by \p allocator. 1.481 + * 1.482 + * \note The resulting array contains strings that point to the source 1.483 + * \p string. Use cx_strdup() to get copies. 1.484 + * 1.485 + * \attention If allocation fails, the \c NULL pointer will be written to 1.486 + * \p output and the number returned will be zero. 1.487 + * 1.488 + * @param allocator the allocator to use for allocating the resulting array 1.489 + * @param string the string to split 1.490 + * @param delim the delimiter 1.491 + * @param limit the maximum number of split items 1.492 + * @param output a pointer where the address of the allocated array shall be 1.493 + * written to 1.494 + * @return the actual number of split items 1.495 + */ 1.496 +__attribute__((__warn_unused_result__, __nonnull__)) 1.497 +size_t cx_strsplit_a( 1.498 + CxAllocator *allocator, 1.499 + cxstring string, 1.500 + cxstring delim, 1.501 + size_t limit, 1.502 + cxstring **output 1.503 +); 1.504 + 1.505 + 1.506 +/** 1.507 + * Splits a given string using a delimiter string. 1.508 + * 1.509 + * \note The resulting array contains strings that point to the source 1.510 + * \p string. Use cx_strdup() to get copies. 1.511 + * 1.512 + * @param string the string to split 1.513 + * @param delim the delimiter 1.514 + * @param limit the maximum number of split items 1.515 + * @param output a pre-allocated array of at least \p limit length 1.516 + * @return the actual number of split items 1.517 + */ 1.518 +__attribute__((__warn_unused_result__, __nonnull__)) 1.519 +size_t cx_strsplit_m( 1.520 + cxmutstr string, 1.521 + cxstring delim, 1.522 + size_t limit, 1.523 + cxmutstr *output 1.524 +); 1.525 + 1.526 +/** 1.527 + * Splits a given string using a delimiter string. 1.528 + * 1.529 + * The array pointed to by \p output will be allocated by \p allocator. 1.530 + * 1.531 + * \note The resulting array contains strings that point to the source 1.532 + * \p string. Use cx_strdup() to get copies. 1.533 + * 1.534 + * \attention If allocation fails, the \c NULL pointer will be written to 1.535 + * \p output and the number returned will be zero. 1.536 + * 1.537 + * @param allocator the allocator to use for allocating the resulting array 1.538 + * @param string the string to split 1.539 + * @param delim the delimiter 1.540 + * @param limit the maximum number of split items 1.541 + * @param output a pointer where the address of the allocated array shall be 1.542 + * written to 1.543 + * @return the actual number of split items 1.544 + */ 1.545 +__attribute__((__warn_unused_result__, __nonnull__)) 1.546 +size_t cx_strsplit_ma( 1.547 + CxAllocator *allocator, 1.548 + cxmutstr string, 1.549 + cxstring delim, 1.550 + size_t limit, 1.551 + cxmutstr **output 1.552 +); 1.553 + 1.554 +/** 1.555 + * Compares two strings. 1.556 + * 1.557 + * @param s1 the first string 1.558 + * @param s2 the second string 1.559 + * @return negative if \p s1 is smaller than \p s2, positive if \p s1 is larger 1.560 + * than \p s2, zero if both strings equal 1.561 + */ 1.562 +__attribute__((__warn_unused_result__)) 1.563 +int cx_strcmp( 1.564 + cxstring s1, 1.565 + cxstring s2 1.566 +); 1.567 + 1.568 +/** 1.569 + * Compares two strings ignoring case. 1.570 + * 1.571 + * @param s1 the first string 1.572 + * @param s2 the second string 1.573 + * @return negative if \p s1 is smaller than \p s2, positive if \p s1 is larger 1.574 + * than \p s2, zero if both strings equal ignoring case 1.575 + */ 1.576 +__attribute__((__warn_unused_result__)) 1.577 +int cx_strcasecmp( 1.578 + cxstring s1, 1.579 + cxstring s2 1.580 +); 1.581 + 1.582 +/** 1.583 + * Creates a duplicate of the specified string. 1.584 + * 1.585 + * The new string will contain a copy allocated by standard 1.586 + * \c malloc(). So developers \em must pass the return value to cx_strfree(). 1.587 + * 1.588 + * \note The returned string is guaranteed to be zero-terminated and can safely 1.589 + * be passed to other APIs. 1.590 + * 1.591 + * @param string the string to duplicate 1.592 + * @return a duplicate of the string 1.593 + * @see cx_strdup_a() 1.594 + */ 1.595 +__attribute__((__warn_unused_result__)) 1.596 +cxmutstr cx_strdup(cxstring string); 1.597 + 1.598 +/** 1.599 + * Creates a duplicate of the specified string. 1.600 + * 1.601 + * The new string will contain a copy allocated by \p allocator. 1.602 + * 1.603 + * \note The returned string is guaranteed to be zero-terminated and can safely 1.604 + * be passed to other APIs. 1.605 + * 1.606 + * @param allocator the allocator to use 1.607 + * @param string the string to duplicate 1.608 + * @return a duplicate of the string 1.609 + * @see cx_strdup() 1.610 + */ 1.611 +__attribute__((__warn_unused_result__, __nonnull__)) 1.612 +cxmutstr cx_strdup_a( 1.613 + CxAllocator *allocator, 1.614 + cxstring string 1.615 +); 1.616 + 1.617 +/** 1.618 + * Omits leading and trailing spaces. 1.619 + * 1.620 + * \note the returned string references the same memory, thus you 1.621 + * must \em not free the returned memory. 1.622 + * 1.623 + * @param string the string that shall be trimmed 1.624 + * @return the trimmed string 1.625 + */ 1.626 +__attribute__((__warn_unused_result__)) 1.627 +cxstring cx_strtrim(cxstring string); 1.628 + 1.629 +/** 1.630 + * Omits leading and trailing spaces. 1.631 + * 1.632 + * \note the returned string references the same memory, thus you 1.633 + * must \em not free the returned memory. 1.634 + * 1.635 + * @param string the string that shall be trimmed 1.636 + * @return the trimmed string 1.637 + */ 1.638 +__attribute__((__warn_unused_result__)) 1.639 +cxmutstr cx_strtrim_m(cxmutstr string); 1.640 + 1.641 +/** 1.642 + * Checks, if a string has a specific prefix. 1.643 + * 1.644 + * @param string the string to check 1.645 + * @param prefix the prefix the string should have 1.646 + * @return \c true, if and only if the string has the specified prefix, 1.647 + * \c false otherwise 1.648 + */ 1.649 +__attribute__((__warn_unused_result__)) 1.650 +bool cx_strprefix( 1.651 + cxstring string, 1.652 + cxstring prefix 1.653 +); 1.654 + 1.655 +/** 1.656 + * Checks, if a string has a specific suffix. 1.657 + * 1.658 + * @param string the string to check 1.659 + * @param suffix the suffix the string should have 1.660 + * @return \c true, if and only if the string has the specified suffix, 1.661 + * \c false otherwise 1.662 + */ 1.663 +__attribute__((__warn_unused_result__)) 1.664 +int cx_strsuffix( 1.665 + cxstring string, 1.666 + cxstring suffix 1.667 +); 1.668 + 1.669 +/** 1.670 + * Checks, if a string has a specific prefix, ignoring the case. 1.671 + * 1.672 + * @param string the string to check 1.673 + * @param prefix the prefix the string should have 1.674 + * @return \c true, if and only if the string has the specified prefix, 1.675 + * \c false otherwise 1.676 + */ 1.677 +__attribute__((__warn_unused_result__)) 1.678 +int cx_strcaseprefix( 1.679 + cxstring string, 1.680 + cxstring prefix 1.681 +); 1.682 + 1.683 +/** 1.684 + * Checks, if a string has a specific suffix, ignoring the case. 1.685 + * 1.686 + * @param string the string to check 1.687 + * @param suffix the suffix the string should have 1.688 + * @return \c true, if and only if the string has the specified suffix, 1.689 + * \c false otherwise 1.690 + */ 1.691 +__attribute__((__warn_unused_result__)) 1.692 +int cx_strcasesuffix( 1.693 + cxstring string, 1.694 + cxstring suffix 1.695 +); 1.696 + 1.697 +/** 1.698 + * Converts the string to lower case. 1.699 + * 1.700 + * The change is made in-place. If you want a copy, use cx_strdup(), first. 1.701 + * 1.702 + * @param string the string to modify 1.703 + * @see cx_strdup() 1.704 + */ 1.705 +void cx_strlower(cxmutstr string); 1.706 + 1.707 +/** 1.708 + * Converts the string to upper case. 1.709 + * 1.710 + * The change is made in-place. If you want a copy, use cx_strdup(), first. 1.711 + * 1.712 + * @param string the string to modify 1.713 + * @see cx_strdup() 1.714 + */ 1.715 +void cx_strupper(cxmutstr string); 1.716 + 1.717 +/** 1.718 + * Replaces a pattern in a string with another string. 1.719 + * 1.720 + * The pattern is taken literally and is no regular expression. 1.721 + * Replaces at most \p replmax occurrences. 1.722 + * 1.723 + * The returned string will be allocated by \c malloc() and \em must be passed 1.724 + * to cx_strfree() eventually. 1.725 + * 1.726 + * If allocation fails, or the input string is empty, 1.727 + * the returned string will point to \c NULL. 1.728 + * 1.729 + * @param str the string where replacements should be applied 1.730 + * @param pattern the pattern to search for 1.731 + * @param replacement the replacement string 1.732 + * @param replmax maximum number of replacements 1.733 + * @return the resulting string after applying the replacements 1.734 + */ 1.735 +__attribute__((__warn_unused_result__)) 1.736 +cxmutstr cx_strreplace( 1.737 + cxstring str, 1.738 + cxstring pattern, 1.739 + cxstring replacement, 1.740 + size_t replmax 1.741 +); 1.742 + 1.743 +/** 1.744 + * Replaces a pattern in a string with another string. 1.745 + * 1.746 + * The pattern is taken literally and is no regular expression. 1.747 + * Replaces at most \p replmax occurrences. 1.748 + * 1.749 + * The returned string will be allocated by \p allocator. 1.750 + * 1.751 + * If allocation fails, or the input string is empty, 1.752 + * the returned string will point to \c NULL. 1.753 + * 1.754 + * @param allocator the allocator to use 1.755 + * @param str the string where replacements should be applied 1.756 + * @param pattern the pattern to search for 1.757 + * @param replacement the replacement string 1.758 + * @param replmax maximum number of replacements 1.759 + * @return the resulting string after applying the replacements 1.760 + */ 1.761 +__attribute__((__warn_unused_result__, __nonnull__)) 1.762 +cxmutstr cx_strreplace_a( 1.763 + CxAllocator *allocator, 1.764 + cxstring str, 1.765 + cxstring pattern, 1.766 + cxstring replacement, 1.767 + size_t replmax 1.768 +); 1.769 + 1.770 +#ifdef __cplusplus 1.771 +} // extern "C" 1.772 +#endif 1.773 + 1.774 +#endif //UCX_STRING_H