frames.c 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288
  1. /* Copyright (C) 2001, 2009 Free Software Foundation, Inc.
  2. *
  3. * This library is free software; you can redistribute it and/or
  4. * modify it under the terms of the GNU Lesser General Public License
  5. * as published by the Free Software Foundation; either version 3 of
  6. * the License, or (at your option) any later version.
  7. *
  8. * This library is distributed in the hope that it will be useful, but
  9. * WITHOUT ANY WARRANTY; without even the implied warranty of
  10. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. * Lesser General Public License for more details.
  12. *
  13. * You should have received a copy of the GNU Lesser General Public
  14. * License along with this library; if not, write to the Free Software
  15. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
  16. * 02110-1301 USA
  17. */
  18. #if HAVE_CONFIG_H
  19. # include <config.h>
  20. #endif
  21. #include <stdlib.h>
  22. #include <string.h>
  23. #include "_scm.h"
  24. #include "vm-bootstrap.h"
  25. #include "frames.h"
  26. scm_t_bits scm_tc16_vm_frame;
  27. #define RELOC(frame, val) (val + SCM_VM_FRAME_OFFSET (frame))
  28. SCM
  29. scm_c_make_vm_frame (SCM stack_holder, SCM *fp, SCM *sp,
  30. scm_byte_t *ip, scm_t_ptrdiff offset)
  31. {
  32. struct scm_vm_frame *p = scm_gc_malloc (sizeof (struct scm_vm_frame),
  33. "vmframe");
  34. p->stack_holder = stack_holder;
  35. p->fp = fp;
  36. p->sp = sp;
  37. p->ip = ip;
  38. p->offset = offset;
  39. SCM_RETURN_NEWSMOB (scm_tc16_vm_frame, p);
  40. }
  41. static int
  42. vm_frame_print (SCM frame, SCM port, scm_print_state *pstate)
  43. {
  44. scm_puts ("#<vm-frame ", port);
  45. scm_uintprint (SCM_UNPACK (frame), 16, port);
  46. scm_putc (' ', port);
  47. scm_write (scm_vm_frame_program (frame), port);
  48. /* don't write args, they can get us into trouble. */
  49. scm_puts (">", port);
  50. return 1;
  51. }
  52. static SCM
  53. vm_frame_mark (SCM obj)
  54. {
  55. return SCM_VM_FRAME_STACK_HOLDER (obj);
  56. }
  57. static size_t
  58. vm_frame_free (SCM obj)
  59. {
  60. struct scm_vm_frame *p = SCM_VM_FRAME_DATA (obj);
  61. scm_gc_free (p, sizeof(struct scm_vm_frame), "vmframe");
  62. return 0;
  63. }
  64. /* Scheme interface */
  65. SCM_DEFINE (scm_vm_frame_p, "vm-frame?", 1, 0, 0,
  66. (SCM obj),
  67. "")
  68. #define FUNC_NAME s_scm_vm_frame_p
  69. {
  70. return SCM_BOOL (SCM_VM_FRAME_P (obj));
  71. }
  72. #undef FUNC_NAME
  73. SCM_DEFINE (scm_vm_frame_program, "vm-frame-program", 1, 0, 0,
  74. (SCM frame),
  75. "")
  76. #define FUNC_NAME s_scm_vm_frame_program
  77. {
  78. SCM_VALIDATE_VM_FRAME (1, frame);
  79. return SCM_FRAME_PROGRAM (SCM_VM_FRAME_FP (frame));
  80. }
  81. #undef FUNC_NAME
  82. SCM_DEFINE (scm_vm_frame_arguments, "vm-frame-arguments", 1, 0, 0,
  83. (SCM frame),
  84. "")
  85. #define FUNC_NAME s_scm_vm_frame_arguments
  86. {
  87. SCM *fp;
  88. int i;
  89. struct scm_objcode *bp;
  90. SCM ret;
  91. SCM_VALIDATE_VM_FRAME (1, frame);
  92. fp = SCM_VM_FRAME_FP (frame);
  93. bp = SCM_PROGRAM_DATA (SCM_FRAME_PROGRAM (fp));
  94. if (!bp->nargs)
  95. return SCM_EOL;
  96. else if (bp->nrest)
  97. ret = fp[bp->nargs - 1];
  98. else
  99. ret = scm_cons (fp[bp->nargs - 1], SCM_EOL);
  100. for (i = bp->nargs - 2; i >= 0; i--)
  101. ret = scm_cons (fp[i], ret);
  102. return ret;
  103. }
  104. #undef FUNC_NAME
  105. SCM_DEFINE (scm_vm_frame_source, "vm-frame-source", 1, 0, 0,
  106. (SCM frame),
  107. "")
  108. #define FUNC_NAME s_scm_vm_frame_source
  109. {
  110. SCM *fp;
  111. struct scm_objcode *bp;
  112. SCM_VALIDATE_VM_FRAME (1, frame);
  113. fp = SCM_VM_FRAME_FP (frame);
  114. bp = SCM_PROGRAM_DATA (SCM_FRAME_PROGRAM (fp));
  115. return scm_c_program_source (SCM_FRAME_PROGRAM (fp),
  116. SCM_VM_FRAME_IP (frame) - bp->base);
  117. }
  118. #undef FUNC_NAME
  119. SCM_DEFINE (scm_vm_frame_local_ref, "vm-frame-local-ref", 2, 0, 0,
  120. (SCM frame, SCM index),
  121. "")
  122. #define FUNC_NAME s_scm_vm_frame_local_ref
  123. {
  124. SCM *fp;
  125. unsigned int i;
  126. struct scm_objcode *bp;
  127. SCM_VALIDATE_VM_FRAME (1, frame);
  128. fp = SCM_VM_FRAME_FP (frame);
  129. bp = SCM_PROGRAM_DATA (SCM_FRAME_PROGRAM (fp));
  130. SCM_VALIDATE_UINT_COPY (2, index, i);
  131. SCM_ASSERT_RANGE (2, index, i < bp->nargs + bp->nlocs);
  132. return SCM_FRAME_VARIABLE (fp, i);
  133. }
  134. #undef FUNC_NAME
  135. SCM_DEFINE (scm_vm_frame_local_set_x, "vm-frame-local-set!", 3, 0, 0,
  136. (SCM frame, SCM index, SCM val),
  137. "")
  138. #define FUNC_NAME s_scm_vm_frame_local_set_x
  139. {
  140. SCM *fp;
  141. unsigned int i;
  142. struct scm_objcode *bp;
  143. SCM_VALIDATE_VM_FRAME (1, frame);
  144. fp = SCM_VM_FRAME_FP (frame);
  145. bp = SCM_PROGRAM_DATA (SCM_FRAME_PROGRAM (fp));
  146. SCM_VALIDATE_UINT_COPY (2, index, i);
  147. SCM_ASSERT_RANGE (2, index, i < bp->nargs + bp->nlocs);
  148. SCM_FRAME_VARIABLE (fp, i) = val;
  149. return SCM_UNSPECIFIED;
  150. }
  151. #undef FUNC_NAME
  152. SCM_DEFINE (scm_vm_frame_return_address, "vm-frame-return-address", 1, 0, 0,
  153. (SCM frame),
  154. "")
  155. #define FUNC_NAME s_scm_vm_frame_return_address
  156. {
  157. SCM_VALIDATE_VM_FRAME (1, frame);
  158. return scm_from_ulong ((unsigned long)
  159. (SCM_FRAME_RETURN_ADDRESS
  160. (SCM_VM_FRAME_FP (frame))));
  161. }
  162. #undef FUNC_NAME
  163. SCM_DEFINE (scm_vm_frame_mv_return_address, "vm-frame-mv-return-address", 1, 0, 0,
  164. (SCM frame),
  165. "")
  166. #define FUNC_NAME s_scm_vm_frame_mv_return_address
  167. {
  168. SCM_VALIDATE_VM_FRAME (1, frame);
  169. return scm_from_ulong ((unsigned long)
  170. (SCM_FRAME_MV_RETURN_ADDRESS
  171. (SCM_VM_FRAME_FP (frame))));
  172. }
  173. #undef FUNC_NAME
  174. SCM_DEFINE (scm_vm_frame_dynamic_link, "vm-frame-dynamic-link", 1, 0, 0,
  175. (SCM frame),
  176. "")
  177. #define FUNC_NAME s_scm_vm_frame_dynamic_link
  178. {
  179. SCM_VALIDATE_VM_FRAME (1, frame);
  180. /* fixme: munge fp if holder is a continuation */
  181. return scm_from_ulong
  182. ((unsigned long)
  183. RELOC (frame,
  184. SCM_FRAME_DYNAMIC_LINK (SCM_VM_FRAME_FP (frame))));
  185. }
  186. #undef FUNC_NAME
  187. SCM_DEFINE (scm_vm_frame_stack, "vm-frame-stack", 1, 0, 0,
  188. (SCM frame),
  189. "")
  190. #define FUNC_NAME s_scm_vm_frame_stack
  191. {
  192. SCM *top, *bottom, ret = SCM_EOL;
  193. SCM_VALIDATE_VM_FRAME (1, frame);
  194. top = SCM_VM_FRAME_SP (frame);
  195. bottom = SCM_FRAME_UPPER_ADDRESS (SCM_VM_FRAME_FP (frame));
  196. while (bottom <= top)
  197. ret = scm_cons (*bottom++, ret);
  198. return ret;
  199. }
  200. #undef FUNC_NAME
  201. extern SCM
  202. scm_c_vm_frame_prev (SCM frame)
  203. {
  204. SCM *this_fp, *new_fp, *new_sp;
  205. this_fp = SCM_VM_FRAME_FP (frame);
  206. new_fp = SCM_FRAME_DYNAMIC_LINK (this_fp);
  207. if (new_fp)
  208. { new_fp = RELOC (frame, new_fp);
  209. new_sp = SCM_FRAME_LOWER_ADDRESS (this_fp) - 1;
  210. return scm_c_make_vm_frame (SCM_VM_FRAME_STACK_HOLDER (frame),
  211. new_fp, new_sp,
  212. SCM_FRAME_RETURN_ADDRESS (this_fp),
  213. SCM_VM_FRAME_OFFSET (frame));
  214. }
  215. else
  216. return SCM_BOOL_F;
  217. }
  218. void
  219. scm_bootstrap_frames (void)
  220. {
  221. scm_tc16_vm_frame = scm_make_smob_type ("vm-frame", 0);
  222. scm_set_smob_mark (scm_tc16_vm_frame, vm_frame_mark);
  223. scm_set_smob_free (scm_tc16_vm_frame, vm_frame_free);
  224. scm_set_smob_print (scm_tc16_vm_frame, vm_frame_print);
  225. scm_c_register_extension ("libguile", "scm_init_frames",
  226. (scm_t_extension_init_func)scm_init_frames, NULL);
  227. }
  228. void
  229. scm_init_frames (void)
  230. {
  231. scm_bootstrap_vm ();
  232. #ifndef SCM_MAGIC_SNARFER
  233. #include "libguile/frames.x"
  234. #endif
  235. }
  236. /*
  237. Local Variables:
  238. c-file-style: "gnu"
  239. End:
  240. */