PageRenderTime 62ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/tags/rel-1-3-30rc1-afterbeautify/SWIG/Source/Modules/guile.cxx

#
C++ | 1746 lines | 1347 code | 205 blank | 194 comment | 435 complexity | 7a37849db0ee08c9867fde9083be00e4 MD5 | raw file
Possible License(s): LGPL-2.1, Cube, GPL-3.0, 0BSD, GPL-2.0

Large files files are truncated, but you can click here to view the full file

  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. * guile.cxx
  6. *
  7. * Guile language module for SWIG.
  8. * ----------------------------------------------------------------------------- */
  9. char cvsroot_guile_cxx[] = "$Header$";
  10. #include "swigmod.h"
  11. #include <ctype.h>
  12. // Note string broken in half for compilers that can't handle long strings
  13. static const char *guile_usage = (char *) "\
  14. Guile Options (available with -guile)\n\
  15. -prefix <name> - Use <name> as prefix [default \"gswig_\"]\n\
  16. -package <name> - Set the path of the module to <name>\n\
  17. (default NULL)\n\
  18. -emitsetters - Emit procedures-with-setters for variables\n\
  19. and structure slots.\n\
  20. -onlysetters - Don't emit traditional getter and setter\n\
  21. procedures for structure slots,\n\
  22. only emit procedures-with-setters.\n\
  23. -procdoc <file> - Output procedure documentation to <file>\n\
  24. -procdocformat <format> - Output procedure documentation in <format>;\n\
  25. one of `guile-1.4', `plain', `texinfo'\n\
  26. -linkage <lstyle> - Use linkage protocol <lstyle> (default `simple')\n\
  27. Use `module' for native Guile module linking\n\
  28. (requires Guile >= 1.5.0). Use `passive' for\n\
  29. passive linking (no C-level module-handling code),\n\
  30. `ltdlmod' for Guile's old dynamic module\n\
  31. convention (Guile <= 1.4), or `hobbit' for hobbit\n\
  32. modules.\n\
  33. -scmstub - Output Scheme file with module declaration and\n\
  34. exports; only with `passive' and `simple' linkage\n\
  35. -gh - Use the gh_ Guile API. (Guile <= 1.8) \n\
  36. -scm - Use the scm Guile API. (Guile >= 1.6, default) \n\
  37. -proxy - Export GOOPS class definitions\n\
  38. -emitslotaccessors - Emit accessor methods for all GOOPS slots\n" "\
  39. -primsuffix <suffix> - Name appended to primitive module when exporting\n\
  40. GOOPS classes. (default = \"primitive\")\n\
  41. -goopsprefix <prefix> - Prepend <prefix> to all goops identifiers\n\
  42. -useclassprefix - Prepend the class name to all goops identifiers\n\
  43. -exportprimitive - Add the (export ...) code from scmstub into the\n\
  44. GOOPS file.\n";
  45. static File *f_runtime = 0;
  46. static File *f_header = 0;
  47. static File *f_wrappers = 0;
  48. static File *f_init = 0;
  49. static char *prefix = (char *) "gswig_";
  50. static char *module = 0;
  51. static char *package = 0;
  52. static enum {
  53. GUILE_LSTYLE_SIMPLE, // call `SWIG_init()'
  54. GUILE_LSTYLE_PASSIVE, // passive linking (no module code)
  55. GUILE_LSTYLE_MODULE, // native guile module linking (Guile >= 1.4.1)
  56. GUILE_LSTYLE_LTDLMOD_1_4, // old (Guile <= 1.4) dynamic module convention
  57. GUILE_LSTYLE_HOBBIT // use (hobbit4d link)
  58. } linkage = GUILE_LSTYLE_SIMPLE;
  59. static File *procdoc = 0;
  60. static bool scmstub = false;
  61. static String *scmtext;
  62. static bool goops = false;
  63. static String *goopstext;
  64. static String *goopscode;
  65. static String *goopsexport;
  66. static enum {
  67. GUILE_1_4,
  68. PLAIN,
  69. TEXINFO
  70. } docformat = GUILE_1_4;
  71. static int emit_setters = 0;
  72. static int only_setters = 0;
  73. static int emit_slot_accessors = 0;
  74. static int struct_member = 0;
  75. static String *beforereturn = 0;
  76. static String *return_nothing_doc = 0;
  77. static String *return_one_doc = 0;
  78. static String *return_multi_doc = 0;
  79. static String *exported_symbols = 0;
  80. static int use_scm_interface = 1;
  81. static int exporting_destructor = 0;
  82. static String *swigtype_ptr = 0;
  83. /* GOOPS stuff */
  84. static String *primsuffix = 0;
  85. static String *class_name = 0;
  86. static String *short_class_name = 0;
  87. static String *goops_class_methods;
  88. static int in_class = 0;
  89. static int have_constructor = 0;
  90. static int useclassprefix = 0; // -useclassprefix argument
  91. static String *goopsprefix = 0; // -goopsprefix argument
  92. static int primRenamer = 0; // if (use-modules ((...) :renamer ...) is exported to GOOPS file
  93. static int exportprimitive = 0; // -exportprimitive argument
  94. static String *memberfunction_name = 0;
  95. extern "C" {
  96. static int has_classname(Node *class_node) {
  97. return Getattr(class_node, "guile:goopsclassname") != NULL;
  98. }
  99. }
  100. class GUILE:public Language {
  101. public:
  102. /* ------------------------------------------------------------
  103. * main()
  104. * ------------------------------------------------------------ */
  105. virtual void main(int argc, char *argv[]) {
  106. int i, orig_len;
  107. SWIG_library_directory("guile");
  108. SWIG_typemap_lang("guile");
  109. // Look for certain command line options
  110. for (i = 1; i < argc; i++) {
  111. if (argv[i]) {
  112. if (strcmp(argv[i], "-help") == 0) {
  113. fputs(guile_usage, stdout);
  114. SWIG_exit(EXIT_SUCCESS);
  115. } else if (strcmp(argv[i], "-prefix") == 0) {
  116. if (argv[i + 1]) {
  117. prefix = new char[strlen(argv[i + 1]) + 2];
  118. strcpy(prefix, argv[i + 1]);
  119. Swig_mark_arg(i);
  120. Swig_mark_arg(i + 1);
  121. i++;
  122. } else {
  123. Swig_arg_error();
  124. }
  125. } else if (strcmp(argv[i], "-package") == 0) {
  126. if (argv[i + 1]) {
  127. package = new char[strlen(argv[i + 1]) + 2];
  128. strcpy(package, argv[i + 1]);
  129. Swig_mark_arg(i);
  130. Swig_mark_arg(i + 1);
  131. i++;
  132. } else {
  133. Swig_arg_error();
  134. }
  135. } else if (strcmp(argv[i], "-Linkage") == 0 || strcmp(argv[i], "-linkage") == 0) {
  136. if (argv[i + 1]) {
  137. if (0 == strcmp(argv[i + 1], "ltdlmod"))
  138. linkage = GUILE_LSTYLE_LTDLMOD_1_4;
  139. else if (0 == strcmp(argv[i + 1], "hobbit"))
  140. linkage = GUILE_LSTYLE_HOBBIT;
  141. else if (0 == strcmp(argv[i + 1], "simple"))
  142. linkage = GUILE_LSTYLE_SIMPLE;
  143. else if (0 == strcmp(argv[i + 1], "passive"))
  144. linkage = GUILE_LSTYLE_PASSIVE;
  145. else if (0 == strcmp(argv[i + 1], "module"))
  146. linkage = GUILE_LSTYLE_MODULE;
  147. else
  148. Swig_arg_error();
  149. Swig_mark_arg(i);
  150. Swig_mark_arg(i + 1);
  151. i++;
  152. } else {
  153. Swig_arg_error();
  154. }
  155. } else if (strcmp(argv[i], "-procdoc") == 0) {
  156. if (argv[i + 1]) {
  157. procdoc = NewFile(argv[i + 1], (char *) "w");
  158. if (!procdoc) {
  159. FileErrorDisplay(argv[i + 1]);
  160. SWIG_exit(EXIT_FAILURE);
  161. }
  162. Swig_mark_arg(i);
  163. Swig_mark_arg(i + 1);
  164. i++;
  165. } else {
  166. Swig_arg_error();
  167. }
  168. } else if (strcmp(argv[i], "-procdocformat") == 0) {
  169. if (strcmp(argv[i + 1], "guile-1.4") == 0)
  170. docformat = GUILE_1_4;
  171. else if (strcmp(argv[i + 1], "plain") == 0)
  172. docformat = PLAIN;
  173. else if (strcmp(argv[i + 1], "texinfo") == 0)
  174. docformat = TEXINFO;
  175. else
  176. Swig_arg_error();
  177. Swig_mark_arg(i);
  178. Swig_mark_arg(i + 1);
  179. i++;
  180. } else if (strcmp(argv[i], "-emit-setters") == 0 || strcmp(argv[i], "-emitsetters") == 0) {
  181. emit_setters = 1;
  182. Swig_mark_arg(i);
  183. } else if (strcmp(argv[i], "-only-setters") == 0 || strcmp(argv[i], "-onlysetters") == 0) {
  184. emit_setters = 1;
  185. only_setters = 1;
  186. Swig_mark_arg(i);
  187. } else if (strcmp(argv[i], "-emit-slot-accessors") == 0 || strcmp(argv[i], "-emitslotaccessors") == 0) {
  188. emit_slot_accessors = 1;
  189. Swig_mark_arg(i);
  190. } else if (strcmp(argv[i], "-scmstub") == 0) {
  191. scmstub = true;
  192. Swig_mark_arg(i);
  193. } else if ((strcmp(argv[i], "-shadow") == 0) || ((strcmp(argv[i], "-proxy") == 0))) {
  194. goops = true;
  195. Swig_mark_arg(i);
  196. } else if (strcmp(argv[i], "-gh") == 0) {
  197. use_scm_interface = 0;
  198. Swig_mark_arg(i);
  199. } else if (strcmp(argv[i], "-scm") == 0) {
  200. use_scm_interface = 1;
  201. Swig_mark_arg(i);
  202. } else if (strcmp(argv[i], "-primsuffix") == 0) {
  203. if (argv[i + 1]) {
  204. primsuffix = NewString(argv[i + 1]);
  205. Swig_mark_arg(i);
  206. Swig_mark_arg(i + 1);
  207. i++;
  208. } else {
  209. Swig_arg_error();
  210. }
  211. } else if (strcmp(argv[i], "-goopsprefix") == 0) {
  212. if (argv[i + 1]) {
  213. goopsprefix = NewString(argv[i + 1]);
  214. Swig_mark_arg(i);
  215. Swig_mark_arg(i + 1);
  216. i++;
  217. } else {
  218. Swig_arg_error();
  219. }
  220. } else if (strcmp(argv[i], "-useclassprefix") == 0) {
  221. useclassprefix = 1;
  222. Swig_mark_arg(i);
  223. } else if (strcmp(argv[i], "-exportprimitive") == 0) {
  224. exportprimitive = 1;
  225. // should use Swig_warning() here?
  226. Swig_mark_arg(i);
  227. }
  228. }
  229. }
  230. // set default value for primsuffix
  231. if (primsuffix == NULL)
  232. primsuffix = NewString("primitive");
  233. //goops support can only be enabled if passive or module linkage is used
  234. if (goops) {
  235. if (linkage != GUILE_LSTYLE_PASSIVE && linkage != GUILE_LSTYLE_MODULE) {
  236. Printf(stderr, "guile: GOOPS support requires passive or module linkage\n");
  237. exit(1);
  238. }
  239. }
  240. if (goops) {
  241. // -proxy implies -emit-setters
  242. emit_setters = 1;
  243. }
  244. if ((linkage == GUILE_LSTYLE_PASSIVE && scmstub) || linkage == GUILE_LSTYLE_MODULE)
  245. primRenamer = 1;
  246. if (exportprimitive && primRenamer) {
  247. // should use Swig_warning() ?
  248. Printf(stderr, "guile: Warning: -exportprimitive only makes sense with passive linkage without a scmstub.\n");
  249. }
  250. // Make sure `prefix' ends in an underscore
  251. orig_len = strlen(prefix);
  252. if (prefix[orig_len - 1] != '_') {
  253. prefix[1 + orig_len] = 0;
  254. prefix[orig_len] = '_';
  255. }
  256. /* Add a symbol for this module */
  257. Preprocessor_define("SWIGGUILE 1", 0);
  258. /* Read in default typemaps */
  259. if (use_scm_interface)
  260. SWIG_config_file("guile_scm.swg");
  261. else
  262. SWIG_config_file("guile_gh.swg");
  263. allow_overloading();
  264. }
  265. /* ------------------------------------------------------------
  266. * top()
  267. * ------------------------------------------------------------ */
  268. virtual int top(Node *n) {
  269. /* Initialize all of the output files */
  270. String *outfile = Getattr(n, "outfile");
  271. f_runtime = NewFile(outfile, "w");
  272. if (!f_runtime) {
  273. FileErrorDisplay(outfile);
  274. SWIG_exit(EXIT_FAILURE);
  275. }
  276. f_init = NewString("");
  277. f_header = NewString("");
  278. f_wrappers = NewString("");
  279. /* Register file targets with the SWIG file handler */
  280. Swig_register_filebyname("header", f_header);
  281. Swig_register_filebyname("wrapper", f_wrappers);
  282. Swig_register_filebyname("runtime", f_runtime);
  283. Swig_register_filebyname("init", f_init);
  284. scmtext = NewString("");
  285. Swig_register_filebyname("scheme", scmtext);
  286. exported_symbols = NewString("");
  287. goopstext = NewString("");
  288. Swig_register_filebyname("goops", goopstext);
  289. goopscode = NewString("");
  290. goopsexport = NewString("");
  291. Printf(f_runtime, "/* -*- buffer-read-only: t -*- vi: set ro: */\n");
  292. Swig_banner(f_runtime);
  293. Printf(f_runtime, "/* Implementation : GUILE */\n\n");
  294. if (!use_scm_interface) {
  295. if (SwigRuntime == 1)
  296. Printf(f_runtime, "#define SWIG_GLOBAL\n");
  297. if (SwigRuntime == 2)
  298. Printf(f_runtime, "#define SWIG_NOINCLUDE\n");
  299. }
  300. /* Write out directives and declarations */
  301. module = Swig_copy_string(Char(Getattr(n, "name")));
  302. switch (linkage) {
  303. case GUILE_LSTYLE_SIMPLE:
  304. /* Simple linkage; we have to export the SWIG_init function. The user can
  305. rename the function by a #define. */
  306. Printf(f_runtime, "#define SWIG_GUILE_INIT_STATIC extern\n");
  307. break;
  308. default:
  309. /* Other linkage; we make the SWIG_init function static */
  310. Printf(f_runtime, "#define SWIG_GUILE_INIT_STATIC static\n");
  311. break;
  312. }
  313. if (CPlusPlus) {
  314. Printf(f_runtime, "extern \"C\" {\n\n");
  315. }
  316. Printf(f_runtime, "SWIG_GUILE_INIT_STATIC void\nSWIG_init (void);\n");
  317. if (CPlusPlus) {
  318. Printf(f_runtime, "\n}\n");
  319. }
  320. Language::top(n);
  321. /* Close module */
  322. Printf(f_wrappers, "#ifdef __cplusplus\nextern \"C\" {\n#endif\n");
  323. SwigType_emit_type_table(f_runtime, f_wrappers);
  324. Printf(f_init, "}\n\n");
  325. Printf(f_init, "#ifdef __cplusplus\n}\n#endif\n");
  326. String *module_name = NewString("");
  327. if (!module)
  328. Printv(module_name, "swig", NIL);
  329. else {
  330. if (package)
  331. Printf(module_name, "%s/%s", package, module);
  332. else
  333. Printv(module_name, module, NIL);
  334. }
  335. emit_linkage(module_name);
  336. Delete(module_name);
  337. if (procdoc) {
  338. Delete(procdoc);
  339. procdoc = NULL;
  340. }
  341. Delete(goopscode);
  342. Delete(goopsexport);
  343. Delete(goopstext);
  344. /* Close all of the files */
  345. Dump(f_header, f_runtime);
  346. Dump(f_wrappers, f_runtime);
  347. Wrapper_pretty_print(f_init, f_runtime);
  348. Delete(f_header);
  349. Delete(f_wrappers);
  350. Delete(f_init);
  351. Close(f_runtime);
  352. Delete(f_runtime);
  353. return SWIG_OK;
  354. }
  355. void emit_linkage(String *module_name) {
  356. String *module_func = NewString("");
  357. if (CPlusPlus) {
  358. Printf(f_init, "extern \"C\" {\n\n");
  359. }
  360. Printv(module_func, module_name, NIL);
  361. Replaceall(module_func, "-", "_");
  362. switch (linkage) {
  363. case GUILE_LSTYLE_SIMPLE:
  364. Printf(f_init, "\n/* Linkage: simple */\n");
  365. break;
  366. case GUILE_LSTYLE_PASSIVE:
  367. Printf(f_init, "\n/* Linkage: passive */\n");
  368. Replaceall(module_func, "/", "_");
  369. Insert(module_func, 0, "scm_init_");
  370. Append(module_func, "_module");
  371. Printf(f_init, "SCM\n%s (void)\n{\n", module_func);
  372. Printf(f_init, " SWIG_init();\n");
  373. Printf(f_init, " return SCM_UNSPECIFIED;\n");
  374. Printf(f_init, "}\n");
  375. break;
  376. case GUILE_LSTYLE_LTDLMOD_1_4:
  377. Printf(f_init, "\n/* Linkage: ltdlmod */\n");
  378. Replaceall(module_func, "/", "_");
  379. Insert(module_func, 0, "scm_init_");
  380. Append(module_func, "_module");
  381. Printf(f_init, "SCM\n%s (void)\n{\n", module_func);
  382. {
  383. String *mod = NewString(module_name);
  384. Replaceall(mod, "/", " ");
  385. Printf(f_init, " scm_register_module_xxx (\"%s\", (void *) SWIG_init);\n", mod);
  386. Printf(f_init, " return SCM_UNSPECIFIED;\n");
  387. Delete(mod);
  388. }
  389. Printf(f_init, "}\n");
  390. break;
  391. case GUILE_LSTYLE_MODULE:
  392. Printf(f_init, "\n/* Linkage: module */\n");
  393. Replaceall(module_func, "/", "_");
  394. Insert(module_func, 0, "scm_init_");
  395. Append(module_func, "_module");
  396. Printf(f_init, "static void SWIG_init_helper(void *data)\n");
  397. Printf(f_init, "{\n SWIG_init();\n");
  398. if (Len(exported_symbols) > 0)
  399. Printf(f_init, " scm_c_export(%sNULL);", exported_symbols);
  400. Printf(f_init, "\n}\n\n");
  401. Printf(f_init, "SCM\n%s (void)\n{\n", module_func);
  402. {
  403. String *mod = NewString(module_name);
  404. if (goops)
  405. Printv(mod, "-", primsuffix, NIL);
  406. Replaceall(mod, "/", " ");
  407. Printf(f_init, " scm_c_define_module(\"%s\",\n", mod);
  408. Printf(f_init, " SWIG_init_helper, NULL);\n");
  409. Printf(f_init, " return SCM_UNSPECIFIED;\n");
  410. Delete(mod);
  411. }
  412. Printf(f_init, "}\n");
  413. break;
  414. case GUILE_LSTYLE_HOBBIT:
  415. Printf(f_init, "\n/* Linkage: hobbit */\n");
  416. Replaceall(module_func, "/", "_slash_");
  417. Insert(module_func, 0, "scm_init_");
  418. Printf(f_init, "SCM\n%s (void)\n{\n", module_func);
  419. {
  420. String *mod = NewString(module_name);
  421. Replaceall(mod, "/", " ");
  422. Printf(f_init, " scm_register_module_xxx (\"%s\", (void *) SWIG_init);\n", mod);
  423. Printf(f_init, " return SCM_UNSPECIFIED;\n");
  424. Delete(mod);
  425. }
  426. Printf(f_init, "}\n");
  427. break;
  428. default:
  429. abort(); // for now
  430. }
  431. if (scmstub) {
  432. /* Emit Scheme stub if requested */
  433. String *primitive_name = NewString(module_name);
  434. if (goops)
  435. Printv(primitive_name, "-", primsuffix, NIL);
  436. String *mod = NewString(primitive_name);
  437. Replaceall(mod, "/", " ");
  438. String *fname = NewStringf("%s%s.scm",
  439. SWIG_output_directory(),
  440. primitive_name);
  441. Delete(primitive_name);
  442. File *scmstubfile = NewFile(fname, (char *) "w");
  443. if (!scmstubfile) {
  444. FileErrorDisplay(fname);
  445. SWIG_exit(EXIT_FAILURE);
  446. }
  447. Delete(fname);
  448. Printf(scmstubfile, ";;; -*- buffer-read-only: t -*- vi: set ro: */\n");
  449. Printf(scmstubfile, ";;; Automatically generated by SWIG; do not edit.\n\n");
  450. if (linkage == GUILE_LSTYLE_SIMPLE || linkage == GUILE_LSTYLE_PASSIVE)
  451. Printf(scmstubfile, "(define-module (%s))\n\n", mod);
  452. Delete(mod);
  453. Printf(scmstubfile, "%s", scmtext);
  454. if ((linkage == GUILE_LSTYLE_SIMPLE || linkage == GUILE_LSTYLE_PASSIVE)
  455. && Len(exported_symbols) > 0) {
  456. String *ex = NewString(exported_symbols);
  457. Replaceall(ex, ", ", "\n ");
  458. Replaceall(ex, "\"", "");
  459. Chop(ex);
  460. Printf(scmstubfile, "\n(export %s)\n", ex);
  461. Delete(ex);
  462. }
  463. Delete(scmstubfile);
  464. }
  465. if (goops) {
  466. String *mod = NewString(module_name);
  467. Replaceall(mod, "/", " ");
  468. String *fname = NewStringf("%s%s.scm", SWIG_output_directory(),
  469. module_name);
  470. File *goopsfile = NewFile(fname, (char *) "w");
  471. if (!goopsfile) {
  472. FileErrorDisplay(fname);
  473. SWIG_exit(EXIT_FAILURE);
  474. }
  475. Delete(fname);
  476. Printf(goopsfile, ";;; -*- buffer-read-only: t -*- vi: set ro: */\n");
  477. Printf(goopsfile, ";;; Automatically generated by SWIG; do not edit.\n\n");
  478. Printf(goopsfile, "(define-module (%s))\n", mod);
  479. Printf(goopsfile, "%s\n", goopstext);
  480. Printf(goopsfile, "(use-modules (oop goops) (Swig common))\n");
  481. if (primRenamer) {
  482. Printf(goopsfile, "(use-modules ((%s-%s) :renamer (symbol-prefix-proc 'primitive:)))\n", mod, primsuffix);
  483. }
  484. Printf(goopsfile, "%s\n(export %s)", goopscode, goopsexport);
  485. if (exportprimitive) {
  486. String *ex = NewString(exported_symbols);
  487. Replaceall(ex, ", ", "\n ");
  488. Replaceall(ex, "\"", "");
  489. Chop(ex);
  490. Printf(goopsfile, "\n(export %s)", ex);
  491. Delete(ex);
  492. }
  493. Delete(mod);
  494. Delete(goopsfile);
  495. }
  496. Delete(module_func);
  497. if (CPlusPlus) {
  498. Printf(f_init, "\n}\n");
  499. }
  500. }
  501. /* Return true iff T is a pointer type */
  502. int is_a_pointer(SwigType *t) {
  503. return SwigType_ispointer(SwigType_typedef_resolve_all(t));
  504. }
  505. /* Report an error handling the given type. */
  506. void throw_unhandled_guile_type_error(SwigType *d) {
  507. Swig_warning(WARN_TYPEMAP_UNDEF, input_file, line_number, "Unable to handle type %s.\n", SwigType_str(d, 0));
  508. }
  509. /* Write out procedure documentation */
  510. void write_doc(const String *proc_name, const String *signature, const String *doc, const String *signature2 = NULL) {
  511. switch (docformat) {
  512. case GUILE_1_4:
  513. Printv(procdoc, "\f\n", NIL);
  514. Printv(procdoc, "(", signature, ")\n", NIL);
  515. if (signature2)
  516. Printv(procdoc, "(", signature2, ")\n", NIL);
  517. Printv(procdoc, doc, "\n", NIL);
  518. break;
  519. case PLAIN:
  520. Printv(procdoc, "\f", proc_name, "\n\n", NIL);
  521. Printv(procdoc, "(", signature, ")\n", NIL);
  522. if (signature2)
  523. Printv(procdoc, "(", signature2, ")\n", NIL);
  524. Printv(procdoc, doc, "\n\n", NIL);
  525. break;
  526. case TEXINFO:
  527. Printv(procdoc, "\f", proc_name, "\n", NIL);
  528. Printv(procdoc, "@deffn primitive ", signature, "\n", NIL);
  529. if (signature2)
  530. Printv(procdoc, "@deffnx primitive ", signature2, "\n", NIL);
  531. Printv(procdoc, doc, "\n", NIL);
  532. Printv(procdoc, "@end deffn\n\n", NIL);
  533. break;
  534. }
  535. }
  536. /* returns false if the typemap is an empty string */
  537. bool handle_documentation_typemap(String *output,
  538. const String *maybe_delimiter, Parm *p, const String *typemap, const String *default_doc, const String *name = NULL) {
  539. String *tmp = NewString("");
  540. String *tm;
  541. if (!(tm = Getattr(p, typemap))) {
  542. Printf(tmp, "%s", default_doc);
  543. tm = tmp;
  544. }
  545. bool result = (Len(tm) > 0);
  546. if (maybe_delimiter && Len(output) > 0 && Len(tm) > 0) {
  547. Printv(output, maybe_delimiter, NIL);
  548. }
  549. const String *pn = (name == NULL) ? (const String *) Getattr(p, "name") : name;
  550. String *pt = Getattr(p, "type");
  551. Replaceall(tm, "$name", pn); // legacy for $parmname
  552. Replaceall(tm, "$type", SwigType_str(pt, 0));
  553. /* $NAME is like $name, but marked-up as a variable. */
  554. String *ARGNAME = NewString("");
  555. if (docformat == TEXINFO)
  556. Printf(ARGNAME, "@var{%s}", pn);
  557. else
  558. Printf(ARGNAME, "%(upper)s", pn);
  559. Replaceall(tm, "$NAME", ARGNAME);
  560. Replaceall(tm, "$PARMNAME", ARGNAME);
  561. Printv(output, tm, NIL);
  562. Delete(tmp);
  563. return result;
  564. }
  565. /* ------------------------------------------------------------
  566. * functionWrapper()
  567. * Create a function declaration and register it with the interpreter.
  568. * ------------------------------------------------------------ */
  569. virtual int functionWrapper(Node *n) {
  570. String *iname = Getattr(n, "sym:name");
  571. SwigType *d = Getattr(n, "type");
  572. ParmList *l = Getattr(n, "parms");
  573. Parm *p;
  574. String *proc_name = 0;
  575. char source[256];
  576. Wrapper *f = NewWrapper();;
  577. String *cleanup = NewString("");
  578. String *outarg = NewString("");
  579. String *signature = NewString("");
  580. String *doc_body = NewString("");
  581. String *returns = NewString("");
  582. String *method_signature = NewString("");
  583. String *primitive_args = NewString("");
  584. Hash *scheme_arg_names = NewHash();
  585. int num_results = 1;
  586. String *tmp = NewString("");
  587. String *tm;
  588. int i;
  589. int numargs = 0;
  590. int numreq = 0;
  591. String *overname = 0;
  592. int args_passed_as_array = 0;
  593. int scheme_argnum = 0;
  594. bool any_specialized_arg = false;
  595. // Make a wrapper name for this
  596. String *wname = Swig_name_wrapper(iname);
  597. if (Getattr(n, "sym:overloaded")) {
  598. overname = Getattr(n, "sym:overname");
  599. args_passed_as_array = 1;
  600. } else {
  601. if (!addSymbol(iname, n))
  602. return SWIG_ERROR;
  603. }
  604. if (overname) {
  605. Append(wname, overname);
  606. }
  607. Setattr(n, "wrap:name", wname);
  608. // Build the name for scheme.
  609. proc_name = NewString(iname);
  610. Replaceall(proc_name, "_", "-");
  611. /* Emit locals etc. into f->code; figure out which args to ignore */
  612. emit_args(d, l, f);
  613. /* Attach the standard typemaps */
  614. emit_attach_parmmaps(l, f);
  615. Setattr(n, "wrap:parms", l);
  616. /* Get number of required and total arguments */
  617. numargs = emit_num_arguments(l);
  618. numreq = emit_num_required(l);
  619. /* Declare return variable */
  620. Wrapper_add_local(f, "gswig_result", "SCM gswig_result");
  621. Wrapper_add_local(f, "gswig_list_p", "SWIGUNUSED int gswig_list_p = 0");
  622. /* Get the output typemap so we can start generating documentation. Don't
  623. worry, the returned string is saved as 'tmap:out' */
  624. Swig_typemap_lookup_new("out", n, "result", 0);
  625. if ((tm = Getattr(n, "tmap:out:doc"))) {
  626. Printv(returns, tm, NIL);
  627. if (Len(tm) > 0)
  628. num_results = 1;
  629. else
  630. num_results = 0;
  631. } else {
  632. String *s = SwigType_str(d, 0);
  633. Chop(s);
  634. Printf(returns, "<%s>", s);
  635. Delete(s);
  636. num_results = 1;
  637. }
  638. /* Open prototype and signature */
  639. Printv(f->def, "static SCM\n", wname, " (", NIL);
  640. if (args_passed_as_array) {
  641. Printv(f->def, "int argc, SCM *argv", NIL);
  642. }
  643. Printv(signature, proc_name, NIL);
  644. /* Now write code to extract the parameters */
  645. for (i = 0, p = l; i < numargs; i++) {
  646. while (checkAttribute(p, "tmap:in:numinputs", "0")) {
  647. p = Getattr(p, "tmap:in:next");
  648. }
  649. SwigType *pt = Getattr(p, "type");
  650. int opt_p = (i >= numreq);
  651. // Produce names of source and target
  652. if (args_passed_as_array)
  653. sprintf(source, "argv[%d]", i);
  654. else
  655. sprintf(source, "s_%d", i);
  656. String *target = Getattr(p, "lname");
  657. if (!args_passed_as_array) {
  658. if (i != 0)
  659. Printf(f->def, ", ");
  660. Printf(f->def, "SCM s_%d", i);
  661. }
  662. if (opt_p) {
  663. Printf(f->code, " if (%s != SCM_UNDEFINED) {\n", source);
  664. }
  665. if ((tm = Getattr(p, "tmap:in"))) {
  666. Replaceall(tm, "$source", source);
  667. Replaceall(tm, "$target", target);
  668. Replaceall(tm, "$input", source);
  669. Setattr(p, "emit:input", source);
  670. Printv(f->code, tm, "\n", NIL);
  671. SwigType *pb = SwigType_typedef_resolve_all(SwigType_base(pt));
  672. SwigType *pn = Getattr(p, "name");
  673. String *argname;
  674. scheme_argnum++;
  675. if (pn && !Getattr(scheme_arg_names, pn))
  676. argname = pn;
  677. else {
  678. /* Anonymous arg or re-used argument name -- choose a name that cannot clash */
  679. argname = NewStringf("%%arg%d", scheme_argnum);
  680. }
  681. if (procdoc) {
  682. if (i == numreq) {
  683. /* First optional argument */
  684. Printf(signature, " #:optional");
  685. }
  686. /* Add to signature (arglist) */
  687. handle_documentation_typemap(signature, " ", p, "tmap:in:arglist", "$name", argname);
  688. /* Document the type of the arg in the documentation body */
  689. handle_documentation_typemap(doc_body, ", ", p, "tmap:in:doc", "$NAME is of type <$type>", argname);
  690. }
  691. if (goops) {
  692. if (i < numreq) {
  693. if (strcmp("void", Char(pt)) != 0) {
  694. Node *class_node = Swig_symbol_clookup_check(pb, Getattr(n, "sym:symtab"),
  695. has_classname);
  696. String *goopsclassname = (class_node == NULL) ? NULL : Getattr(class_node, "guile:goopsclassname");
  697. /* do input conversion */
  698. if (goopsclassname) {
  699. Printv(method_signature, " (", argname, " ", goopsclassname, ")", NIL);
  700. any_specialized_arg = true;
  701. } else {
  702. Printv(method_signature, " ", argname, NIL);
  703. }
  704. Printv(primitive_args, " ", argname, NIL);
  705. Setattr(scheme_arg_names, argname, p);
  706. }
  707. }
  708. }
  709. if (!pn) {
  710. Delete(argname);
  711. }
  712. p = Getattr(p, "tmap:in:next");
  713. } else {
  714. throw_unhandled_guile_type_error(pt);
  715. p = nextSibling(p);
  716. }
  717. if (opt_p)
  718. Printf(f->code, " }\n");
  719. }
  720. if (Len(doc_body) > 0)
  721. Printf(doc_body, ".\n");
  722. /* Insert constraint checking code */
  723. for (p = l; p;) {
  724. if ((tm = Getattr(p, "tmap:check"))) {
  725. Replaceall(tm, "$target", Getattr(p, "lname"));
  726. Printv(f->code, tm, "\n", NIL);
  727. p = Getattr(p, "tmap:check:next");
  728. } else {
  729. p = nextSibling(p);
  730. }
  731. }
  732. /* Pass output arguments back to the caller. */
  733. /* Insert argument output code */
  734. for (p = l; p;) {
  735. if ((tm = Getattr(p, "tmap:argout"))) {
  736. Replaceall(tm, "$source", Getattr(p, "lname"));
  737. Replaceall(tm, "$target", Getattr(p, "lname"));
  738. Replaceall(tm, "$arg", Getattr(p, "emit:input"));
  739. Replaceall(tm, "$input", Getattr(p, "emit:input"));
  740. Printv(outarg, tm, "\n", NIL);
  741. if (procdoc) {
  742. if (handle_documentation_typemap(returns, ", ", p, "tmap:argout:doc", "$NAME (of type $type)")) {
  743. /* A documentation typemap that is not the empty string
  744. indicates that a value is returned to Scheme. */
  745. num_results++;
  746. }
  747. }
  748. p = Getattr(p, "tmap:argout:next");
  749. } else {
  750. p = nextSibling(p);
  751. }
  752. }
  753. /* Insert cleanup code */
  754. for (p = l; p;) {
  755. if ((tm = Getattr(p, "tmap:freearg"))) {
  756. Replaceall(tm, "$target", Getattr(p, "lname"));
  757. Replaceall(tm, "$input", Getattr(p, "emit:input"));
  758. Printv(cleanup, tm, "\n", NIL);
  759. p = Getattr(p, "tmap:freearg:next");
  760. } else {
  761. p = nextSibling(p);
  762. }
  763. }
  764. if (use_scm_interface && exporting_destructor) {
  765. /* Mark the destructor's argument as destroyed. */
  766. String *tm = NewString("SWIG_Guile_MarkPointerDestroyed($input);");
  767. Replaceall(tm, "$input", Getattr(l, "emit:input"));
  768. Printv(cleanup, tm, "\n", NIL);
  769. Delete(tm);
  770. }
  771. /* Close prototype */
  772. Printf(f->def, ")\n{\n");
  773. /* Define the scheme name in C. This define is used by several Guile
  774. macros. */
  775. Printv(f->def, "#define FUNC_NAME \"", proc_name, "\"", NIL);
  776. // Now write code to make the function call
  777. if (!use_scm_interface)
  778. Printv(f->code, tab4, "gh_defer_ints();\n", NIL);
  779. emit_action(n, f);
  780. if (!use_scm_interface)
  781. Printv(f->code, tab4, "gh_allow_ints();\n", NIL);
  782. // Now have return value, figure out what to do with it.
  783. if ((tm = Getattr(n, "tmap:out"))) {
  784. Replaceall(tm, "$result", "gswig_result");
  785. Replaceall(tm, "$target", "gswig_result");
  786. Replaceall(tm, "$source", "result");
  787. if (GetFlag(n, "feature:new"))
  788. Replaceall(tm, "$owner", "1");
  789. else
  790. Replaceall(tm, "$owner", "0");
  791. Printv(f->code, tm, "\n", NIL);
  792. } else {
  793. throw_unhandled_guile_type_error(d);
  794. }
  795. // Dump the argument output code
  796. Printv(f->code, outarg, NIL);
  797. // Dump the argument cleanup code
  798. Printv(f->code, cleanup, NIL);
  799. // Look for any remaining cleanup
  800. if (GetFlag(n, "feature:new")) {
  801. if ((tm = Swig_typemap_lookup_new("newfree", n, "result", 0))) {
  802. Replaceall(tm, "$source", "result");
  803. Printv(f->code, tm, "\n", NIL);
  804. }
  805. }
  806. // Free any memory allocated by the function being wrapped..
  807. if ((tm = Swig_typemap_lookup_new("ret", n, "result", 0))) {
  808. Replaceall(tm, "$source", "result");
  809. Printv(f->code, tm, "\n", NIL);
  810. }
  811. // Wrap things up (in a manner of speaking)
  812. if (beforereturn)
  813. Printv(f->code, beforereturn, "\n", NIL);
  814. Printv(f->code, "return gswig_result;\n", NIL);
  815. /* Substitute the function name */
  816. Replaceall(f->code, "$symname", iname);
  817. // Undefine the scheme name
  818. Printf(f->code, "#undef FUNC_NAME\n");
  819. Printf(f->code, "}\n");
  820. Wrapper_print(f, f_wrappers);
  821. if (!Getattr(n, "sym:overloaded")) {
  822. if (numargs > 10) {
  823. int i;
  824. /* gh_new_procedure would complain: too many args */
  825. /* Build a wrapper wrapper */
  826. Printv(f_wrappers, "static SCM\n", wname, "_rest (SCM rest)\n", NIL);
  827. Printv(f_wrappers, "{\n", NIL);
  828. Printf(f_wrappers, "SCM arg[%d];\n", numargs);
  829. Printf(f_wrappers, "SWIG_Guile_GetArgs (arg, rest, %d, %d, \"%s\");\n", numreq, numargs - numreq, proc_name);
  830. Printv(f_wrappers, "return ", wname, "(", NIL);
  831. Printv(f_wrappers, "arg[0]", NIL);
  832. for (i = 1; i < numargs; i++)
  833. Printf(f_wrappers, ", arg[%d]", i);
  834. Printv(f_wrappers, ");\n", NIL);
  835. Printv(f_wrappers, "}\n", NIL);
  836. /* Register it */
  837. if (use_scm_interface) {
  838. Printf(f_init, "scm_c_define_gsubr(\"%s\", 0, 0, 1, (swig_guile_proc) %s_rest);\n", proc_name, wname);
  839. } else {
  840. Printf(f_init, "gh_new_procedure(\"%s\", (swig_guile_proc) %s_rest, 0, 0, 1);\n", proc_name, wname, numreq, numargs - numreq);
  841. }
  842. } else if (emit_setters && struct_member && strlen(Char(proc_name)) > 3) {
  843. int len = Len(proc_name);
  844. const char *pc = Char(proc_name);
  845. /* MEMBER-set and MEMBER-get functions. */
  846. int is_setter = (pc[len - 3] == 's');
  847. if (is_setter) {
  848. Printf(f_init, "SCM setter = ");
  849. struct_member = 2; /* have a setter */
  850. } else
  851. Printf(f_init, "SCM getter = ");
  852. if (use_scm_interface) {
  853. /* GOOPS support uses the MEMBER-set and MEMBER-get functions,
  854. so ignore only_setters in this case. */
  855. if (only_setters && !goops)
  856. Printf(f_init, "scm_c_make_gsubr(\"%s\", %d, %d, 0, (swig_guile_proc) %s);\n", proc_name, numreq, numargs - numreq, wname);
  857. else
  858. Printf(f_init, "scm_c_define_gsubr(\"%s\", %d, %d, 0, (swig_guile_proc) %s);\n", proc_name, numreq, numargs - numreq, wname);
  859. } else {
  860. if (only_setters && !goops)
  861. Printf(f_init, "scm_make_gsubr(\"%s\", %d, %d, 0, (swig_guile_proc) %s);\n", proc_name, numreq, numargs - numreq, wname);
  862. else
  863. Printf(f_init, "gh_new_procedure(\"%s\", (swig_guile_proc) %s, %d, %d, 0);\n", proc_name, wname, numreq, numargs - numreq);
  864. }
  865. if (!is_setter) {
  866. /* Strip off "-get" */
  867. char *pws_name = (char *) malloc(sizeof(char) * (len - 3));
  868. strncpy(pws_name, pc, len - 3);
  869. pws_name[len - 4] = 0;
  870. if (struct_member == 2) {
  871. /* There was a setter, so create a procedure with setter */
  872. if (use_scm_interface) {
  873. Printf(f_init, "scm_c_define");
  874. } else {
  875. Printf(f_init, "gh_define");
  876. }
  877. Printf(f_init, "(\"%s\", " "scm_make_procedure_with_setter(getter, setter));\n", pws_name);
  878. } else {
  879. /* There was no setter, so make an alias to the getter */
  880. if (use_scm_interface) {
  881. Printf(f_init, "scm_c_define");
  882. } else {
  883. Printf(f_init, "gh_define");
  884. }
  885. Printf(f_init, "(\"%s\", getter);\n", pws_name);
  886. }
  887. Printf(exported_symbols, "\"%s\", ", pws_name);
  888. free(pws_name);
  889. }
  890. } else {
  891. /* Register the function */
  892. if (use_scm_interface) {
  893. if (exporting_destructor) {
  894. Printf(f_init, "((swig_guile_clientdata *)(SWIGTYPE%s->clientdata))->destroy = (guile_destructor) %s;\n", swigtype_ptr, wname);
  895. //Printf(f_init, "SWIG_TypeClientData(SWIGTYPE%s, (void *) %s);\n", swigtype_ptr, wname);
  896. }
  897. Printf(f_init, "scm_c_define_gsubr(\"%s\", %d, %d, 0, (swig_guile_proc) %s);\n", proc_name, numreq, numargs - numreq, wname);
  898. } else {
  899. Printf(f_init, "gh_new_procedure(\"%s\", (swig_guile_proc) %s, %d, %d, 0);\n", proc_name, wname, numreq, numargs - numreq);
  900. }
  901. }
  902. } else { /* overloaded function; don't export the single methods */
  903. if (!Getattr(n, "sym:nextSibling")) {
  904. /* Emit overloading dispatch function */
  905. int maxargs;
  906. String *dispatch = Swig_overload_dispatch(n, "return %s(argc,argv);", &maxargs);
  907. /* Generate a dispatch wrapper for all overloaded functions */
  908. Wrapper *df = NewWrapper();
  909. String *dname = Swig_name_wrapper(iname);
  910. Printv(df->def, "static SCM\n", dname, "(SCM rest)\n{\n", NIL);
  911. Printf(df->code, "#define FUNC_NAME \"%s\"\n", proc_name);
  912. Printf(df->code, "SCM argv[%d];\n", maxargs);
  913. Printf(df->code, "int argc = SWIG_Guile_GetArgs (argv, rest, %d, %d, \"%s\");\n", 0, maxargs, proc_name);
  914. Printv(df->code, dispatch, "\n", NIL);
  915. Printf(df->code, "scm_misc_error(\"%s\", \"No matching method for generic function `%s'\", SCM_EOL);\n", proc_name, iname);
  916. Printf(df->code, "#undef FUNC_NAME\n");
  917. Printv(df->code, "}\n", NIL);
  918. Wrapper_print(df, f_wrappers);
  919. if (use_scm_interface) {
  920. Printf(f_init, "scm_c_define_gsubr(\"%s\", 0, 0, 1, (swig_guile_proc) %s);\n", proc_name, dname);
  921. } else {
  922. Printf(f_init, "gh_new_procedure(\"%s\", (swig_guile_proc) %s, 0, 0, 1);\n", proc_name, dname);
  923. }
  924. DelWrapper(df);
  925. Delete(dispatch);
  926. Delete(dname);
  927. }
  928. }
  929. Printf(exported_symbols, "\"%s\", ", proc_name);
  930. if (!in_class || memberfunction_name) {
  931. // export wrapper into goops file
  932. String *method_def = NewString("");
  933. String *goops_name;
  934. if (in_class)
  935. goops_name = NewString(memberfunction_name);
  936. else
  937. goops_name = goopsNameMapping(proc_name, (char *) "");
  938. String *primitive_name = NewString("");
  939. if (primRenamer)
  940. Printv(primitive_name, "primitive:", proc_name, NIL);
  941. else
  942. Printv(primitive_name, proc_name, NIL);
  943. Replaceall(method_signature, "_", "-");
  944. Replaceall(primitive_args, "_", "-");
  945. if (!any_specialized_arg) {
  946. /* If there would not be any specialized argument in
  947. the method declaration, we simply re-export the
  948. function. This is a performance optimization. */
  949. Printv(method_def, "(define ", goops_name, " ", primitive_name, ")\n", NIL);
  950. } else if (numreq == numargs) {
  951. Printv(method_def, "(define-method (", goops_name, method_signature, ")\n", NIL);
  952. Printv(method_def, " (", primitive_name, primitive_args, "))\n", NIL);
  953. } else {
  954. /* Handle optional args. For the rest argument, use a name
  955. that cannot clash. */
  956. Printv(method_def, "(define-method (", goops_name, method_signature, " . %args)\n", NIL);
  957. Printv(method_def, " (apply ", primitive_name, primitive_args, " %args))\n", NIL);
  958. }
  959. if (in_class) {
  960. /* Defer method definition till end of class definition. */
  961. Printv(goops_class_methods, method_def, NIL);
  962. } else {
  963. Printv(goopscode, method_def, NIL);
  964. }
  965. Printf(goopsexport, "%s ", goops_name);
  966. Delete(primitive_name);
  967. Delete(goops_name);
  968. Delete(method_def);
  969. }
  970. if (procdoc) {
  971. String *returns_text = NewString("");
  972. if (num_results == 0)
  973. Printv(returns_text, return_nothing_doc, NIL);
  974. else if (num_results == 1)
  975. Printv(returns_text, return_one_doc, NIL);
  976. else
  977. Printv(returns_text, return_multi_doc, NIL);
  978. /* Substitute documentation variables */
  979. static const char *numbers[] = { "zero", "one", "two", "three",
  980. "four", "five", "six", "seven",
  981. "eight", "nine", "ten", "eleven",
  982. "twelve"
  983. };
  984. if (num_results <= 12)
  985. Replaceall(returns_text, "$num_values", numbers[num_results]);
  986. else {
  987. String *num_results_str = NewStringf("%d", num_results);
  988. Replaceall(returns_text, "$num_values", num_results_str);
  989. Delete(num_results_str);
  990. }
  991. Replaceall(returns_text, "$values", returns);
  992. Printf(doc_body, "\n%s", returns_text);
  993. write_doc(proc_name, signature, doc_body);
  994. Delete(returns_text);
  995. }
  996. Delete(proc_name);
  997. Delete(outarg);
  998. Delete(cleanup);
  999. Delete(signature);
  1000. Delete(method_signature);
  1001. Delete(primitive_args);
  1002. Delete(doc_body);
  1003. Delete(returns);
  1004. Delete(tmp);
  1005. Delete(scheme_arg_names);
  1006. DelWrapper(f);
  1007. return SWIG_OK;
  1008. }
  1009. /* ------------------------------------------------------------
  1010. * variableWrapper()
  1011. *
  1012. * Create a link to a C variable.
  1013. * This creates a single function PREFIX_var_VARNAME().
  1014. * This function takes a single optional argument. If supplied, it means
  1015. * we are setting this variable to some value. If omitted, it means we are
  1016. * simply evaluating this variable. Either way, we return the variables
  1017. * value.
  1018. * ------------------------------------------------------------ */
  1019. virtual int variableWrapper(Node *n) {
  1020. char *name = GetChar(n, "name");
  1021. char *iname = GetChar(n, "sym:name");
  1022. SwigType *t = Getattr(n, "type");
  1023. String *proc_name;
  1024. Wrapper *f;
  1025. String *tm;
  1026. if (!addSymbol(iname, n))
  1027. return SWIG_ERROR;
  1028. f = NewWrapper();
  1029. // evaluation function names
  1030. String *var_name = Swig_name_wrapper(iname);
  1031. // Build the name for scheme.
  1032. proc_name = NewString(iname);
  1033. Replaceall(proc_name, "_", "-");
  1034. if (1 || (SwigType_type(t) != T_USER) || (is_a_pointer(t))) {
  1035. Printf(f->def, "static SCM\n%s(SCM s_0)\n{\n", var_name);
  1036. /* Define the scheme name in C. This define is used by several Guile
  1037. macros. */
  1038. Printv(f->def, "#define FUNC_NAME \"", proc_name, "\"", NIL);
  1039. Wrapper_add_local(f, "gswig_result", "SCM gswig_result");
  1040. if (!GetFlag(n, "feature:immutable")) {
  1041. /* Check for a setting of the variable value */
  1042. Printf(f->code, "if (s_0 != SCM_UNDEFINED) {\n");
  1043. if ((tm = Swig_typemap_lookup_new("varin", n, name, 0))) {
  1044. Replaceall(tm, "$source", "s_0");
  1045. Replaceall(tm, "$input", "s_0");
  1046. Replaceall(tm, "$target", name);
  1047. /* Printv(f->code,tm,"\n",NIL); */
  1048. emit_action_code(n, f, tm);
  1049. } else {
  1050. throw_unhandled_guile_type_error(t);
  1051. }
  1052. Printf(f->code, "}\n");
  1053. }
  1054. // Now return the value of the variable (regardless
  1055. // of evaluating or setting)
  1056. if ((tm = Swig_typemap_lookup_new("varout", n, name, 0))) {
  1057. Replaceall(tm, "$source", name);
  1058. Replaceall(tm, "$target", "gswig_result");
  1059. Replaceall(tm, "$result", "gswig_result");
  1060. /* Printv(f->code,tm,"\n",NIL); */
  1061. emit_action_code(n, f, tm);
  1062. } else {
  1063. throw_unhandled_guile_type_error(t);
  1064. }
  1065. Printf(f->code, "\nreturn gswig_result;\n");
  1066. Printf(f->code, "#undef FUNC_NAME\n");
  1067. Printf(f->code, "}\n");
  1068. Wrapper_print(f, f_wrappers);
  1069. // Now add symbol to the Guile interpreter
  1070. if (!emit_setters || GetFlag(n, "feature:immutable")) {
  1071. /* Read-only variables become a simple procedure returning the
  1072. value; read-write variables become a simple procedure with
  1073. an optional argument. */
  1074. if (use_scm_interface) {
  1075. if (!goops && GetFlag(n, "feature:constasvar")) {
  1076. /* need to export this function as a variable instead of a procedure */
  1077. if (scmstub) {
  1078. /* export the function in the wrapper, and (set!) it in scmstub */
  1079. Printf(f_init, "scm_c_define_gsubr(\"%s\", 0, %d, 0, (swig_guile_proc) %s);\n", proc_name, !GetFlag(n, "feature:immutable"), var_name);
  1080. Printf(scmtext, "(set! %s (%s))\n", proc_name, proc_name);
  1081. } else {
  1082. /* export the variable directly */
  1083. Printf(f_init, "scm_c_define(\"%s\", %s(SCM_UNDEFINED));\n", proc_name, var_name);
  1084. }
  1085. } else {
  1086. /* Export the function as normal */
  1087. Printf(f_init, "scm_c_define_gsubr(\"%s\", 0, %d, 0, (swig_guile_proc) %s);\n", proc_name, !GetFlag(n, "feature:immutable"), var_name);
  1088. }
  1089. } else {
  1090. Printf(f_init, "\t gh_new_procedure(\"%s\", (swig_guile_proc) %s, 0, %d, 0);\n", proc_name, var_name, !GetFlag(n, "feature:immutable"));
  1091. }
  1092. } else {
  1093. /* Read/write variables become a procedure with setter. */
  1094. if (use_scm_interface) {
  1095. Printf(f_init, "{ SCM p = scm_c_define_gsubr(\"%s\", 0, 1, 0, (swig_guile_proc) %s);\n", proc_name, var_name);
  1096. Printf(f_init, "scm_c_define");
  1097. } else {
  1098. Printf(f_init, "\t{ SCM p = gh_new_procedure(\"%s\", (swig_guile_proc) %s, 0, 1, 0);\n", proc_name, var_name);
  1099. Printf(f_init, "gh_define");
  1100. }
  1101. Printf(f_init, "(\"%s\", " "scm_make_procedure_with_setter(p, p)); }\n", proc_name);
  1102. }
  1103. Printf(exported_symbols, "\"%s\", ", proc_name);
  1104. // export wrapper into goops file
  1105. if (!in_class) { // only if the variable is not part of a class
  1106. String *class_name = SwigType_typedef_resolve_all(SwigType_base(t));
  1107. String *goops_name = goopsNameMapping(proc_name, (char *) "");
  1108. String *primitive_name = NewString("");
  1109. if (primRenamer)
  1110. Printv(primitive_name, "primitive:", NIL);
  1111. Printv(primitive_name, proc_name, NIL);
  1112. /* Simply re-export the procedure */
  1113. if ((!emit_setters || GetFlag(n, "feature:immutable"))
  1114. && GetFlag(n, "feature:constasvar")) {
  1115. Printv(goopscode, "(define ", goops_name, " (", primitive_name, "))\n", NIL);
  1116. } else {
  1117. Printv(goopscode, "(define ", goops_name, " ", primitive_name, ")\n", NIL);
  1118. }
  1119. Printf(goopsexport, "%s ", goops_name);
  1120. Delete(primitive_name);
  1121. Delete(class_name);
  1122. Delete(goops_name);
  1123. }
  1124. if (procdoc) {
  1125. /* Compute documentation */
  1126. String *signature = NewString("");
  1127. String *signature2 = NULL;
  1128. String *doc = NewString("");
  1129. if (GetFlag(n, "feature:immutable")) {
  1130. Printv(signature, proc_name, NIL);
  1131. if (GetFlag(n, "feature:constasvar")) {
  1132. Printv(doc, "Is constant ", NIL);
  1133. } else {
  1134. Printv(doc, "Returns constant ", NIL);
  1135. }
  1136. if ((tm = Getattr(n, "tmap:varout:doc"))) {
  1137. Printv(doc, tm, NIL);
  1138. } else {
  1139. String *s = SwigType_str(t, 0);
  1140. Chop(s);
  1141. Printf(doc, "<%s>", s);
  1142. Delete(s);
  1143. }
  1144. } else if (emit_setters) {
  1145. Printv(signature, proc_name, NIL);
  1146. signature2 = NewString("");
  1147. Printv(signature2, "set! (", proc_name, ") ", NIL);
  1148. handle_documentation_typemap(signature2, NIL, n, "tmap:varin:arglist", "new-value");
  1149. Printv(doc, "Get or set the value of the C variable, \n", NIL);
  1150. Printv(doc, "which is of type ", NIL);
  1151. handle_documentation_typemap(doc, NIL, n, "tmap:varout:doc", "$1_type");
  1152. Printv(doc, ".");
  1153. } else {
  1154. Printv(signature, proc_name, " #:optional ", NIL);
  1155. if ((tm = Getattr(n, "tmap:varin:doc"))) {
  1156. Printv(signature, tm, NIL);
  1157. } else {
  1158. String *s = SwigType_str(t, 0);
  1159. Chop(s);
  1160. Printf(signature, "new-value <%s>", s);
  1161. Delete(s);
  1162. }
  1163. Printv(doc, "If NEW-VALUE is provided, " "set C variable to this value.\n", NIL);
  1164. Printv(doc, "Returns variable value ", NIL);
  1165. if ((tm = Getattr(n, "tmap:varout:doc"))) {
  1166. Printv(doc, tm, NIL);
  1167. } else {
  1168. String *s = SwigType_str(t, 0);
  1169. Chop(s);
  1170. Printf(doc, "<%s>", s);
  1171. Delete(s);
  1172. }
  1173. }
  1174. write_doc(proc_name, signature, doc, signature2);
  1175. Delete(signature);
  1176. if (signature2)
  1177. Delete(signature2);
  1178. Delete(doc);
  1179. }
  1180. } else {
  1181. Swig_warning(WARN_TYPEMAP_VAR_UNDEF, input_file, line_number, "Unsupported variable type %s (ignored).\n", SwigType_str(t, 0));
  1182. }
  1183. Delete(var_name);
  1184. Delete(proc_name);
  1185. DelWrapper(f);
  1186. return SWIG_OK;
  1187. }
  1188. /* ------------------------------------------------------------
  1189. * constantWrapper()
  1190. *
  1191. * We create a read-only variable.
  1192. * ------------------------------------------------------------ */
  1193. virtual int constantWrapper(Node *n) {
  1194. char *name = GetChar(n, "name");
  1195. char *iname = GetChar(n, "sym:name");
  1196. SwigType *type = Getattr(n, "type");
  1197. String *value = Getattr(n, "value");
  1198. int constasvar = GetFlag(n, "feature:constasvar");
  1199. String *proc_name;
  1200. String *var_name;
  1201. String *rvalue;
  1202. Wrapper *f;
  1203. SwigType *nctype;
  1204. String *tm;
  1205. f = NewWrapper();
  1206. // Make a static variable;
  1207. var_name = NewStringf("%sconst_%s", prefix, iname);
  1208. // Strip const qualifier from type if present
  1209. nctype = NewString(type);
  1210. if (SwigType_isconst(nctype)) {
  1211. Delete(SwigType_pop(nctype));
  1212. }
  1213. // Build the name for scheme.
  1214. proc_name = NewString(iname);
  1215. Replaceall(proc_name, "_", "-");
  1216. if ((SwigType_type(nctype) == T_USER) && (!is_a_pointer(nctype))) {
  1217. Swig_warning(WARN_TYPEMAP_CONST_UNDEF, input_file, line_number, "Unsupported constant value.\n");
  1218. Delete(var_name);
  1219. return SWIG_NOWRAP;
  1220. }
  1221. // See if there's a typemap
  1222. if (SwigType_type(nctype) == T_STRING) {
  1223. rvalue = NewStringf("\"%s\"", value);
  1224. } else if (SwigType_type(nctype) == T_CHAR) {
  1225. rvalue = NewStringf("\'%s\'", value);
  1226. } else {
  1227. rvalue = NewString(value);
  1228. }
  1229. if ((tm = Swig_typemap_lookup_new("constant", n, name, 0))) {
  1230. Replaceall(tm, "$source", rvalue);
  1231. Replaceall(tm, "$value", rvalue);
  1232. Replaceall(tm, "$target", name);
  1233. Printv(f_header, tm, "\n", NIL);
  1234. } else {
  1235. // Create variable and assign it a value
  1236. Printf(f_header, "static %s = %s;\n", SwigType_lstr(nctype, var_name), rvalue);
  1237. }
  1238. {
  1239. /* Hack alert: will cleanup later -- Dave */
  1240. Node *n = NewHash();
  1241. Setattr(n, "name", var_name);
  1242. Setattr(n, "sym:name", iname);
  1243. Setattr(n, "type", nctype);
  1244. SetFlag(n, "feature:immutable");
  1245. if (constasvar) {
  1246. SetFlag(n, "feature:constasvar");
  1247. }
  1248. variableWrapper(n);
  1249. Delete(n);
  1250. }
  1251. Delete(var_name);
  1252. Delete(nctype);
  1253. Delete(proc_name);
  1254. Delete(rvalue);
  1255. DelWrapper(f);
  1256. return SWIG_OK;
  1257. }
  1258. /* ------------------------------------------------------------
  1259. * classDeclaration()
  1260. * ------------------------------------------------------------ */
  1261. virtual int classDeclaration(Node *n) {
  1262. String *class_name = NewStringf("<%s>", Getattr(n, "sym:name"));
  1263. Setattr(n, "guile:goopsclassname", class_name);
  1264. return Language::classDeclaration(n);
  1265. }
  1266. /* ------------------------------------------------------------
  1267. * classHandler()
  1268. * ------------------------------------------------------------ */
  1269. virtual int classHandler(Node *n) {
  1270. /* Create new strings for building up a wrapper function */
  1271. have_constructor = 0;
  1272. class_name = NewString("");
  1273. short_class_name = NewString("");
  1274. Printv(class_name, "<", Getattr(n, "sym:name"), ">", NIL);
  1275. Printv(short_class_name, Getattr(n, "sym:name"), NIL);
  1276. Replaceall(class_name, "_", "-");
  1277. Replaceall(short_class_name, "_", "-");
  1278. if (!addSymbol(class_name, n))
  1279. return SWIG_ERROR;
  1280. /* Handle inheritance */
  1281. String *base_class = NewString("<");
  1282. List *baselist = Getattr(n, "bases");
  1283. if (baselist && Len(baselist)) {
  1284. Iterator i = First(baselist);
  1285. while (i.item) {
  1286. Printv(base_class, Getattr(i.item, "sym:name"), NIL);
  1287. i = Next(i);
  1288. if (i.item) {
  1289. Printf(base_class, "> <");
  1290. }
  1291. }
  1292. }
  1293. Printf(base_class, ">");
  1294. Replaceall(base_class, "_", "-");
  1295. Printv(goopscode, "(define-class ", class_name, " ", NIL);
  1296. Printf(goopsexport, "%s ", class_name);
  1297. if (Len(base_class) > 2) {
  1298. Printv(goopscode, "(", base_class, ")\n", NIL);
  1299. } else {
  1300. Printv(goopscode, "(<swig>)\n", NIL);
  1301. }
  1302. SwigType *ct = NewStringf("p.%s", Getattr(n, "name"));
  1303. swigtype_ptr = SwigType_manglestr(ct);
  1304. String *mangled_classname = Swig_name_mangle(Getattr(n, "sym:name"));
  1305. /* Export clientdata structure */
  1306. if (use_scm_interface) {
  1307. Printf(f_runtime, "static swig_guile_clientdata _swig_guile_clientdata%s = { NULL, SCM_EOL };\n", mangled_classname);
  1308. Printv(f_init, "SWIG_TypeClientData(SWIGTYPE", swigtype_ptr, ", (void *) &_swig_guile_clientdata", mangled_classname, ");\n", NIL);
  1309. SwigType_remember(ct);
  1310. }
  1311. Delete(ct);
  1312. /* Emit all of the members */
  1313. goops_class_methods = NewString("");
  1314. in_class = 1;
  1315. Language::classHandler(n);
  1316. in_class = 0;
  1317. Printv(goopscode, " #:metaclass <swig-metaclass>\n", NIL);
  1318. if (have_constructor)
  1319. Printv(goopscode, " #:new-function ", primRenamer ? "primitive:" : "", "new-", short_class_name, "\n", NIL);
  1320. Printf(goopscode, ")\n%s\n", goops_class_methods);
  1321. Delete(goops_class_methods);
  1322. goops_class_methods = 0;
  1323. /* export class initialization function */
  1324. if (goops) {
  1325. /* export the wrapper function */
  1326. String *funcName = NewString(mangled_classname);
  1327. Printf(funcName, "_swig_guile_setgoopsclass");
  1328. String *guileFuncName = NewString(funcName);
  1329. Replaceall(guileFuncName, "_", "-");
  1330. Printv(f_wrappers, "static SCM ", funcName, "(SCM cl) \n", NIL);
  1331. Printf(f_wrappers, "#define FUNC_NAME %s\n{\n", guileFuncName);
  1332. Printv(f_wrappers, " ((swig_guile_clientdata *)(SWIGTYPE", swigtype_ptr, "->clientdata))->goops_class = cl;\n", NIL);
  1333. Printf(f_wrappers, " return SCM_UNSPECIFIED;\n");
  1334. Printf(f_wrappers, "}\n#undef FUNC_NAME\n\n");
  1335. Printf(f_init, "scm_c_define_gsubr(\"%s\", 1, 0, 0, (swig_guile_proc) %s);\n", guileFuncName, funcName);
  1336. Printf(exported_symbols, "\"%s\", ", guileFuncName);
  1337. /* export the call to the wrapper function */
  1338. Printf(goopscode, "(%s%s %s)\n\n", primRenamer ? "primitive:" : "", guileFuncName

Large files files are truncated, but you can click here to view the full file