PageRenderTime 53ms CodeModel.GetById 22ms RepoModel.GetById 0ms app.codeStats 0ms

/branches/swig-2.0/Source/Swig/misc.c

#
C | 1156 lines | 838 code | 102 blank | 216 comment | 292 complexity | c052eda36857fe3b7030b07a2d579aa9 MD5 | raw file
Possible License(s): LGPL-2.1, Cube, GPL-3.0, 0BSD, GPL-2.0
  1. /* -----------------------------------------------------------------------------
  2. * See the LICENSE file for information on copyright, usage and redistribution
  3. * of SWIG, and the README file for authors - http://www.swig.org/release.html.
  4. *
  5. * misc.c
  6. *
  7. * Miscellaneous functions that don't really fit anywhere else.
  8. * ----------------------------------------------------------------------------- */
  9. char cvsroot_misc_c[] = "$Id: misc.c 11091 2009-01-28 16:10:16Z bhy $";
  10. #include "swig.h"
  11. #include <errno.h>
  12. #include <ctype.h>
  13. #include <limits.h>
  14. static char *fake_version = 0;
  15. /* -----------------------------------------------------------------------------
  16. * Swig_copy_string()
  17. *
  18. * Duplicate a NULL-terminate string given as a char *.
  19. * ----------------------------------------------------------------------------- */
  20. char *Swig_copy_string(const char *s) {
  21. char *c = 0;
  22. if (s) {
  23. c = (char *) malloc(strlen(s) + 1);
  24. strcpy(c, s);
  25. }
  26. return c;
  27. }
  28. /* -----------------------------------------------------------------------------
  29. * Swig_set_fakeversion()
  30. *
  31. * Version string override
  32. * ----------------------------------------------------------------------------- */
  33. void Swig_set_fakeversion(const char *version) {
  34. fake_version = Swig_copy_string(version);
  35. }
  36. /* -----------------------------------------------------------------------------
  37. * Swig_package_version()
  38. *
  39. * Return the package string containing the version number
  40. * ----------------------------------------------------------------------------- */
  41. const char *Swig_package_version(void) {
  42. return fake_version ? fake_version : PACKAGE_VERSION;
  43. }
  44. /* -----------------------------------------------------------------------------
  45. * Swig_banner()
  46. *
  47. * Emits the SWIG identifying banner for the C/C++ wrapper file.
  48. * ----------------------------------------------------------------------------- */
  49. void Swig_banner(File *f) {
  50. Printf(f, "/* ----------------------------------------------------------------------------\n\
  51. * This file was automatically generated by SWIG (http://www.swig.org).\n\
  52. * Version %s\n\
  53. * \n\
  54. * This file is not intended to be easily readable and contains a number of \n\
  55. * coding conventions designed to improve portability and efficiency. Do not make\n\
  56. * changes to this file unless you know what you are doing--modify the SWIG \n\
  57. * interface file instead. \n", Swig_package_version());
  58. /* String too long for ISO compliance */
  59. Printf(f, " * ----------------------------------------------------------------------------- */\n\n");
  60. }
  61. /* -----------------------------------------------------------------------------
  62. * Swig_banner_target_lang()
  63. *
  64. * Emits a SWIG identifying banner in the target language
  65. * ----------------------------------------------------------------------------- */
  66. void Swig_banner_target_lang(File *f, const_String_or_char_ptr commentchar) {
  67. Printf(f, "%s This file was automatically generated by SWIG (http://www.swig.org).\n", commentchar);
  68. Printf(f, "%s Version %s\n", commentchar, Swig_package_version());
  69. Printf(f, "%s\n", commentchar);
  70. Printf(f, "%s Do not make changes to this file unless you know what you are doing--modify\n", commentchar);
  71. Printf(f, "%s the SWIG interface file instead.\n", commentchar);
  72. }
  73. /* -----------------------------------------------------------------------------
  74. * Swig_strip_c_comments()
  75. *
  76. * Return a new string with C comments stripped from the input string. Null is
  77. * returned if there aren't any.
  78. * ----------------------------------------------------------------------------- */
  79. String *Swig_strip_c_comments(const String *s) {
  80. const char *c = Char(s);
  81. const char *comment_begin = 0;
  82. const char *comment_end = 0;
  83. String *stripped = 0;
  84. while (*c) {
  85. if (!comment_begin && *c == '/') {
  86. ++c;
  87. if (!*c)
  88. break;
  89. if (*c == '*')
  90. comment_begin = c-1;
  91. } else if (comment_begin && !comment_end && *c == '*') {
  92. ++c;
  93. if (*c == '/')
  94. comment_end = c;
  95. break;
  96. }
  97. ++c;
  98. }
  99. if (comment_begin && comment_end) {
  100. int size = comment_begin - Char(s);
  101. String *stripmore = 0;
  102. stripped = NewStringWithSize(s, size);
  103. Printv(stripped, comment_end + 1, NIL);
  104. do {
  105. stripmore = Swig_strip_c_comments(stripped);
  106. if (stripmore) {
  107. Delete(stripped);
  108. stripped = stripmore;
  109. }
  110. } while (stripmore);
  111. }
  112. return stripped;
  113. }
  114. /* -----------------------------------------------------------------------------
  115. * Swig_filename_correct()
  116. *
  117. * Corrects filenames on non-unix systems
  118. * ----------------------------------------------------------------------------- */
  119. void Swig_filename_correct(String *filename) {
  120. (void)filename;
  121. #if defined(_WIN32) || defined(MACSWIG)
  122. /* accept Unix path separator on non-Unix systems */
  123. Replaceall(filename, "/", SWIG_FILE_DELIMITER);
  124. #endif
  125. #if defined(__CYGWIN__)
  126. /* accept Windows path separator in addition to Unix path separator */
  127. Replaceall(filename, "\\", SWIG_FILE_DELIMITER);
  128. #endif
  129. }
  130. /* -----------------------------------------------------------------------------
  131. * Swig_filename_escape()
  132. *
  133. * Escapes backslashes in filename - for Windows
  134. * ----------------------------------------------------------------------------- */
  135. String *Swig_filename_escape(String *filename) {
  136. String *adjusted_filename = Copy(filename);
  137. #if defined(_WIN32) /* Note not on Cygwin else filename is displayed with double '/' */
  138. Replaceall(adjusted_filename, "\\\\", "\\"); /* remove double '\' in case any already present */
  139. Replaceall(adjusted_filename, "\\", "\\\\");
  140. #endif
  141. return adjusted_filename;
  142. }
  143. /* -----------------------------------------------------------------------------
  144. * Swig_string_escape()
  145. *
  146. * Takes a string object and produces a string with escape codes added to it.
  147. * ----------------------------------------------------------------------------- */
  148. String *Swig_string_escape(String *s) {
  149. String *ns;
  150. int c;
  151. ns = NewStringEmpty();
  152. while ((c = Getc(s)) != EOF) {
  153. if (c == '\n') {
  154. Printf(ns, "\\n");
  155. } else if (c == '\r') {
  156. Printf(ns, "\\r");
  157. } else if (c == '\t') {
  158. Printf(ns, "\\t");
  159. } else if (c == '\\') {
  160. Printf(ns, "\\\\");
  161. } else if (c == '\'') {
  162. Printf(ns, "\\'");
  163. } else if (c == '\"') {
  164. Printf(ns, "\\\"");
  165. } else if (c == ' ') {
  166. Putc(c, ns);
  167. } else if (!isgraph(c)) {
  168. if (c < 0)
  169. c += UCHAR_MAX + 1;
  170. Printf(ns, "\\%o", c);
  171. } else {
  172. Putc(c, ns);
  173. }
  174. }
  175. return ns;
  176. }
  177. /* -----------------------------------------------------------------------------
  178. * Swig_string_upper()
  179. *
  180. * Takes a string object and returns a copy that is uppercase
  181. * ----------------------------------------------------------------------------- */
  182. String *Swig_string_upper(String *s) {
  183. String *ns;
  184. int c;
  185. ns = NewStringEmpty();
  186. Seek(s, 0, SEEK_SET);
  187. while ((c = Getc(s)) != EOF) {
  188. Putc(toupper(c), ns);
  189. }
  190. return ns;
  191. }
  192. /* -----------------------------------------------------------------------------
  193. * Swig_string_lower()
  194. *
  195. * Takes a string object and returns a copy that is lowercase
  196. * ----------------------------------------------------------------------------- */
  197. String *Swig_string_lower(String *s) {
  198. String *ns;
  199. int c;
  200. ns = NewStringEmpty();
  201. Seek(s, 0, SEEK_SET);
  202. while ((c = Getc(s)) != EOF) {
  203. Putc(tolower(c), ns);
  204. }
  205. return ns;
  206. }
  207. /* -----------------------------------------------------------------------------
  208. * Swig_string_title()
  209. *
  210. * Takes a string object and returns a copy that is lowercase with first letter
  211. * capitalized
  212. * ----------------------------------------------------------------------------- */
  213. String *Swig_string_title(String *s) {
  214. String *ns;
  215. int first = 1;
  216. int c;
  217. ns = NewStringEmpty();
  218. Seek(s, 0, SEEK_SET);
  219. while ((c = Getc(s)) != EOF) {
  220. Putc(first ? toupper(c) : tolower(c), ns);
  221. first = 0;
  222. }
  223. return ns;
  224. }
  225. /* -----------------------------------------------------------------------------
  226. * Swig_string_ccase()
  227. *
  228. * Takes a string object and returns a copy that is lowercase with the first
  229. * letter capitalized and the one following '_', which are removed.
  230. *
  231. * camel_case -> CamelCase
  232. * camelCase -> CamelCase
  233. * ----------------------------------------------------------------------------- */
  234. String *Swig_string_ccase(String *s) {
  235. String *ns;
  236. int first = 1;
  237. int c;
  238. ns = NewStringEmpty();
  239. Seek(s, 0, SEEK_SET);
  240. while ((c = Getc(s)) != EOF) {
  241. if (c == '_') {
  242. first = 1;
  243. continue;
  244. }
  245. Putc(first ? toupper(c) : c, ns);
  246. first = 0;
  247. }
  248. return ns;
  249. }
  250. /* -----------------------------------------------------------------------------
  251. * Swig_string_lccase()
  252. *
  253. * Takes a string object and returns a copy with the character after
  254. * each '_' capitalised, and the '_' removed. The first character is
  255. * also forced to lowercase.
  256. *
  257. * camel_case -> camelCase
  258. * CamelCase -> camelCase
  259. * ----------------------------------------------------------------------------- */
  260. String *Swig_string_lccase(String *s) {
  261. String *ns;
  262. int first = 1;
  263. int after_underscore = 0;
  264. int c;
  265. ns = NewStringEmpty();
  266. Seek(s, 0, SEEK_SET);
  267. while ((c = Getc(s)) != EOF) {
  268. if (c == '_') {
  269. after_underscore = 1;
  270. continue;
  271. }
  272. if (first) {
  273. Putc(tolower(c), ns);
  274. first = 0;
  275. } else {
  276. Putc(after_underscore ? toupper(c) : c, ns);
  277. }
  278. after_underscore = 0;
  279. }
  280. return ns;
  281. }
  282. /* -----------------------------------------------------------------------------
  283. * Swig_string_ucase()
  284. *
  285. * This is the reverse case of ccase, ie
  286. *
  287. * CamelCase -> camel_case
  288. * get2D -> get_2d
  289. * asFloat2 -> as_float2
  290. * ----------------------------------------------------------------------------- */
  291. String *Swig_string_ucase(String *s) {
  292. String *ns;
  293. int c;
  294. int lastC = 0;
  295. int nextC = 0;
  296. int underscore = 0;
  297. ns = NewStringEmpty();
  298. /* We insert a underscore when:
  299. 1. Lower case char followed by upper case char
  300. getFoo > get_foo; getFOo > get_foo; GETFOO > getfoo
  301. 2. Number proceded by char and not end of string
  302. get2D > get_2d; get22D > get_22d; GET2D > get_2d
  303. but:
  304. asFloat2 > as_float2
  305. */
  306. Seek(s, 0, SEEK_SET);
  307. while ((c = Getc(s)) != EOF) {
  308. nextC = Getc(s); Ungetc(nextC, s);
  309. if (isdigit(c) && isalpha(lastC) && nextC != EOF)
  310. underscore = 1;
  311. else if (isupper(c) && isalpha(lastC) && !isupper(lastC))
  312. underscore = 1;
  313. lastC = c;
  314. if (underscore) {
  315. Putc('_', ns);
  316. underscore = 0;
  317. }
  318. Putc(tolower(c), ns);
  319. }
  320. return ns;
  321. }
  322. /* -----------------------------------------------------------------------------
  323. * Swig_string_first_upper()
  324. *
  325. * Make the first character in the string uppercase, leave all the
  326. * rest the same. This is used by the Ruby module to provide backwards
  327. * compatibility with the old way of naming classes and constants. For
  328. * more info see the Ruby documentation.
  329. *
  330. * firstUpper -> FirstUpper
  331. * ----------------------------------------------------------------------------- */
  332. String *Swig_string_first_upper(String *s) {
  333. String *ns = NewStringEmpty();
  334. const char *cs = Char(s);
  335. if (cs && cs[0] != 0) {
  336. Putc(toupper((int)cs[0]), ns);
  337. Append(ns, cs + 1);
  338. }
  339. return ns;
  340. }
  341. /* -----------------------------------------------------------------------------
  342. * Swig_string_first_lower()
  343. *
  344. * Make the first character in the string lowercase, leave all the
  345. * rest the same. This is used by the Ruby module to provide backwards
  346. * compatibility with the old way of naming classes and constants. For
  347. * more info see the Ruby documentation.
  348. *
  349. * firstLower -> FirstLower
  350. * ----------------------------------------------------------------------------- */
  351. String *Swig_string_first_lower(String *s) {
  352. String *ns = NewStringEmpty();
  353. const char *cs = Char(s);
  354. if (cs && cs[0] != 0) {
  355. Putc(tolower((int)cs[0]), ns);
  356. Append(ns, cs + 1);
  357. }
  358. return ns;
  359. }
  360. /* -----------------------------------------------------------------------------
  361. * Swig_string_schemify()
  362. *
  363. * Replace underscores with dashes, to make identifiers look nice to Schemers.
  364. *
  365. * under_scores -> under-scores
  366. * ----------------------------------------------------------------------------- */
  367. String *Swig_string_schemify(String *s) {
  368. String *ns = NewString(s);
  369. Replaceall(ns, "_", "-");
  370. return ns;
  371. }
  372. /* -----------------------------------------------------------------------------
  373. * Swig_string_typecode()
  374. *
  375. * Takes a string with possible type-escapes in it and replaces them with
  376. * real C datatypes.
  377. * ----------------------------------------------------------------------------- */
  378. String *Swig_string_typecode(String *s) {
  379. String *ns;
  380. int c;
  381. String *tc;
  382. ns = NewStringEmpty();
  383. while ((c = Getc(s)) != EOF) {
  384. if (c == '`') {
  385. String *str = 0;
  386. tc = NewStringEmpty();
  387. while ((c = Getc(s)) != EOF) {
  388. if (c == '`')
  389. break;
  390. Putc(c, tc);
  391. }
  392. str = SwigType_str(tc, 0);
  393. Append(ns, str);
  394. Delete(str);
  395. } else {
  396. Putc(c, ns);
  397. if (c == '\'') {
  398. while ((c = Getc(s)) != EOF) {
  399. Putc(c, ns);
  400. if (c == '\'')
  401. break;
  402. if (c == '\\') {
  403. c = Getc(s);
  404. Putc(c, ns);
  405. }
  406. }
  407. } else if (c == '\"') {
  408. while ((c = Getc(s)) != EOF) {
  409. Putc(c, ns);
  410. if (c == '\"')
  411. break;
  412. if (c == '\\') {
  413. c = Getc(s);
  414. Putc(c, ns);
  415. }
  416. }
  417. }
  418. }
  419. }
  420. return ns;
  421. }
  422. /* -----------------------------------------------------------------------------
  423. * Swig_string_mangle()
  424. *
  425. * Take a string and mangle it by stripping all non-valid C identifier
  426. * characters.
  427. *
  428. * This routine skips unnecessary blank spaces, therefore mangling
  429. * 'char *' and 'char*', 'std::pair<int, int >' and
  430. * 'std::pair<int,int>', produce the same result.
  431. *
  432. * However, note that 'long long' and 'long_long' produce different
  433. * mangled strings.
  434. *
  435. * The mangling method still is not 'perfect', for example std::pair and
  436. * std_pair return the same mangling. This is just a little better
  437. * than before, but it seems to be enough for most of the purposes.
  438. *
  439. * Having a perfect mangling will break some examples and code which
  440. * assume, for example, that A::get_value will be mangled as
  441. * A_get_value.
  442. * ----------------------------------------------------------------------------- */
  443. String *Swig_string_mangle(const String *s) {
  444. #if 0
  445. /* old mangling, not suitable for using in macros */
  446. String *t = Copy(s);
  447. const char *c = Char(t);
  448. while (*c) {
  449. if (!isalnum(*c))
  450. *c = '_';
  451. c++;
  452. }
  453. return t;
  454. #else
  455. String *result = NewStringEmpty();
  456. int space = 0;
  457. int state = 0;
  458. const char *pc, *cb;
  459. String *b = Copy(s);
  460. if (SwigType_istemplate(b)) {
  461. String *st = Swig_symbol_template_deftype(b, 0);
  462. String *sq = Swig_symbol_type_qualify(st, 0);
  463. String *t = SwigType_namestr(sq);
  464. Delete(st);
  465. Delete(sq);
  466. Delete(b);
  467. b = t;
  468. }
  469. pc = cb = Char(b);
  470. while (*pc) {
  471. char c = *pc;
  472. if (isalnum((int) c) || (c == '_')) {
  473. state = 1;
  474. if (space && (space == state)) {
  475. Append(result, "_SS_");
  476. }
  477. space = 0;
  478. Printf(result, "%c", (int) c);
  479. } else {
  480. if (isspace((int) c)) {
  481. space = state;
  482. ++pc;
  483. continue;
  484. } else {
  485. state = 3;
  486. space = 0;
  487. }
  488. switch (c) {
  489. case '.':
  490. if ((cb != pc) && (*(pc - 1) == 'p')) {
  491. Append(result, "_");
  492. ++pc;
  493. continue;
  494. } else {
  495. c = 'f';
  496. }
  497. break;
  498. case ':':
  499. if (*(pc + 1) == ':') {
  500. Append(result, "_");
  501. ++pc;
  502. ++pc;
  503. continue;
  504. }
  505. break;
  506. case '*':
  507. c = 'm';
  508. break;
  509. case '&':
  510. c = 'A';
  511. break;
  512. case '<':
  513. c = 'l';
  514. break;
  515. case '>':
  516. c = 'g';
  517. break;
  518. case '=':
  519. c = 'e';
  520. break;
  521. case ',':
  522. c = 'c';
  523. break;
  524. case '(':
  525. c = 'p';
  526. break;
  527. case ')':
  528. c = 'P';
  529. break;
  530. case '[':
  531. c = 'b';
  532. break;
  533. case ']':
  534. c = 'B';
  535. break;
  536. case '^':
  537. c = 'x';
  538. break;
  539. case '|':
  540. c = 'o';
  541. break;
  542. case '~':
  543. c = 'n';
  544. break;
  545. case '!':
  546. c = 'N';
  547. break;
  548. case '%':
  549. c = 'M';
  550. break;
  551. case '?':
  552. c = 'q';
  553. break;
  554. case '+':
  555. c = 'a';
  556. break;
  557. case '-':
  558. c = 's';
  559. break;
  560. case '/':
  561. c = 'd';
  562. break;
  563. default:
  564. break;
  565. }
  566. if (isalpha((int) c)) {
  567. Printf(result, "_S%c_", (int) c);
  568. } else {
  569. Printf(result, "_S%02X_", (int) c);
  570. }
  571. }
  572. ++pc;
  573. }
  574. Delete(b);
  575. return result;
  576. #endif
  577. }
  578. String *Swig_string_emangle(String *s) {
  579. return Swig_string_mangle(s);
  580. }
  581. /* -----------------------------------------------------------------------------
  582. * Swig_scopename_prefix()
  583. *
  584. * Take a qualified name like "A::B::C" and return the scope name.
  585. * In this case, "A::B". Returns NULL if there is no base.
  586. * ----------------------------------------------------------------------------- */
  587. void Swig_scopename_split(const String *s, String **rprefix, String **rlast) {
  588. const char *tmp = Char(s);
  589. const char *c = tmp;
  590. const char *cc = c;
  591. char *co = 0;
  592. if (!strstr(c, "::")) {
  593. *rprefix = 0;
  594. *rlast = Copy(s);
  595. }
  596. co = strstr(cc, "operator ");
  597. if (co) {
  598. if (co == cc) {
  599. *rprefix = 0;
  600. *rlast = Copy(s);
  601. return;
  602. } else {
  603. *rprefix = NewStringWithSize(cc, co - cc - 2);
  604. *rlast = NewString(co);
  605. return;
  606. }
  607. }
  608. while (*c) {
  609. if ((*c == ':') && (*(c + 1) == ':')) {
  610. cc = c;
  611. c += 2;
  612. } else {
  613. if (*c == '<') {
  614. int level = 1;
  615. c++;
  616. while (*c && level) {
  617. if (*c == '<')
  618. level++;
  619. if (*c == '>')
  620. level--;
  621. c++;
  622. }
  623. } else {
  624. c++;
  625. }
  626. }
  627. }
  628. if (cc != tmp) {
  629. *rprefix = NewStringWithSize(tmp, cc - tmp);
  630. *rlast = NewString(cc + 2);
  631. return;
  632. } else {
  633. *rprefix = 0;
  634. *rlast = Copy(s);
  635. }
  636. }
  637. String *Swig_scopename_prefix(const String *s) {
  638. const char *tmp = Char(s);
  639. const char *c = tmp;
  640. const char *cc = c;
  641. char *co = 0;
  642. if (!strstr(c, "::"))
  643. return 0;
  644. co = strstr(cc, "operator ");
  645. if (co) {
  646. if (co == cc) {
  647. return 0;
  648. } else {
  649. String *prefix = NewStringWithSize(cc, co - cc - 2);
  650. return prefix;
  651. }
  652. }
  653. while (*c) {
  654. if ((*c == ':') && (*(c + 1) == ':')) {
  655. cc = c;
  656. c += 2;
  657. } else {
  658. if (*c == '<') {
  659. int level = 1;
  660. c++;
  661. while (*c && level) {
  662. if (*c == '<')
  663. level++;
  664. if (*c == '>')
  665. level--;
  666. c++;
  667. }
  668. } else {
  669. c++;
  670. }
  671. }
  672. }
  673. if (cc != tmp) {
  674. return NewStringWithSize(tmp, cc - tmp);
  675. } else {
  676. return 0;
  677. }
  678. }
  679. /* -----------------------------------------------------------------------------
  680. * Swig_scopename_last()
  681. *
  682. * Take a qualified name like "A::B::C" and returns the last. In this
  683. * case, "C".
  684. * ----------------------------------------------------------------------------- */
  685. String *Swig_scopename_last(const String *s) {
  686. const char *tmp = Char(s);
  687. const char *c = tmp;
  688. const char *cc = c;
  689. char *co = 0;
  690. if (!strstr(c, "::"))
  691. return NewString(s);
  692. co = strstr(cc, "operator ");
  693. if (co) {
  694. return NewString(co);
  695. }
  696. while (*c) {
  697. if ((*c == ':') && (*(c + 1) == ':')) {
  698. cc = c;
  699. c += 2;
  700. } else {
  701. if (*c == '<') {
  702. int level = 1;
  703. c++;
  704. while (*c && level) {
  705. if (*c == '<')
  706. level++;
  707. if (*c == '>')
  708. level--;
  709. c++;
  710. }
  711. } else {
  712. c++;
  713. }
  714. }
  715. }
  716. return NewString(cc + 2);
  717. }
  718. /* -----------------------------------------------------------------------------
  719. * Swig_scopename_first()
  720. *
  721. * Take a qualified name like "A::B::C" and returns the first scope name.
  722. * In this case, "A". Returns NULL if there is no base.
  723. * ----------------------------------------------------------------------------- */
  724. String *Swig_scopename_first(const String *s) {
  725. const char *tmp = Char(s);
  726. const char *c = tmp;
  727. const char *co = 0;
  728. if (!strstr(c, "::"))
  729. return 0;
  730. co = strstr(c, "operator ");
  731. if (co) {
  732. if (co == c) {
  733. return 0;
  734. }
  735. } else {
  736. co = c + Len(s);
  737. }
  738. while (*c && (c != co)) {
  739. if ((*c == ':') && (*(c + 1) == ':')) {
  740. break;
  741. } else {
  742. if (*c == '<') {
  743. int level = 1;
  744. c++;
  745. while (*c && level) {
  746. if (*c == '<')
  747. level++;
  748. if (*c == '>')
  749. level--;
  750. c++;
  751. }
  752. } else {
  753. c++;
  754. }
  755. }
  756. }
  757. if (*c && (c != tmp)) {
  758. return NewStringWithSize(tmp, c - tmp);
  759. } else {
  760. return 0;
  761. }
  762. }
  763. /* -----------------------------------------------------------------------------
  764. * Swig_scopename_suffix()
  765. *
  766. * Take a qualified name like "A::B::C" and returns the suffix.
  767. * In this case, "B::C". Returns NULL if there is no suffix.
  768. * ----------------------------------------------------------------------------- */
  769. String *Swig_scopename_suffix(const String *s) {
  770. const char *tmp = Char(s);
  771. const char *c = tmp;
  772. char *co = 0;
  773. if (!strstr(c, "::"))
  774. return 0;
  775. co = strstr(c, "operator ");
  776. if (co) {
  777. if (co == c)
  778. return 0;
  779. }
  780. while (*c) {
  781. if ((*c == ':') && (*(c + 1) == ':')) {
  782. break;
  783. } else {
  784. if (*c == '<') {
  785. int level = 1;
  786. c++;
  787. while (*c && level) {
  788. if (*c == '<')
  789. level++;
  790. if (*c == '>')
  791. level--;
  792. c++;
  793. }
  794. } else {
  795. c++;
  796. }
  797. }
  798. }
  799. if (*c && (c != tmp)) {
  800. return NewString(c + 2);
  801. } else {
  802. return 0;
  803. }
  804. }
  805. /* -----------------------------------------------------------------------------
  806. * Swig_scopename_check()
  807. *
  808. * Checks to see if a name is qualified with a scope name
  809. * ----------------------------------------------------------------------------- */
  810. int Swig_scopename_check(const String *s) {
  811. const char *c = Char(s);
  812. char *co = strstr(c, "operator ");
  813. if (co) {
  814. if (co == c)
  815. return 0;
  816. }
  817. if (!strstr(c, "::"))
  818. return 0;
  819. while (*c) {
  820. if ((*c == ':') && (*(c + 1) == ':')) {
  821. return 1;
  822. } else {
  823. if (*c == '<') {
  824. int level = 1;
  825. c++;
  826. while (*c && level) {
  827. if (*c == '<')
  828. level++;
  829. if (*c == '>')
  830. level--;
  831. c++;
  832. }
  833. } else {
  834. c++;
  835. }
  836. }
  837. }
  838. return 0;
  839. }
  840. /* -----------------------------------------------------------------------------
  841. * Swig_string_command()
  842. *
  843. * Executes a external command via popen with the string as a command
  844. * line parameter. For example:
  845. *
  846. * Printf(stderr,"%(command:sed 's/[a-z]/\U\\1/' <<<)s","hello") -> Hello
  847. * ----------------------------------------------------------------------------- */
  848. #if defined(HAVE_POPEN)
  849. # if defined(_MSC_VER)
  850. # define popen _popen
  851. # define pclose _pclose
  852. # else
  853. extern FILE *popen(const char *command, const char *type);
  854. extern int pclose(FILE *stream);
  855. # endif
  856. #else
  857. # if defined(_MSC_VER)
  858. # define HAVE_POPEN 1
  859. # define popen _popen
  860. # define pclose _pclose
  861. # endif
  862. #endif
  863. String *Swig_string_command(String *s) {
  864. String *res = NewStringEmpty();
  865. #if defined(HAVE_POPEN)
  866. if (Len(s)) {
  867. const char *command = Char(s);
  868. FILE *fp = popen(command, "r");
  869. if (fp) {
  870. char buffer[1025];
  871. while (fscanf(fp, "%1024s", buffer) != EOF) {
  872. Append(res, buffer);
  873. }
  874. pclose(fp);
  875. } else {
  876. Swig_error("SWIG", Getline(s), "Command encoder fails attempting '%s'.\n", s);
  877. exit(1);
  878. }
  879. }
  880. #endif
  881. return res;
  882. }
  883. /* -----------------------------------------------------------------------------
  884. * Swig_string_strip()
  885. *
  886. * Strip given prefix from identifiers
  887. *
  888. * Printf(stderr,"%(strip:[wx])s","wxHello") -> Hello
  889. * ----------------------------------------------------------------------------- */
  890. String *Swig_string_strip(String *s) {
  891. String *ns;
  892. if (!Len(s)) {
  893. ns = NewString(s);
  894. } else {
  895. const char *cs = Char(s);
  896. const char *ce = Strchr(cs, ']');
  897. if (*cs != '[' || ce == NULL) {
  898. ns = NewString(s);
  899. } else {
  900. String *fmt = NewStringf("%%.%ds", ce-cs-1);
  901. String *prefix = NewStringf(fmt, cs+1);
  902. if (0 == Strncmp(ce+1, prefix, Len(prefix))) {
  903. ns = NewString(ce+1+Len(prefix));
  904. } else {
  905. ns = NewString(ce+1);
  906. }
  907. }
  908. }
  909. return ns;
  910. }
  911. /* -----------------------------------------------------------------------------
  912. * Swig_string_rxspencer()
  913. *
  914. * Executes a regexp substitution via the RxSpencer library. For example:
  915. *
  916. * Printf(stderr,"gsl%(rxspencer:[GSL_.*_][@1])s","GSL_Hello_") -> gslHello
  917. * ----------------------------------------------------------------------------- */
  918. #if defined(HAVE_RXSPENCER)
  919. #include <sys/types.h>
  920. #include <rxspencer/regex.h>
  921. #define USE_RXSPENCER
  922. #endif
  923. const char *skip_delim(char pb, char pe, const char *ce) {
  924. int end = 0;
  925. int lb = 0;
  926. while (!end && *ce != '\0') {
  927. if (*ce == pb) {
  928. ++lb;
  929. }
  930. if (*ce == pe) {
  931. if (!lb) {
  932. end = 1;
  933. --ce;
  934. } else {
  935. --lb;
  936. }
  937. }
  938. ++ce;
  939. }
  940. return end ? ce : 0;
  941. }
  942. #if defined(USE_RXSPENCER)
  943. String *Swig_string_rxspencer(String *s) {
  944. String *res = 0;
  945. if (Len(s)) {
  946. const const char *cs = Char(s);
  947. const char *cb;
  948. const char *ce;
  949. if (*cs == '[') {
  950. int retval;
  951. regex_t compiled;
  952. cb = ++cs;
  953. ce = skip_delim('[', ']', cb);
  954. if (ce) {
  955. char bregexp[512];
  956. strncpy(bregexp, cb, ce - cb);
  957. bregexp[ce - cb] = '\0';
  958. ++ce;
  959. retval = regcomp(&compiled, bregexp, REG_EXTENDED);
  960. if (retval == 0) {
  961. cs = ce;
  962. if (*cs == '[') {
  963. cb = ++cs;
  964. ce = skip_delim('[', ']', cb);
  965. if (ce) {
  966. const char *cvalue = ce + 1;
  967. int nsub = (int) compiled.re_nsub + 1;
  968. regmatch_t *pmatch = (regmatch_t *) malloc(sizeof(regmatch_t) * (nsub));
  969. retval = regexec(&compiled, cvalue, nsub, pmatch, 0);
  970. if (retval != REG_NOMATCH) {
  971. char *spos = 0;
  972. res = NewStringWithSize(cb, ce - cb);
  973. spos = Strchr(res, '@');
  974. while (spos) {
  975. char cd = *(++spos);
  976. if (isdigit(cd)) {
  977. char arg[8];
  978. size_t len;
  979. int i = cd - '0';
  980. sprintf(arg, "@%d", i);
  981. if (i < nsub && (len = pmatch[i].rm_eo - pmatch[i].rm_so)) {
  982. char value[256];
  983. strncpy(value, cvalue + pmatch[i].rm_so, len);
  984. value[len] = 0;
  985. Replaceall(res, arg, value);
  986. } else {
  987. Replaceall(res, arg, "");
  988. }
  989. spos = Strchr(res, '@');
  990. } else if (cd == '@') {
  991. spos = strchr(spos + 1, '@');
  992. }
  993. }
  994. }
  995. free(pmatch);
  996. }
  997. }
  998. }
  999. regfree(&compiled);
  1000. }
  1001. }
  1002. }
  1003. if (!res)
  1004. res = NewStringEmpty();
  1005. return res;
  1006. }
  1007. #else
  1008. String *Swig_string_rxspencer(String *s) {
  1009. (void) s;
  1010. return NewStringEmpty();
  1011. }
  1012. #endif
  1013. /* -----------------------------------------------------------------------------
  1014. * Swig_init()
  1015. *
  1016. * Initialize the SWIG core
  1017. * ----------------------------------------------------------------------------- */
  1018. void Swig_init() {
  1019. /* Set some useful string encoding methods */
  1020. DohEncoding("escape", Swig_string_escape);
  1021. DohEncoding("upper", Swig_string_upper);
  1022. DohEncoding("lower", Swig_string_lower);
  1023. DohEncoding("title", Swig_string_title);
  1024. DohEncoding("ctitle", Swig_string_ccase);
  1025. DohEncoding("lctitle", Swig_string_lccase);
  1026. DohEncoding("utitle", Swig_string_ucase);
  1027. DohEncoding("typecode", Swig_string_typecode);
  1028. DohEncoding("mangle", Swig_string_emangle);
  1029. DohEncoding("command", Swig_string_command);
  1030. DohEncoding("rxspencer", Swig_string_rxspencer);
  1031. DohEncoding("schemify", Swig_string_schemify);
  1032. DohEncoding("strip", Swig_string_strip);
  1033. /* aliases for the case encoders */
  1034. DohEncoding("uppercase", Swig_string_upper);
  1035. DohEncoding("lowercase", Swig_string_lower);
  1036. DohEncoding("camelcase", Swig_string_ccase);
  1037. DohEncoding("lowercamelcase", Swig_string_lccase);
  1038. DohEncoding("undercase", Swig_string_ucase);
  1039. DohEncoding("firstuppercase", Swig_string_first_upper);
  1040. DohEncoding("firstlowercase", Swig_string_first_lower);
  1041. /* Initialize typemaps */
  1042. Swig_typemap_init();
  1043. /* Initialize symbol table */
  1044. Swig_symbol_init();
  1045. /* Initialize type system */
  1046. SwigType_typesystem_init();
  1047. /* Initialize template system */
  1048. SwigType_template_init();
  1049. }