triostr.c 41 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112
  1. /*************************************************************************
  2. *
  3. * $Id$
  4. *
  5. * Copyright (C) 2001 Bjorn Reese and Daniel Stenberg.
  6. *
  7. * Permission to use, copy, modify, and distribute this software for any
  8. * purpose with or without fee is hereby granted, provided that the above
  9. * copyright notice and this permission notice appear in all copies.
  10. *
  11. * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  12. * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  13. * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE AUTHORS AND
  14. * CONTRIBUTORS ACCEPT NO RESPONSIBILITY IN ANY CONCEIVABLE MANNER.
  15. *
  16. ************************************************************************/
  17. /*************************************************************************
  18. * Include files
  19. */
  20. #include <assert.h>
  21. #include <stdlib.h>
  22. #include <string.h>
  23. #include <ctype.h>
  24. #include <math.h>
  25. #include "triodef.h"
  26. #include "triostr.h"
  27. /*************************************************************************
  28. * Definitions
  29. */
  30. #if !defined(TRIO_STRING_PUBLIC)
  31. # define TRIO_STRING_PUBLIC TRIO_PUBLIC
  32. #endif
  33. #if !defined(TRIO_STRING_PRIVATE)
  34. # define TRIO_STRING_PRIVATE TRIO_PRIVATE
  35. #endif
  36. #if !defined(NULL)
  37. # define NULL 0
  38. #endif
  39. #if !defined(NIL)
  40. # define NIL ((char)0)
  41. #endif
  42. #if !defined(FALSE)
  43. # define FALSE (1 == 0)
  44. # define TRUE (! FALSE)
  45. #endif
  46. #if !defined(BOOLEAN_T)
  47. # define BOOLEAN_T int
  48. #endif
  49. #ifdef __VMS
  50. # define USE_STRTOD
  51. #elif defined(TRIO_COMPILER_SUPPORTS_C99)
  52. # define USE_STRTOD
  53. # define USE_STRTOF
  54. #elif defined(TRIO_COMPILER_MSVC)
  55. # define USE_STRTOD
  56. #endif
  57. #if defined(TRIO_PLATFORM_UNIX)
  58. # define USE_STRCASECMP
  59. # define USE_STRNCASECMP
  60. # if defined(TRIO_PLATFORM_SUNOS)
  61. # define USE_SYS_ERRLIST
  62. # else
  63. # define USE_STRERROR
  64. # endif
  65. # if defined(TRIO_PLATFORM_QNX)
  66. # define strcasecmp(x,y) stricmp(x,y)
  67. # define strncasecmp(x,y,n) strnicmp(x,y,n)
  68. # endif
  69. #elif defined(TRIO_PLATFORM_WIN32)
  70. # define USE_STRCASECMP
  71. # if defined(_WIN32_WCE)
  72. # define strcasecmp(x,y) _stricmp(x,y)
  73. # else
  74. # define strcasecmp(x,y) strcmpi(x,y)
  75. # endif
  76. #elif defined(TRIO_PLATFORM_OS400)
  77. # define USE_STRCASECMP
  78. # define USE_STRNCASECMP
  79. # include <strings.h>
  80. #endif
  81. #if !(defined(TRIO_PLATFORM_SUNOS))
  82. # define USE_TOLOWER
  83. # define USE_TOUPPER
  84. #endif
  85. /*************************************************************************
  86. * Structures
  87. */
  88. struct _trio_string_t
  89. {
  90. char *content;
  91. size_t length;
  92. size_t allocated;
  93. };
  94. /*************************************************************************
  95. * Constants
  96. */
  97. #if !defined(TRIO_MINIMAL)
  98. static TRIO_CONST char rcsid[] = "@(#)$Id$";
  99. #endif
  100. /*************************************************************************
  101. * Static String Functions
  102. */
  103. #if defined(TRIO_DOCUMENTATION)
  104. # include "doc/doc_static.h"
  105. #endif
  106. /** @addtogroup StaticStrings
  107. @{
  108. */
  109. /**
  110. Create new string.
  111. @param size Size of new string.
  112. @return Pointer to string, or NULL if allocation failed.
  113. */
  114. TRIO_STRING_PUBLIC char *
  115. trio_create
  116. TRIO_ARGS1((size),
  117. size_t size)
  118. {
  119. return (char *)TRIO_MALLOC(size);
  120. }
  121. /**
  122. Destroy string.
  123. @param string String to be freed.
  124. */
  125. TRIO_STRING_PUBLIC void
  126. trio_destroy
  127. TRIO_ARGS1((string),
  128. char *string)
  129. {
  130. if (string)
  131. {
  132. TRIO_FREE(string);
  133. }
  134. }
  135. /**
  136. Count the number of characters in a string.
  137. @param string String to measure.
  138. @return Number of characters in @string.
  139. */
  140. TRIO_STRING_PUBLIC size_t
  141. trio_length
  142. TRIO_ARGS1((string),
  143. TRIO_CONST char *string)
  144. {
  145. return strlen(string);
  146. }
  147. #if !defined(TRIO_MINIMAL)
  148. /**
  149. Append @p source at the end of @p target.
  150. @param target Target string.
  151. @param source Source string.
  152. @return Boolean value indicating success or failure.
  153. @pre @p target must point to a memory chunk with sufficient room to
  154. contain the @p target string and @p source string.
  155. @pre No boundary checking is performed, so insufficient memory will
  156. result in a buffer overrun.
  157. @post @p target will be zero terminated.
  158. */
  159. TRIO_STRING_PUBLIC int
  160. trio_append
  161. TRIO_ARGS2((target, source),
  162. char *target,
  163. TRIO_CONST char *source)
  164. {
  165. assert(target);
  166. assert(source);
  167. return (strcat(target, source) != NULL);
  168. }
  169. #endif /* !defined(TRIO_MINIMAL) */
  170. #if !defined(TRIO_MINIMAL)
  171. /**
  172. Append at most @p max characters from @p source to @p target.
  173. @param target Target string.
  174. @param max Maximum number of characters to append.
  175. @param source Source string.
  176. @return Boolean value indicating success or failure.
  177. @pre @p target must point to a memory chuck with sufficient room to
  178. contain the @p target string and the @p source string (at most @p max
  179. characters).
  180. @pre No boundary checking is performed, so insufficient memory will
  181. result in a buffer overrun.
  182. @post @p target will be zero terminated.
  183. */
  184. TRIO_STRING_PUBLIC int
  185. trio_append_max
  186. TRIO_ARGS3((target, max, source),
  187. char *target,
  188. size_t max,
  189. TRIO_CONST char *source)
  190. {
  191. size_t length;
  192. assert(target);
  193. assert(source);
  194. length = trio_length(target);
  195. if (max > length)
  196. {
  197. strncat(target, source, max - length - 1);
  198. }
  199. return TRUE;
  200. }
  201. #endif /* !defined(TRIO_MINIMAL) */
  202. #if !defined(TRIO_MINIMAL)
  203. /**
  204. Determine if a string contains a substring.
  205. @param string String to be searched.
  206. @param substring String to be found.
  207. @return Boolean value indicating success or failure.
  208. */
  209. TRIO_STRING_PUBLIC int
  210. trio_contains
  211. TRIO_ARGS2((string, substring),
  212. TRIO_CONST char *string,
  213. TRIO_CONST char *substring)
  214. {
  215. assert(string);
  216. assert(substring);
  217. return (0 != strstr(string, substring));
  218. }
  219. #endif /* !defined(TRIO_MINIMAL) */
  220. #if !defined(TRIO_MINIMAL)
  221. /**
  222. Copy @p source to @p target.
  223. @param target Target string.
  224. @param source Source string.
  225. @return Boolean value indicating success or failure.
  226. @pre @p target must point to a memory chunk with sufficient room to
  227. contain the @p source string.
  228. @pre No boundary checking is performed, so insufficient memory will
  229. result in a buffer overrun.
  230. @post @p target will be zero terminated.
  231. */
  232. TRIO_STRING_PUBLIC int
  233. trio_copy
  234. TRIO_ARGS2((target, source),
  235. char *target,
  236. TRIO_CONST char *source)
  237. {
  238. assert(target);
  239. assert(source);
  240. (void)strcpy(target, source);
  241. return TRUE;
  242. }
  243. #endif /* !defined(TRIO_MINIMAL) */
  244. /**
  245. Copy at most @p max characters from @p source to @p target.
  246. @param target Target string.
  247. @param max Maximum number of characters to append.
  248. @param source Source string.
  249. @return Boolean value indicating success or failure.
  250. @pre @p target must point to a memory chunk with sufficient room to
  251. contain the @p source string (at most @p max characters).
  252. @pre No boundary checking is performed, so insufficient memory will
  253. result in a buffer overrun.
  254. @post @p target will be zero terminated.
  255. */
  256. TRIO_STRING_PUBLIC int
  257. trio_copy_max
  258. TRIO_ARGS3((target, max, source),
  259. char *target,
  260. size_t max,
  261. TRIO_CONST char *source)
  262. {
  263. assert(target);
  264. assert(source);
  265. assert(max > 0); /* Includes != 0 */
  266. (void)strncpy(target, source, max - 1);
  267. target[max - 1] = (char)0;
  268. return TRUE;
  269. }
  270. /*
  271. * TrioDuplicateMax
  272. */
  273. TRIO_STRING_PRIVATE char *
  274. TrioDuplicateMax
  275. TRIO_ARGS2((source, size),
  276. TRIO_CONST char *source,
  277. size_t size)
  278. {
  279. char *target;
  280. assert(source);
  281. /* Make room for string plus a terminating zero */
  282. size++;
  283. target = trio_create(size);
  284. if (target)
  285. {
  286. trio_copy_max(target, size, source);
  287. }
  288. return target;
  289. }
  290. /**
  291. Duplicate @p source.
  292. @param source Source string.
  293. @return A copy of the @p source string.
  294. @post @p target will be zero terminated.
  295. */
  296. TRIO_STRING_PUBLIC char *
  297. trio_duplicate
  298. TRIO_ARGS1((source),
  299. TRIO_CONST char *source)
  300. {
  301. return TrioDuplicateMax(source, trio_length(source));
  302. }
  303. #if !defined(TRIO_MINIMAL)
  304. /**
  305. Duplicate at most @p max characters of @p source.
  306. @param source Source string.
  307. @param max Maximum number of characters to duplicate.
  308. @return A copy of the @p source string.
  309. @post @p target will be zero terminated.
  310. */
  311. TRIO_STRING_PUBLIC char *
  312. trio_duplicate_max TRIO_ARGS2((source, max),
  313. TRIO_CONST char *source,
  314. size_t max)
  315. {
  316. size_t length;
  317. assert(source);
  318. assert(max > 0);
  319. length = trio_length(source);
  320. if (length > max)
  321. {
  322. length = max;
  323. }
  324. return TrioDuplicateMax(source, length);
  325. }
  326. #endif /* !defined(TRIO_MINIMAL) */
  327. /**
  328. Compare if two strings are equal.
  329. @param first First string.
  330. @param second Second string.
  331. @return Boolean indicating whether the two strings are equal or not.
  332. Case-insensitive comparison.
  333. */
  334. TRIO_STRING_PUBLIC int
  335. trio_equal
  336. TRIO_ARGS2((first, second),
  337. TRIO_CONST char *first,
  338. TRIO_CONST char *second)
  339. {
  340. assert(first);
  341. assert(second);
  342. if ((first != NULL) && (second != NULL))
  343. {
  344. #if defined(USE_STRCASECMP)
  345. return (0 == strcasecmp(first, second));
  346. #else
  347. while ((*first != NIL) && (*second != NIL))
  348. {
  349. if (trio_to_upper(*first) != trio_to_upper(*second))
  350. {
  351. break;
  352. }
  353. first++;
  354. second++;
  355. }
  356. return ((*first == NIL) && (*second == NIL));
  357. #endif
  358. }
  359. return FALSE;
  360. }
  361. /**
  362. Compare if two strings are equal.
  363. @param first First string.
  364. @param second Second string.
  365. @return Boolean indicating whether the two strings are equal or not.
  366. Case-sensitive comparison.
  367. */
  368. TRIO_STRING_PUBLIC int
  369. trio_equal_case
  370. TRIO_ARGS2((first, second),
  371. TRIO_CONST char *first,
  372. TRIO_CONST char *second)
  373. {
  374. assert(first);
  375. assert(second);
  376. if ((first != NULL) && (second != NULL))
  377. {
  378. return (0 == strcmp(first, second));
  379. }
  380. return FALSE;
  381. }
  382. #if !defined(TRIO_MINIMAL)
  383. /**
  384. Compare if two strings up until the first @p max characters are equal.
  385. @param first First string.
  386. @param max Maximum number of characters to compare.
  387. @param second Second string.
  388. @return Boolean indicating whether the two strings are equal or not.
  389. Case-sensitive comparison.
  390. */
  391. TRIO_STRING_PUBLIC int
  392. trio_equal_case_max
  393. TRIO_ARGS3((first, max, second),
  394. TRIO_CONST char *first,
  395. size_t max,
  396. TRIO_CONST char *second)
  397. {
  398. assert(first);
  399. assert(second);
  400. if ((first != NULL) && (second != NULL))
  401. {
  402. return (0 == strncmp(first, second, max));
  403. }
  404. return FALSE;
  405. }
  406. #endif /* !defined(TRIO_MINIMAL) */
  407. /**
  408. Compare if two strings are equal.
  409. @param first First string.
  410. @param second Second string.
  411. @return Boolean indicating whether the two strings are equal or not.
  412. Collating characters are considered equal.
  413. */
  414. TRIO_STRING_PUBLIC int
  415. trio_equal_locale
  416. TRIO_ARGS2((first, second),
  417. TRIO_CONST char *first,
  418. TRIO_CONST char *second)
  419. {
  420. assert(first);
  421. assert(second);
  422. #if defined(LC_COLLATE)
  423. return (strcoll(first, second) == 0);
  424. #else
  425. return trio_equal(first, second);
  426. #endif
  427. }
  428. /**
  429. Compare if two strings up until the first @p max characters are equal.
  430. @param first First string.
  431. @param max Maximum number of characters to compare.
  432. @param second Second string.
  433. @return Boolean indicating whether the two strings are equal or not.
  434. Case-insensitive comparison.
  435. */
  436. TRIO_STRING_PUBLIC int
  437. trio_equal_max
  438. TRIO_ARGS3((first, max, second),
  439. TRIO_CONST char *first,
  440. size_t max,
  441. TRIO_CONST char *second)
  442. {
  443. assert(first);
  444. assert(second);
  445. if ((first != NULL) && (second != NULL))
  446. {
  447. #if defined(USE_STRNCASECMP)
  448. return (0 == strncasecmp(first, second, max));
  449. #else
  450. /* Not adequately tested yet */
  451. size_t cnt = 0;
  452. while ((*first != NIL) && (*second != NIL) && (cnt <= max))
  453. {
  454. if (trio_to_upper(*first) != trio_to_upper(*second))
  455. {
  456. break;
  457. }
  458. first++;
  459. second++;
  460. cnt++;
  461. }
  462. return ((cnt == max) || ((*first == NIL) && (*second == NIL)));
  463. #endif
  464. }
  465. return FALSE;
  466. }
  467. /**
  468. Provide a textual description of an error code (errno).
  469. @param error_number Error number.
  470. @return Textual description of @p error_number.
  471. */
  472. TRIO_STRING_PUBLIC TRIO_CONST char *
  473. trio_error
  474. TRIO_ARGS1((error_number),
  475. int error_number)
  476. {
  477. #if defined(USE_STRERROR)
  478. return strerror(error_number);
  479. #elif defined(USE_SYS_ERRLIST)
  480. extern char *sys_errlist[];
  481. extern int sys_nerr;
  482. return ((error_number < 0) || (error_number >= sys_nerr))
  483. ? "unknown"
  484. : sys_errlist[error_number];
  485. #else
  486. return "unknown";
  487. #endif
  488. }
  489. #if !defined(TRIO_MINIMAL) && !defined(_WIN32_WCE)
  490. /**
  491. Format the date/time according to @p format.
  492. @param target Target string.
  493. @param max Maximum number of characters to format.
  494. @param format Formatting string.
  495. @param datetime Date/time structure.
  496. @return Number of formatted characters.
  497. The formatting string accepts the same specifiers as the standard C
  498. function strftime.
  499. */
  500. TRIO_STRING_PUBLIC size_t
  501. trio_format_date_max
  502. TRIO_ARGS4((target, max, format, datetime),
  503. char *target,
  504. size_t max,
  505. TRIO_CONST char *format,
  506. TRIO_CONST struct tm *datetime)
  507. {
  508. assert(target);
  509. assert(format);
  510. assert(datetime);
  511. assert(max > 0);
  512. return strftime(target, max, format, datetime);
  513. }
  514. #endif /* !defined(TRIO_MINIMAL) */
  515. #if !defined(TRIO_MINIMAL)
  516. /**
  517. Calculate a hash value for a string.
  518. @param string String to be calculated on.
  519. @param type Hash function.
  520. @return Calculated hash value.
  521. @p type can be one of the following
  522. @li @c TRIO_HASH_PLAIN Plain hash function.
  523. */
  524. TRIO_STRING_PUBLIC unsigned long
  525. trio_hash
  526. TRIO_ARGS2((string, type),
  527. TRIO_CONST char *string,
  528. int type)
  529. {
  530. unsigned long value = 0L;
  531. char ch;
  532. assert(string);
  533. switch (type)
  534. {
  535. case TRIO_HASH_PLAIN:
  536. while ( (ch = *string++) != NIL )
  537. {
  538. value *= 31;
  539. value += (unsigned long)ch;
  540. }
  541. break;
  542. default:
  543. assert(FALSE);
  544. break;
  545. }
  546. return value;
  547. }
  548. #endif /* !defined(TRIO_MINIMAL) */
  549. #if !defined(TRIO_MINIMAL)
  550. /**
  551. Find first occurrence of a character in a string.
  552. @param string String to be searched.
  553. @param character Character to be found.
  554. @param A pointer to the found character, or NULL if character was not found.
  555. */
  556. TRIO_STRING_PUBLIC char *
  557. trio_index
  558. TRIO_ARGS2((string, character),
  559. TRIO_CONST char *string,
  560. int character)
  561. {
  562. assert(string);
  563. return strchr(string, character);
  564. }
  565. #endif /* !defined(TRIO_MINIMAL) */
  566. #if !defined(TRIO_MINIMAL)
  567. /**
  568. Find last occurrence of a character in a string.
  569. @param string String to be searched.
  570. @param character Character to be found.
  571. @param A pointer to the found character, or NULL if character was not found.
  572. */
  573. TRIO_STRING_PUBLIC char *
  574. trio_index_last
  575. TRIO_ARGS2((string, character),
  576. TRIO_CONST char *string,
  577. int character)
  578. {
  579. assert(string);
  580. return strchr(string, character);
  581. }
  582. #endif /* !defined(TRIO_MINIMAL) */
  583. #if !defined(TRIO_MINIMAL)
  584. /**
  585. Convert the alphabetic letters in the string to lower-case.
  586. @param target String to be converted.
  587. @return Number of processed characters (converted or not).
  588. */
  589. TRIO_STRING_PUBLIC int
  590. trio_lower
  591. TRIO_ARGS1((target),
  592. char *target)
  593. {
  594. assert(target);
  595. return trio_span_function(target, target, trio_to_lower);
  596. }
  597. #endif /* !defined(TRIO_MINIMAL) */
  598. #if !defined(TRIO_MINIMAL)
  599. /**
  600. Compare two strings using wildcards.
  601. @param string String to be searched.
  602. @param pattern Pattern, including wildcards, to search for.
  603. @return Boolean value indicating success or failure.
  604. Case-insensitive comparison.
  605. The following wildcards can be used
  606. @li @c * Match any number of characters.
  607. @li @c ? Match a single character.
  608. */
  609. TRIO_STRING_PUBLIC int
  610. trio_match
  611. TRIO_ARGS2((string, pattern),
  612. TRIO_CONST char *string,
  613. TRIO_CONST char *pattern)
  614. {
  615. assert(string);
  616. assert(pattern);
  617. for (; ('*' != *pattern); ++pattern, ++string)
  618. {
  619. if (NIL == *string)
  620. {
  621. return (NIL == *pattern);
  622. }
  623. if ((trio_to_upper((int)*string) != trio_to_upper((int)*pattern))
  624. && ('?' != *pattern))
  625. {
  626. return FALSE;
  627. }
  628. }
  629. /* two-line patch to prevent *too* much recursiveness: */
  630. while ('*' == pattern[1])
  631. pattern++;
  632. do
  633. {
  634. if ( trio_match(string, &pattern[1]) )
  635. {
  636. return TRUE;
  637. }
  638. }
  639. while (*string++);
  640. return FALSE;
  641. }
  642. #endif /* !defined(TRIO_MINIMAL) */
  643. #if !defined(TRIO_MINIMAL)
  644. /**
  645. Compare two strings using wildcards.
  646. @param string String to be searched.
  647. @param pattern Pattern, including wildcards, to search for.
  648. @return Boolean value indicating success or failure.
  649. Case-sensitive comparison.
  650. The following wildcards can be used
  651. @li @c * Match any number of characters.
  652. @li @c ? Match a single character.
  653. */
  654. TRIO_STRING_PUBLIC int
  655. trio_match_case
  656. TRIO_ARGS2((string, pattern),
  657. TRIO_CONST char *string,
  658. TRIO_CONST char *pattern)
  659. {
  660. assert(string);
  661. assert(pattern);
  662. for (; ('*' != *pattern); ++pattern, ++string)
  663. {
  664. if (NIL == *string)
  665. {
  666. return (NIL == *pattern);
  667. }
  668. if ((*string != *pattern)
  669. && ('?' != *pattern))
  670. {
  671. return FALSE;
  672. }
  673. }
  674. /* two-line patch to prevent *too* much recursiveness: */
  675. while ('*' == pattern[1])
  676. pattern++;
  677. do
  678. {
  679. if ( trio_match_case(string, &pattern[1]) )
  680. {
  681. return TRUE;
  682. }
  683. }
  684. while (*string++);
  685. return FALSE;
  686. }
  687. #endif /* !defined(TRIO_MINIMAL) */
  688. #if !defined(TRIO_MINIMAL)
  689. /**
  690. Execute a function on each character in string.
  691. @param target Target string.
  692. @param source Source string.
  693. @param Function Function to be executed.
  694. @return Number of processed characters.
  695. */
  696. TRIO_STRING_PUBLIC size_t
  697. trio_span_function
  698. TRIO_ARGS3((target, source, Function),
  699. char *target,
  700. TRIO_CONST char *source,
  701. int (*Function) TRIO_PROTO((int)))
  702. {
  703. size_t count = 0;
  704. assert(target);
  705. assert(source);
  706. assert(Function);
  707. while (*source != NIL)
  708. {
  709. *target++ = Function(*source++);
  710. count++;
  711. }
  712. return count;
  713. }
  714. #endif /* !defined(TRIO_MINIMAL) */
  715. #if !defined(TRIO_MINIMAL)
  716. /**
  717. Search for a substring in a string.
  718. @param string String to be searched.
  719. @param substring String to be found.
  720. @return Pointer to first occurrence of @p substring in @p string, or NULL
  721. if no match was found.
  722. */
  723. TRIO_STRING_PUBLIC char *
  724. trio_substring
  725. TRIO_ARGS2((string, substring),
  726. TRIO_CONST char *string,
  727. TRIO_CONST char *substring)
  728. {
  729. assert(string);
  730. assert(substring);
  731. return strstr(string, substring);
  732. }
  733. #endif /* !defined(TRIO_MINIMAL) */
  734. #if !defined(TRIO_MINIMAL)
  735. /**
  736. Search for a substring in the first @p max characters of a string.
  737. @param string String to be searched.
  738. @param max Maximum characters to be searched.
  739. @param substring String to be found.
  740. @return Pointer to first occurrence of @p substring in @p string, or NULL
  741. if no match was found.
  742. */
  743. TRIO_STRING_PUBLIC char *
  744. trio_substring_max
  745. TRIO_ARGS3((string, max, substring),
  746. TRIO_CONST char *string,
  747. size_t max,
  748. TRIO_CONST char *substring)
  749. {
  750. size_t count;
  751. size_t size;
  752. char *result = NULL;
  753. assert(string);
  754. assert(substring);
  755. size = trio_length(substring);
  756. if (size <= max)
  757. {
  758. for (count = 0; count <= max - size; count++)
  759. {
  760. if (trio_equal_max(substring, size, &string[count]))
  761. {
  762. result = (char *)&string[count];
  763. break;
  764. }
  765. }
  766. }
  767. return result;
  768. }
  769. #endif /* !defined(TRIO_MINIMAL) */
  770. #if !defined(TRIO_MINIMAL)
  771. /**
  772. Tokenize string.
  773. @param string String to be tokenized.
  774. @param tokens String containing list of delimiting characters.
  775. @return Start of new token.
  776. @warning @p string will be destroyed.
  777. */
  778. TRIO_STRING_PUBLIC char *
  779. trio_tokenize
  780. TRIO_ARGS2((string, delimiters),
  781. char *string,
  782. TRIO_CONST char *delimiters)
  783. {
  784. assert(delimiters);
  785. return strtok(string, delimiters);
  786. }
  787. #endif /* !defined(TRIO_MINIMAL) */
  788. /**
  789. Convert string to floating-point number.
  790. @param source String to be converted.
  791. @param endp Pointer to end of the converted string.
  792. @return A floating-point number.
  793. The following Extended Backus-Naur form is used
  794. @verbatim
  795. double ::= [ <sign> ]
  796. ( <number> |
  797. <number> <decimal_point> <number> |
  798. <decimal_point> <number> )
  799. [ <exponential> [ <sign> ] <number> ]
  800. number ::= 1*( <digit> )
  801. digit ::= ( '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9' )
  802. exponential ::= ( 'e' | 'E' )
  803. sign ::= ( '-' | '+' )
  804. decimal_point ::= '.'
  805. @endverbatim
  806. */
  807. /* FIXME: Add EBNF for hex-floats */
  808. TRIO_STRING_PUBLIC trio_long_double_t
  809. trio_to_long_double
  810. TRIO_ARGS2((source, endp),
  811. TRIO_CONST char *source,
  812. char **endp)
  813. {
  814. #if defined(USE_STRTOLD)
  815. return strtold(source, endp);
  816. #else
  817. int isNegative = FALSE;
  818. int isExponentNegative = FALSE;
  819. trio_long_double_t integer = 0.0;
  820. trio_long_double_t fraction = 0.0;
  821. unsigned long exponent = 0;
  822. trio_long_double_t base;
  823. trio_long_double_t fracdiv = 1.0;
  824. trio_long_double_t value = 0.0;
  825. /* First try hex-floats */
  826. if ((source[0] == '0') && ((source[1] == 'x') || (source[1] == 'X')))
  827. {
  828. base = 16.0;
  829. source += 2;
  830. while (isxdigit((int)*source))
  831. {
  832. integer *= base;
  833. integer += (isdigit((int)*source)
  834. ? (*source - '0')
  835. : 10 + (trio_to_upper((int)*source) - 'A'));
  836. source++;
  837. }
  838. if (*source == '.')
  839. {
  840. source++;
  841. while (isxdigit((int)*source))
  842. {
  843. fracdiv /= base;
  844. fraction += fracdiv * (isdigit((int)*source)
  845. ? (*source - '0')
  846. : 10 + (trio_to_upper((int)*source) - 'A'));
  847. source++;
  848. }
  849. if ((*source == 'p') || (*source == 'P'))
  850. {
  851. source++;
  852. if ((*source == '+') || (*source == '-'))
  853. {
  854. isExponentNegative = (*source == '-');
  855. source++;
  856. }
  857. while (isdigit((int)*source))
  858. {
  859. exponent *= 10;
  860. exponent += (*source - '0');
  861. source++;
  862. }
  863. }
  864. }
  865. /* For later use with exponent */
  866. base = 2.0;
  867. }
  868. else /* Then try normal decimal floats */
  869. {
  870. base = 10.0;
  871. isNegative = (*source == '-');
  872. /* Skip sign */
  873. if ((*source == '+') || (*source == '-'))
  874. source++;
  875. /* Integer part */
  876. while (isdigit((int)*source))
  877. {
  878. integer *= base;
  879. integer += (*source - '0');
  880. source++;
  881. }
  882. if (*source == '.')
  883. {
  884. source++; /* skip decimal point */
  885. while (isdigit((int)*source))
  886. {
  887. fracdiv /= base;
  888. fraction += (*source - '0') * fracdiv;
  889. source++;
  890. }
  891. }
  892. if ((*source == 'e')
  893. || (*source == 'E')
  894. #if TRIO_MICROSOFT
  895. || (*source == 'd')
  896. || (*source == 'D')
  897. #endif
  898. )
  899. {
  900. source++; /* Skip exponential indicator */
  901. isExponentNegative = (*source == '-');
  902. if ((*source == '+') || (*source == '-'))
  903. source++;
  904. while (isdigit((int)*source))
  905. {
  906. exponent *= (int)base;
  907. exponent += (*source - '0');
  908. source++;
  909. }
  910. }
  911. }
  912. value = integer + fraction;
  913. if (exponent != 0)
  914. {
  915. if (isExponentNegative)
  916. value /= pow(base, (double)exponent);
  917. else
  918. value *= pow(base, (double)exponent);
  919. }
  920. if (isNegative)
  921. value = -value;
  922. if (endp)
  923. *endp = (char *)source;
  924. return value;
  925. #endif
  926. }
  927. /**
  928. Convert string to floating-point number.
  929. @param source String to be converted.
  930. @param endp Pointer to end of the converted string.
  931. @return A floating-point number.
  932. See @ref trio_to_long_double.
  933. */
  934. TRIO_STRING_PUBLIC double
  935. trio_to_double
  936. TRIO_ARGS2((source, endp),
  937. TRIO_CONST char *source,
  938. char **endp)
  939. {
  940. #if defined(USE_STRTOD)
  941. return strtod(source, endp);
  942. #else
  943. return (double)trio_to_long_double(source, endp);
  944. #endif
  945. }
  946. #if !defined(TRIO_MINIMAL)
  947. /**
  948. Convert string to floating-point number.
  949. @param source String to be converted.
  950. @param endp Pointer to end of the converted string.
  951. @return A floating-point number.
  952. See @ref trio_to_long_double.
  953. */
  954. TRIO_STRING_PUBLIC float
  955. trio_to_float
  956. TRIO_ARGS2((source, endp),
  957. TRIO_CONST char *source,
  958. char **endp)
  959. {
  960. #if defined(USE_STRTOF)
  961. return strtof(source, endp);
  962. #else
  963. return (float)trio_to_long_double(source, endp);
  964. #endif
  965. }
  966. #endif /* !defined(TRIO_MINIMAL) */
  967. /**
  968. Convert string to signed integer.
  969. @param string String to be converted.
  970. @param endp Pointer to end of converted string.
  971. @param base Radix number of number.
  972. */
  973. TRIO_STRING_PUBLIC long
  974. trio_to_long
  975. TRIO_ARGS3((string, endp, base),
  976. TRIO_CONST char *string,
  977. char **endp,
  978. int base)
  979. {
  980. assert(string);
  981. assert((base >= 2) && (base <= 36));
  982. return strtol(string, endp, base);
  983. }
  984. #if !defined(TRIO_MINIMAL)
  985. /**
  986. Convert one alphabetic letter to lower-case.
  987. @param source The letter to be converted.
  988. @return The converted letter.
  989. */
  990. TRIO_STRING_PUBLIC int
  991. trio_to_lower
  992. TRIO_ARGS1((source),
  993. int source)
  994. {
  995. #if defined(USE_TOLOWER)
  996. return tolower(source);
  997. #else
  998. /* Does not handle locales or non-contiguous alphabetic characters */
  999. return ((source >= (int)'A') && (source <= (int)'Z'))
  1000. ? source - 'A' + 'a'
  1001. : source;
  1002. #endif
  1003. }
  1004. #endif /* !defined(TRIO_MINIMAL) */
  1005. #if !defined(TRIO_MINIMAL)
  1006. /**
  1007. Convert string to unsigned integer.
  1008. @param string String to be converted.
  1009. @param endp Pointer to end of converted string.
  1010. @param base Radix number of number.
  1011. */
  1012. TRIO_STRING_PUBLIC unsigned long
  1013. trio_to_unsigned_long
  1014. TRIO_ARGS3((string, endp, base),
  1015. TRIO_CONST char *string,
  1016. char **endp,
  1017. int base)
  1018. {
  1019. assert(string);
  1020. assert((base >= 2) && (base <= 36));
  1021. return strtoul(string, endp, base);
  1022. }
  1023. #endif /* !defined(TRIO_MINIMAL) */
  1024. /**
  1025. Convert one alphabetic letter to upper-case.
  1026. @param source The letter to be converted.
  1027. @return The converted letter.
  1028. */
  1029. TRIO_STRING_PUBLIC int
  1030. trio_to_upper
  1031. TRIO_ARGS1((source),
  1032. int source)
  1033. {
  1034. #if defined(USE_TOUPPER)
  1035. return toupper(source);
  1036. #else
  1037. /* Does not handle locales or non-contiguous alphabetic characters */
  1038. return ((source >= (int)'a') && (source <= (int)'z'))
  1039. ? source - 'a' + 'A'
  1040. : source;
  1041. #endif
  1042. }
  1043. #if !defined(TRIO_MINIMAL)
  1044. /**
  1045. Convert the alphabetic letters in the string to upper-case.
  1046. @param target The string to be converted.
  1047. @return The number of processed characters (converted or not).
  1048. */
  1049. TRIO_STRING_PUBLIC int
  1050. trio_upper
  1051. TRIO_ARGS1((target),
  1052. char *target)
  1053. {
  1054. assert(target);
  1055. return trio_span_function(target, target, trio_to_upper);
  1056. }
  1057. #endif /* !defined(TRIO_MINIMAL) */
  1058. /** @} End of StaticStrings */
  1059. /*************************************************************************
  1060. * Dynamic String Functions
  1061. */
  1062. #if defined(TRIO_DOCUMENTATION)
  1063. # include "doc/doc_dynamic.h"
  1064. #endif
  1065. /** @addtogroup DynamicStrings
  1066. @{
  1067. */
  1068. /*
  1069. * TrioStringAlloc
  1070. */
  1071. TRIO_STRING_PRIVATE trio_string_t *
  1072. TrioStringAlloc(TRIO_NOARGS)
  1073. {
  1074. trio_string_t *self;
  1075. self = (trio_string_t *)TRIO_MALLOC(sizeof(trio_string_t));
  1076. if (self)
  1077. {
  1078. self->content = NULL;
  1079. self->length = 0;
  1080. self->allocated = 0;
  1081. }
  1082. return self;
  1083. }
  1084. /*
  1085. * TrioStringGrow
  1086. *
  1087. * The size of the string will be increased by 'delta' characters. If
  1088. * 'delta' is zero, the size will be doubled.
  1089. */
  1090. TRIO_STRING_PRIVATE BOOLEAN_T
  1091. TrioStringGrow
  1092. TRIO_ARGS2((self, delta),
  1093. trio_string_t *self,
  1094. size_t delta)
  1095. {
  1096. BOOLEAN_T status = FALSE;
  1097. char *new_content;
  1098. size_t new_size;
  1099. new_size = (delta == 0)
  1100. ? ( (self->allocated == 0) ? 1 : self->allocated * 2 )
  1101. : self->allocated + delta;
  1102. new_content = (char *)TRIO_REALLOC(self->content, new_size);
  1103. if (new_content)
  1104. {
  1105. self->content = new_content;
  1106. self->allocated = new_size;
  1107. status = TRUE;
  1108. }
  1109. return status;
  1110. }
  1111. #if !defined(TRIO_MINIMAL)
  1112. /*
  1113. * TrioStringGrowTo
  1114. *
  1115. * The size of the string will be increased to 'length' plus one characters.
  1116. * If 'length' is less than the original size, the original size will be
  1117. * used (that is, the size of the string is never decreased).
  1118. */
  1119. TRIO_STRING_PRIVATE BOOLEAN_T
  1120. TrioStringGrowTo
  1121. TRIO_ARGS2((self, length),
  1122. trio_string_t *self,
  1123. size_t length)
  1124. {
  1125. length++; /* Room for terminating zero */
  1126. return (self->allocated < length)
  1127. ? TrioStringGrow(self, length - self->allocated)
  1128. : TRUE;
  1129. }
  1130. #endif /* !defined(TRIO_MINIMAL) */
  1131. #if !defined(TRIO_MINIMAL)
  1132. /**
  1133. Create a new dynamic string.
  1134. @param initial_size Initial size of the buffer.
  1135. @return Newly allocated dynamic string, or NULL if memory allocation failed.
  1136. */
  1137. TRIO_STRING_PUBLIC trio_string_t *
  1138. trio_string_create
  1139. TRIO_ARGS1((initial_size),
  1140. int initial_size)
  1141. {
  1142. trio_string_t *self;
  1143. self = TrioStringAlloc();
  1144. if (self)
  1145. {
  1146. if (TrioStringGrow(self,
  1147. (size_t)((initial_size > 0) ? initial_size : 1)))
  1148. {
  1149. self->content[0] = (char)0;
  1150. self->allocated = initial_size;
  1151. }
  1152. else
  1153. {
  1154. trio_string_destroy(self);
  1155. self = NULL;
  1156. }
  1157. }
  1158. return self;
  1159. }
  1160. #endif /* !defined(TRIO_MINIMAL) */
  1161. /**
  1162. Deallocate the dynamic string and its contents.
  1163. @param self Dynamic string
  1164. */
  1165. TRIO_STRING_PUBLIC void
  1166. trio_string_destroy
  1167. TRIO_ARGS1((self),
  1168. trio_string_t *self)
  1169. {
  1170. assert(self);
  1171. if (self)
  1172. {
  1173. trio_destroy(self->content);
  1174. TRIO_FREE(self);
  1175. }
  1176. }
  1177. #if !defined(TRIO_MINIMAL)
  1178. /**
  1179. Get a pointer to the content.
  1180. @param self Dynamic string.
  1181. @param offset Offset into content.
  1182. @return Pointer to the content.
  1183. @p Offset can be zero, positive, or negative. If @p offset is zero,
  1184. then the start of the content will be returned. If @p offset is positive,
  1185. then a pointer to @p offset number of characters from the beginning of the
  1186. content is returned. If @p offset is negative, then a pointer to @p offset
  1187. number of characters from the ending of the string, starting at the
  1188. terminating zero, is returned.
  1189. */
  1190. TRIO_STRING_PUBLIC char *
  1191. trio_string_get
  1192. TRIO_ARGS2((self, offset),
  1193. trio_string_t *self,
  1194. int offset)
  1195. {
  1196. char *result = NULL;
  1197. assert(self);
  1198. if (self->content != NULL)
  1199. {
  1200. if (self->length == 0)
  1201. {
  1202. (void)trio_string_length(self);
  1203. }
  1204. if (offset >= 0)
  1205. {
  1206. if (offset > (int)self->length)
  1207. {
  1208. offset = self->length;
  1209. }
  1210. }
  1211. else
  1212. {
  1213. offset += self->length + 1;
  1214. if (offset < 0)
  1215. {
  1216. offset = 0;
  1217. }
  1218. }
  1219. result = &(self->content[offset]);
  1220. }
  1221. return result;
  1222. }
  1223. #endif /* !defined(TRIO_MINIMAL) */
  1224. /**
  1225. Extract the content.
  1226. @param self Dynamic String
  1227. @return Content of dynamic string.
  1228. The content is removed from the dynamic string. This enables destruction
  1229. of the dynamic string without deallocation of the content.
  1230. */
  1231. TRIO_STRING_PUBLIC char *
  1232. trio_string_extract
  1233. TRIO_ARGS1((self),
  1234. trio_string_t *self)
  1235. {
  1236. char *result;
  1237. assert(self);
  1238. result = self->content;
  1239. /* FIXME: Allocate new empty buffer? */
  1240. self->content = NULL;
  1241. self->length = self->allocated = 0;
  1242. return result;
  1243. }
  1244. #if !defined(TRIO_MINIMAL)
  1245. /**
  1246. Set the content of the dynamic string.
  1247. @param self Dynamic String
  1248. @param buffer The new content.
  1249. Sets the content of the dynamic string to a copy @p buffer.
  1250. An existing content will be deallocated first, if necessary.
  1251. @remark
  1252. This function will make a copy of @p buffer.
  1253. You are responsible for deallocating @p buffer yourself.
  1254. */
  1255. TRIO_STRING_PUBLIC void
  1256. trio_xstring_set
  1257. TRIO_ARGS2((self, buffer),
  1258. trio_string_t *self,
  1259. char *buffer)
  1260. {
  1261. assert(self);
  1262. trio_destroy(self->content);
  1263. self->content = trio_duplicate(buffer);
  1264. }
  1265. #endif /* !defined(TRIO_MINIMAL) */
  1266. /*
  1267. * trio_string_size
  1268. */
  1269. TRIO_STRING_PUBLIC int
  1270. trio_string_size
  1271. TRIO_ARGS1((self),
  1272. trio_string_t *self)
  1273. {
  1274. assert(self);
  1275. return self->allocated;
  1276. }
  1277. /*
  1278. * trio_string_terminate
  1279. */
  1280. TRIO_STRING_PUBLIC void
  1281. trio_string_terminate
  1282. TRIO_ARGS1((self),
  1283. trio_string_t *self)
  1284. {
  1285. trio_xstring_append_char(self, 0);
  1286. }
  1287. #if !defined(TRIO_MINIMAL)
  1288. /**
  1289. Append the second string to the first.
  1290. @param self Dynamic string to be modified.
  1291. @param other Dynamic string to copy from.
  1292. @return Boolean value indicating success or failure.
  1293. */
  1294. TRIO_STRING_PUBLIC int
  1295. trio_string_append
  1296. TRIO_ARGS2((self, other),
  1297. trio_string_t *self,
  1298. trio_string_t *other)
  1299. {
  1300. size_t length;
  1301. assert(self);
  1302. assert(other);
  1303. length = self->length + other->length;
  1304. if (!TrioStringGrowTo(self, length))
  1305. goto error;
  1306. trio_copy(&self->content[self->length], other->content);
  1307. self->length = length;
  1308. return TRUE;
  1309. error:
  1310. return FALSE;
  1311. }
  1312. #endif /* !defined(TRIO_MINIMAL) */
  1313. #if !defined(TRIO_MINIMAL)
  1314. /*
  1315. * trio_xstring_append
  1316. */
  1317. TRIO_STRING_PUBLIC int
  1318. trio_xstring_append
  1319. TRIO_ARGS2((self, other),
  1320. trio_string_t *self,
  1321. TRIO_CONST char *other)
  1322. {
  1323. size_t length;
  1324. assert(self);
  1325. assert(other);
  1326. length = self->length + trio_length(other);
  1327. if (!TrioStringGrowTo(self, length))
  1328. goto error;
  1329. trio_copy(&self->content[self->length], other);
  1330. self->length = length;
  1331. return TRUE;
  1332. error:
  1333. return FALSE;
  1334. }
  1335. #endif /* !defined(TRIO_MINIMAL) */
  1336. /*
  1337. * trio_xstring_append_char
  1338. */
  1339. TRIO_STRING_PUBLIC int
  1340. trio_xstring_append_char
  1341. TRIO_ARGS2((self, character),
  1342. trio_string_t *self,
  1343. char character)
  1344. {
  1345. assert(self);
  1346. if ((int)self->length >= trio_string_size(self))
  1347. {
  1348. if (!TrioStringGrow(self, 0))
  1349. goto error;
  1350. }
  1351. self->content[self->length] = character;
  1352. self->length++;
  1353. return TRUE;
  1354. error:
  1355. return FALSE;
  1356. }
  1357. #if !defined(TRIO_MINIMAL)
  1358. /**
  1359. Search for the first occurrence of second parameter in the first.
  1360. @param self Dynamic string to be modified.
  1361. @param other Dynamic string to copy from.
  1362. @return Boolean value indicating success or failure.
  1363. */
  1364. TRIO_STRING_PUBLIC int
  1365. trio_string_contains
  1366. TRIO_ARGS2((self, other),
  1367. trio_string_t *self,
  1368. trio_string_t *other)
  1369. {
  1370. assert(self);
  1371. assert(other);
  1372. return trio_contains(self->content, other->content);
  1373. }
  1374. #endif /* !defined(TRIO_MINIMAL) */
  1375. #if !defined(TRIO_MINIMAL)
  1376. /*
  1377. * trio_xstring_contains
  1378. */
  1379. TRIO_STRING_PUBLIC int
  1380. trio_xstring_contains
  1381. TRIO_ARGS2((self, other),
  1382. trio_string_t *self,
  1383. TRIO_CONST char *other)
  1384. {
  1385. assert(self);
  1386. assert(other);
  1387. return trio_contains(self->content, other);
  1388. }
  1389. #endif /* !defined(TRIO_MINIMAL) */
  1390. #if !defined(TRIO_MINIMAL)
  1391. /*
  1392. * trio_string_copy
  1393. */
  1394. TRIO_STRING_PUBLIC int
  1395. trio_string_copy
  1396. TRIO_ARGS2((self, other),
  1397. trio_string_t *self,
  1398. trio_string_t *other)
  1399. {
  1400. assert(self);
  1401. assert(other);
  1402. self->length = 0;
  1403. return trio_string_append(self, other);
  1404. }
  1405. #endif /* !defined(TRIO_MINIMAL) */
  1406. #if !defined(TRIO_MINIMAL)
  1407. /*
  1408. * trio_xstring_copy
  1409. */
  1410. TRIO_STRING_PUBLIC int
  1411. trio_xstring_copy
  1412. TRIO_ARGS2((self, other),
  1413. trio_string_t *self,
  1414. TRIO_CONST char *other)
  1415. {
  1416. assert(self);
  1417. assert(other);
  1418. self->length = 0;
  1419. return trio_xstring_append(self, other);
  1420. }
  1421. #endif /* !defined(TRIO_MINIMAL) */
  1422. #if !defined(TRIO_MINIMAL)
  1423. /*
  1424. * trio_string_duplicate
  1425. */
  1426. TRIO_STRING_PUBLIC trio_string_t *
  1427. trio_string_duplicate
  1428. TRIO_ARGS1((other),
  1429. trio_string_t *other)
  1430. {
  1431. trio_string_t *self;
  1432. assert(other);
  1433. self = TrioStringAlloc();
  1434. if (self)
  1435. {
  1436. self->content = TrioDuplicateMax(other->content, other->length);
  1437. if (self->content)
  1438. {
  1439. self->length = other->length;
  1440. self->allocated = self->length + 1;
  1441. }
  1442. else
  1443. {
  1444. self->length = self->allocated = 0;
  1445. }
  1446. }
  1447. return self;
  1448. }
  1449. #endif /* !defined(TRIO_MINIMAL) */
  1450. /*
  1451. * trio_xstring_duplicate
  1452. */
  1453. TRIO_STRING_PUBLIC trio_string_t *
  1454. trio_xstring_duplicate
  1455. TRIO_ARGS1((other),
  1456. TRIO_CONST char *other)
  1457. {
  1458. trio_string_t *self;
  1459. assert(other);
  1460. self = TrioStringAlloc();
  1461. if (self)
  1462. {
  1463. self->content = TrioDuplicateMax(other, trio_length(other));
  1464. if (self->content)
  1465. {
  1466. self->length = trio_length(self->content);
  1467. self->allocated = self->length + 1;
  1468. }
  1469. else
  1470. {
  1471. self->length = self->allocated = 0;
  1472. }
  1473. }
  1474. return self;
  1475. }
  1476. #if !defined(TRIO_MINIMAL)
  1477. /*
  1478. * trio_string_equal
  1479. */
  1480. TRIO_STRING_PUBLIC int
  1481. trio_string_equal
  1482. TRIO_ARGS2((self, other),
  1483. trio_string_t *self,
  1484. trio_string_t *other)
  1485. {
  1486. assert(self);
  1487. assert(other);
  1488. return trio_equal(self->content, other->content);
  1489. }
  1490. #endif /* !defined(TRIO_MINIMAL) */
  1491. #if !defined(TRIO_MINIMAL)
  1492. /*
  1493. * trio_xstring_equal
  1494. */
  1495. TRIO_STRING_PUBLIC int
  1496. trio_xstring_equal
  1497. TRIO_ARGS2((self, other),
  1498. trio_string_t *self,
  1499. TRIO_CONST char *other)
  1500. {
  1501. assert(self);
  1502. assert(other);
  1503. return trio_equal(self->content, other);
  1504. }
  1505. #endif /* !defined(TRIO_MINIMAL) */
  1506. #if !defined(TRIO_MINIMAL)
  1507. /*
  1508. * trio_string_equal_max
  1509. */
  1510. TRIO_STRING_PUBLIC int
  1511. trio_string_equal_max
  1512. TRIO_ARGS3((self, max, other),
  1513. trio_string_t *self,
  1514. size_t max,
  1515. trio_string_t *other)
  1516. {
  1517. assert(self);
  1518. assert(other);
  1519. return trio_equal_max(self->content, max, other->content);
  1520. }
  1521. #endif /* !defined(TRIO_MINIMAL) */
  1522. #if !defined(TRIO_MINIMAL)
  1523. /*
  1524. * trio_xstring_equal_max
  1525. */
  1526. TRIO_STRING_PUBLIC int
  1527. trio_xstring_equal_max
  1528. TRIO_ARGS3((self, max, other),
  1529. trio_string_t *self,
  1530. size_t max,
  1531. TRIO_CONST char *other)
  1532. {
  1533. assert(self);
  1534. assert(other);
  1535. return trio_equal_max(self->content, max, other);
  1536. }
  1537. #endif /* !defined(TRIO_MINIMAL) */
  1538. #if !defined(TRIO_MINIMAL)
  1539. /*
  1540. * trio_string_equal_case
  1541. */
  1542. TRIO_STRING_PUBLIC int
  1543. trio_string_equal_case
  1544. TRIO_ARGS2((self, other),
  1545. trio_string_t *self,
  1546. trio_string_t *other)
  1547. {
  1548. assert(self);
  1549. assert(other);
  1550. return trio_equal_case(self->content, other->content);
  1551. }
  1552. #endif /* !defined(TRIO_MINIMAL) */
  1553. #if !defined(TRIO_MINIMAL)
  1554. /*
  1555. * trio_xstring_equal_case
  1556. */
  1557. TRIO_STRING_PUBLIC int
  1558. trio_xstring_equal_case
  1559. TRIO_ARGS2((self, other),
  1560. trio_string_t *self,
  1561. TRIO_CONST char *other)
  1562. {
  1563. assert(self);
  1564. assert(other);
  1565. return trio_equal_case(self->content, other);
  1566. }
  1567. #endif /* !defined(TRIO_MINIMAL) */
  1568. #if !defined(TRIO_MINIMAL)
  1569. /*
  1570. * trio_string_equal_case_max
  1571. */
  1572. TRIO_STRING_PUBLIC int
  1573. trio_string_equal_case_max
  1574. TRIO_ARGS3((self, max, other),
  1575. trio_string_t *self,
  1576. size_t max,
  1577. trio_string_t *other)
  1578. {
  1579. assert(self);
  1580. assert(other);
  1581. return trio_equal_case_max(self->content, max, other->content);
  1582. }
  1583. #endif /* !defined(TRIO_MINIMAL) */
  1584. #if !defined(TRIO_MINIMAL)
  1585. /*
  1586. * trio_xstring_equal_case_max
  1587. */
  1588. TRIO_STRING_PUBLIC int
  1589. trio_xstring_equal_case_max
  1590. TRIO_ARGS3((self, max, other),
  1591. trio_string_t *self,
  1592. size_t max,
  1593. TRIO_CONST char *other)
  1594. {
  1595. assert(self);
  1596. assert(other);
  1597. return trio_equal_case_max(self->content, max, other);
  1598. }
  1599. #endif /* !defined(TRIO_MINIMAL) */
  1600. #if !defined(TRIO_MINIMAL) && !defined(_WIN32_WCE)
  1601. /*
  1602. * trio_string_format_data_max
  1603. */
  1604. TRIO_STRING_PUBLIC size_t
  1605. trio_string_format_date_max
  1606. TRIO_ARGS4((self, max, format, datetime),
  1607. trio_string_t *self,
  1608. size_t max,
  1609. TRIO_CONST char *format,
  1610. TRIO_CONST struct tm *datetime)
  1611. {
  1612. assert(self);
  1613. return trio_format_date_max(self->content, max, format, datetime);
  1614. }
  1615. #endif /* !defined(TRIO_MINIMAL) */
  1616. #if !defined(TRIO_MINIMAL)
  1617. /*
  1618. * trio_string_index
  1619. */
  1620. TRIO_STRING_PUBLIC char *
  1621. trio_string_index
  1622. TRIO_ARGS2((self, character),
  1623. trio_string_t *self,
  1624. int character)
  1625. {
  1626. assert(self);
  1627. return trio_index(self->content, character);
  1628. }
  1629. #endif /* !defined(TRIO_MINIMAL) */
  1630. #if !defined(TRIO_MINIMAL)
  1631. /*
  1632. * trio_string_index_last
  1633. */
  1634. TRIO_STRING_PUBLIC char *
  1635. trio_string_index_last
  1636. TRIO_ARGS2((self, character),
  1637. trio_string_t *self,
  1638. int character)
  1639. {
  1640. assert(self);
  1641. return trio_index_last(self->content, character);
  1642. }
  1643. #endif /* !defined(TRIO_MINIMAL) */
  1644. #if !defined(TRIO_MINIMAL)
  1645. /*
  1646. * trio_string_length
  1647. */
  1648. TRIO_STRING_PUBLIC int
  1649. trio_string_length
  1650. TRIO_ARGS1((self),
  1651. trio_string_t *self)
  1652. {
  1653. assert(self);
  1654. if (self->length == 0)
  1655. {
  1656. self->length = trio_length(self->content);
  1657. }
  1658. return self->length;
  1659. }
  1660. #endif /* !defined(TRIO_MINIMAL) */
  1661. #if !defined(TRIO_MINIMAL)
  1662. /*
  1663. * trio_string_lower
  1664. */
  1665. TRIO_STRING_PUBLIC int
  1666. trio_string_lower
  1667. TRIO_ARGS1((self),
  1668. trio_string_t *self)
  1669. {
  1670. assert(self);
  1671. return trio_lower(self->content);
  1672. }
  1673. #endif /* !defined(TRIO_MINIMAL) */
  1674. #if !defined(TRIO_MINIMAL)
  1675. /*
  1676. * trio_string_match
  1677. */
  1678. TRIO_STRING_PUBLIC int
  1679. trio_string_match
  1680. TRIO_ARGS2((self, other),
  1681. trio_string_t *self,
  1682. trio_string_t *other)
  1683. {
  1684. assert(self);
  1685. assert(other);
  1686. return trio_match(self->content, other->content);
  1687. }
  1688. #endif /* !defined(TRIO_MINIMAL) */
  1689. #if !defined(TRIO_MINIMAL)
  1690. /*
  1691. * trio_xstring_match
  1692. */
  1693. TRIO_STRING_PUBLIC int
  1694. trio_xstring_match
  1695. TRIO_ARGS2((self, other),
  1696. trio_string_t *self,
  1697. TRIO_CONST char *other)
  1698. {
  1699. assert(self);
  1700. assert(other);
  1701. return trio_match(self->content, other);
  1702. }
  1703. #endif /* !defined(TRIO_MINIMAL) */
  1704. #if !defined(TRIO_MINIMAL)
  1705. /*
  1706. * trio_string_match_case
  1707. */
  1708. TRIO_STRING_PUBLIC int
  1709. trio_string_match_case
  1710. TRIO_ARGS2((self, other),
  1711. trio_string_t *self,
  1712. trio_string_t *other)
  1713. {
  1714. assert(self);
  1715. assert(other);
  1716. return trio_match_case(self->content, other->content);
  1717. }
  1718. #endif /* !defined(TRIO_MINIMAL) */
  1719. #if !defined(TRIO_MINIMAL)
  1720. /*
  1721. * trio_xstring_match_case
  1722. */
  1723. TRIO_STRING_PUBLIC int
  1724. trio_xstring_match_case
  1725. TRIO_ARGS2((self, other),
  1726. trio_string_t *self,
  1727. TRIO_CONST char *other)
  1728. {
  1729. assert(self);
  1730. assert(other);
  1731. return trio_match_case(self->content, other);
  1732. }
  1733. #endif /* !defined(TRIO_MINIMAL) */
  1734. #if !defined(TRIO_MINIMAL)
  1735. /*
  1736. * trio_string_substring
  1737. */
  1738. TRIO_STRING_PUBLIC char *
  1739. trio_string_substring
  1740. TRIO_ARGS2((self, other),
  1741. trio_string_t *self,
  1742. trio_string_t *other)
  1743. {
  1744. assert(self);
  1745. assert(other);
  1746. return trio_substring(self->content, other->content);
  1747. }
  1748. #endif /* !defined(TRIO_MINIMAL) */
  1749. #if !defined(TRIO_MINIMAL)
  1750. /*
  1751. * trio_xstring_substring
  1752. */
  1753. TRIO_STRING_PUBLIC char *
  1754. trio_xstring_substring
  1755. TRIO_ARGS2((self, other),
  1756. trio_string_t *self,
  1757. TRIO_CONST char *other)
  1758. {
  1759. assert(self);
  1760. assert(other);
  1761. return trio_substring(self->content, other);
  1762. }
  1763. #endif /* !defined(TRIO_MINIMAL) */
  1764. #if !defined(TRIO_MINIMAL)
  1765. /*
  1766. * trio_string_upper
  1767. */
  1768. TRIO_STRING_PUBLIC int
  1769. trio_string_upper
  1770. TRIO_ARGS1((self),
  1771. trio_string_t *self)
  1772. {
  1773. assert(self);
  1774. return trio_upper(self->content);
  1775. }
  1776. #endif /* !defined(TRIO_MINIMAL) */
  1777. /** @} End of DynamicStrings */