gc1.5 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238
  1. ;;
  2. ;; Clu garbage collector - step 1
  3. ;; Arguments and initialization
  4. ;;
  5. ;; Arguments are as follows:
  6. ;; register 0 end of basic&types,,start of basic&types
  7. ;; 1 end of stack,,start of stack
  8. ;; 2 end of GC area,,start of GC area
  9. ;; 3 anything,,frame pointer to trace from
  10. ;; 4 last page to use,,first page to use
  11. ;; 5 last page to map out,,first to map out
  12. ;;
  13. ;; The names for registers below are used only here
  14. ;;
  15. bas== 0
  16. stk== 1
  17. gca== 2
  18. frm== 3
  19. use== 4
  20. map== 5
  21. ;;
  22. ;; First, store arguments
  23. ;;
  24. hrrzm bas,bstart ;; save pointers defining basic area
  25. hlrz bas,bas
  26. movem bas,bend
  27. camg bas,bstart ;; make sure size of basic area > 0
  28. $die Start of basic area > end!
  29. hrrzm stk,sstart ;; save pointers to stack
  30. hlrz stk,stk
  31. movem stk,send
  32. camg stk,sstart ;; make sure size of stack > 0
  33. $die Start of stack > end!
  34. hrrzm gca,gstart ;; save pointers to garbage collected area
  35. hlrz gca,gca
  36. movem gca,gend
  37. camg gca,gstart ;; make sure its size is > 0
  38. $die Start of GC area > end!
  39. hrrz frm,frm ;; save the frame pointer
  40. movem frm,frame
  41. camge frm,sstart ;; make sure it points inside the stack
  42. $die Frame pointer not in stack!
  43. camle frm,send
  44. $die Frame pointer not in stack!
  45. hrrzm use,lopage ;; save numbers of highest and lowest usable pages
  46. hlrz use,use ;; (usable means space we can use for storage during
  47. movem use,hipage ;; GC; it includes GC area, stack, etc.)
  48. camge use,lopage ;; make sure its size is > 0
  49. $die Start of usable > end!
  50. hrrzm map,lomap ;; save numbers of highest and lowest pages
  51. hlrz map,map ;; to be mapped out
  52. movem map,himap
  53. camge map,lomap ;; make sure its size >= 0
  54. $die Start of mapped > end!
  55. ;;
  56. ;; Now compute page numbers of areas
  57. ;;
  58. move r1,[-6,,bstart]
  59. loop11: move r0,(r1)
  60. lsh r0,-pglog2
  61. movem r0,6(r1)
  62. aobjn r1,loop11
  63. ;;
  64. ;; Compute checks on size and placement of pages, as follows:
  65. ;;
  66. ;; we give an error if there is not enough room in the usable area;
  67. ;; we need at least 1 more page than twice what the stack uses,
  68. ;; (used like this:
  69. ;; our stack (>= 1 page),
  70. ;; frame save pages (= size of stack, compacted when done),
  71. ;; the stack (= size of stack)), and
  72. ;; we need at least 4 more pages than the gc area uses, and
  73. ;; the addresses must work out like this:
  74. ;; at least two pages, gc area, at least two pages;
  75. ;; (we use the space like this:
  76. ;; our stack (>= 1 page),
  77. ;; frame save (>= 1 page),
  78. ;; gc area,
  79. ;; read window (= 1 page),
  80. ;; write window (= 1 page)).
  81. ;;
  82. move r0,hipage ;; # usable pages = high-low+1
  83. sub r0,lopage
  84. aoj r0, ;; r0 = # usable pages
  85. move r1,sepg ;; likewise for # stack pages
  86. sub r1,sspg
  87. aoj r1,
  88. ash r1,1
  89. aoj r1, ;; r1 = number of pages required for stack hacking
  90. camge r0,r1 ;; = 2*(# stack pages)+1
  91. $die Not enough pages for stack hacking
  92. move r0,gspg ;; make sure at least 2 pages free below GC area
  93. subi r0,2
  94. camge r0,lopage
  95. $die Not enough pages below GC area
  96. move r0,gepg ;; make sure at least 2 pages free above GC area
  97. addi r0,2
  98. camle r0,hipage
  99. $die Not enough pages above GC area
  100. move r0,hipage ;; save the page numbers of the write window page
  101. movem r0,wwind
  102. soj r0,
  103. movem r0,rwind ;; and the read window page
  104. move r0,lopage ;; make sure all space used is mapped out
  105. camge r0,lomap
  106. $die Used space not mapped out!
  107. move r0,hipage
  108. camle r0,himap
  109. $die Used space not mapped out!
  110. ;;
  111. ;; Set up new interrupt table
  112. ;;
  113. move r0,inttab
  114. exch r0,intptr
  115. movem r0,optr
  116. ;;
  117. ;; Create inferior job (we use its address space as storage; it never runs)
  118. ;;
  119. move r0,[sixbit /CLUGC0/]
  120. movem r0,jobnam
  121. tryit: .call jexist ;; this call skips if a job with the given name exists
  122. jrst [movei r2,4 ;; error code meaning job exists
  123. came r2,errcod
  124. $die Call to see if job exists failed in wrong way!!
  125. jrst makeit] ;; try to make job
  126. .call [setz ;; close the channel
  127. ciarg usro
  128. clerr errcod]
  129. again: aos jobnam ;; try another name
  130. jrst tryit
  131. makeit: .call jmake ;; this actually creates the job
  132. jrst [move r2,errcod ;; check error code
  133. cain r2,12 ;; 12 => job not inferior
  134. jrst again
  135. cain r2,6 ;; 6 => no job slots
  136. $die No jobs slots available for GC
  137. cain r2,5 ;; 5 => already have 8 inferiors
  138. $die No inferiors available for GC
  139. $die Couldn't get job for GC (strange error)
  140. ]
  141. ;;
  142. ;; Map out pages asked to
  143. ;;
  144. move r0,lomap
  145. movn r1,himap ;; # of pages = hi - lo + 1 = n
  146. add r1,r0
  147. soj r1,
  148. hrl r0,r1 ;; r0 = -n,,lo
  149. movem r0,pgdest
  150. hrrzm r0,pgsrc ;; for other pointer
  151. .call mapem ;; map pages out
  152. $die Couldn't map pages out
  153. ;;
  154. ;; Jump to next phase
  155. ;;
  156. jrst cont2
  157. ;;
  158. ;; Put variables here
  159. ;;
  160. ;; First, the pointers that define the various areas:
  161. ;; note: these six must be together, and bstart must be first!
  162. ;;
  163. bstart: block 1 ;; address of first word of basic&types area
  164. bend: block 1 ;; address of last word of basic&types area
  165. sstart: block 1 ;; address of first word of the stack
  166. send: block 1 ;; address of last word of the stack
  167. gstart: block 1 ;; address of first word of the GC area
  168. gend: block 1 ;; address of last word of the GC area
  169. ;;
  170. ;; These six must also be together, in the same order as the six above,
  171. ;; and just after them!
  172. ;;
  173. bspg: block 1 ;; number of first page of basic&types
  174. bepg: block 1 ;; number of last page of basic&types
  175. sspg: block 1 ;; number of first page of the stack
  176. sepg: block 1 ;; number of last page of the stack
  177. gspg: block 1 ;; number of first page of the GC area
  178. gepg: block 1 ;; number of last page of the GC area
  179. ;;
  180. ;; Rest of arguments
  181. ;;
  182. frame: block 1 ;; pointer to top frame in the stack
  183. lopage: block 1 ;; number of lowest page to use
  184. hipage: block 1 ;; number of highest page to use
  185. lomap: block 1 ;; number of lowest page to map out
  186. himap: block 1 ;; number of highest page to map out
  187. rwind: block 1 ;; number of read window page
  188. wwind: block 1 ;; number of write window page
  189. ;;
  190. ;; Interrupt hacking stuff
  191. ;;
  192. intptr==42 ;; loc of pointer to interrupt table
  193. optr: block 1 ;; old pointer to interrupt table
  194. inttab: -intlen,,intrup ;; new interrupt table word
  195. ;;
  196. ;; New interrupt table
  197. ;;
  198. intrup: 400020,,intpdl ;; push all regs, and debugging info
  199. ;; intpdl is intr stack ptr
  200. %pipdl ? 0 ? %pipdl ? 0 ? pdlov
  201. ;; pdl is 1st word, masks self, handler is pdlov
  202. %pimpv ? 0 ? %pimpv ? 0 ? mpvint
  203. ;; mpv is 1st word, masks self, handler is mpvint
  204. intlen==.-intrup
  205. ;;
  206. ;; New interrupt stack pointer and stack
  207. ;;
  208. intpdl: -istkln,,intstk ;; new interrupt stack pointer
  209. intstk: block 48. ;; new interrupt stack, room for 2 interrupts
  210. istkln= .-intstk
  211. ;;
  212. ;; Interrupt handlers
  213. ;;
  214. ;; PDL Overflow handler
  215. ;;
  216. pdlov: $die Push down stack overflow
  217. .call intdis ;; dismiss (assume DDT took care of it)
  218. $die Couldn't dismiss PDL OV interrupt
  219. ;;
  220. ;; MPV Interrupt handler
  221. ;;
  222. mpvint: $die MPV interrupt
  223. .call intdis ;; dismiss (assume DDT took care of it)
  224. $die Couldn't dismiss MPV interrupt
  225. ;;
  226. ;; Job hacking stuff
  227. ;;
  228. usro== 17 ;; channel # for job as output
  229. jobnam: block 1 ;; word for job name
  230. ;;
  231. ;; Constants for locality
  232. ;;
  233. consta
  234. ;;
  235. ;; Start of next phase
  236. ;;
  237. cont2: