1 " BEGIN INCLUDE FILE ...... gate_macros.incl.alm
  2 "   Last modified 6/77 by N. Morris, B. Greenberg, & T. VanVleck
  3 "   Modified 741212 by PG to inhibit while computing virtual CPU time
  4 "   Modified 83-03-14 by E. N. Kittlitz to clear IR
  5 "   Modified 83-06-01 BIM for ring alarm polling
  6 "   Modified 85-04-03 by Keith Loepere to make polling a little smarter.
  7 
  8 " This file contains several macros used when generating gate segments.
  9 " The major macros that are defined are:
 10 "
 11 "         gate_info           general setup code for normal gates
 12 "         hardcore_gate_info  general setup code for hardcore gates
 13 "         bad_dir_handler     setup and handler for bad_dir_ condition (goes at bottom)
 14 "         bad_dir_handler_entry         entrypoint for above (goes at top)
 15 "         gate                to define a normal gate
 16 "         hgate               to define a hardcore gate
 17 "         fgate               to define a fast hardcore gate
 18 "
 19 
 20 
 21           maclist   off
 22 
 23 ^L
 24 " HGATE - define a hardcore gate entry
 25 "
 26 "         hgate     gatename,procedure,entry,args{,bad_dir_trap}
 27 "
 28 " The entrypoint gatename is defined in the gate segment.  If args
 29 " is nonzero, the number of arguments passed to gatename must be
 30 " equal to args.  When gatename is called, it will in turn call
 31 " procedure$entry.
 32 "
 33 
 34 macro     hgate
 35           gentry    &1,&4*2,&1.t
 36           tsx2      .setup
 37 &=&5,bad_dir_trap&[ tsx0      .set_dir_trap
 38 &]        ldi       =0,dl
 39           short_call &2$&3(ap|0)
 40           eppbp     lp|&1.t
 41           tra       .return_code
 42           maclist   restore
 43           use       linkage
 44           even
 45           maclist   on,save
 46 &1.t:
 47           bss       ,gate_entry_data_size
 48 
 49           maclist   restore
 50 &end
 51 
 52 
 53 " FGATE - define a fast hardcore gate
 54 "
 55 "         fgate     gatename,procedure,entry
 56 "
 57 
 58 macro     fgate
 59           gentry    &1,0,0
 60           ldi       =0,dl
 61           epplp     .my_lp,*
 62           tra       &2$&3
 63 
 64           maclist   off
 65 &end
 66 
 67 
 68 " GATE - define a normal gate entry
 69 "
 70 "         gate      gatename,procedure,entry,args
 71 "
 72 
 73 macro     gate
 74           gentry    &1,&4*2,0
 75           tsx2      .setup
 76           ldi       =0,dl
 77           short_call &2$&3(ap|0)
 78           return
 79 
 80           maclist   restore
 81 &end
 82 
 83 ^L
 84 
 85 macro     gentry
 86           maclist   on,save
 87           segdef    &1
 88           maclist   restore
 89           use       transfer_vector
 90           maclist   on,save
 91 &1:
 92           tra       &1.e
 93           maclist   restore
 94           use       main
 95           maclist   on,save
 96           zero      &2,&3
 97 &1.e:
 98 &end
 99 
100 ^L
101 " HARDCORE_GATE_INFO - general info for hardcore gates
102 
103 macro     hardcore_gate_info
104           maclist   on,save
105           name      &1
106 
107           include   stack_header
108 
109           include   stack_frame
110           include   gate_data
111 
112           maclist   restore
113           eject
114 
115           tempd     .temp
116           tempd     .label_variable(0)
117           tempd     .time1,.time2
118           tempd     .unwinder_arglist(0)
119           tempd     .on_unit(5)
120           temp      .pf,.entryp
121           tempd     .vfl_arglist(2)
122           tempd     .mcptr
123 
124           use       transfer_vector
125           equ       .tv_begin,*
126 
127           tra       .actor
128 
129           use       tv_end
130           entrybound
131 
132           segdef    .tv_end
133 .tv_end:  vfd       14/(*-.tv_begin)
134 
135           use       main
136 
137           segdef    .my_lp
138           even
139 .my_lp:   bss       ,2
140 
141           join      /text/transfer_vector,tv_end,main
142 
143           use       linkage
144           join      /link/linkage
145 
146           use       main
147 
148           maclist   restore
149           eject
150 
151 .actor:   epplp     .my_lp,*
152           maclist   restore
153           gate_actor
154 
155 ^L
156 
157 .setup:   push
158           epplp     .my_lp,*
159           sprilp    sp|stack_frame.lp_ptr
160 
161           maclist   restore
162           gcheck
163 
164           inhibit   on        <+><+><+><+><+><+><+><+><+><+><+><+>
165           rccl      sys_info$clock_,*   calculate times
166           sbaq      pds$cpu_time
167           staq      .time1
168           sbaq      pds$virtual_delta
169           staq      .time2
170           lda       pds$page_waits
171           sta       .pf
172           inhibit   off       <-><-><-><-><-><-><-><-><-><-><-><->
173           tra       0,2
174 
175           maclist   restore
176           eject
177 
178 .return_code:
179 
180           inhibit   on        <+><+><+><+><+><+><+><+><+><+><+><+>
181           rccl      sys_info$clock_,*   calculate times
182           sbaq      pds$cpu_time
183           staq      .temp
184           sbaq      .time1
185           adaq      bp|gate_entry_data.cpu_time
186           staq      bp|gate_entry_data.cpu_time
187           ldaq      .temp
188           sbaq      pds$virtual_delta
189           sbaq      .time2
190           adaq      bp|gate_entry_data.vcpu_time
191           staq      bp|gate_entry_data.vcpu_time
192           lda       pds$page_waits
193           sbla      .pf
194           asa       bp|gate_entry_data.page_waits
195           aos       bp|gate_entry_data.calls
196           inhibit   off       <-><-><-><-><-><-><-><-><-><-><-><->
197 
198                               " Poll for ring alarms
199           sra       .temp     Borrow from time calc
200           szn       .temp     Zero?
201           tze       .return_code_return
202 
203           epp1      sp|stack_frame.prev_sp,*      "possible ring alarm
204           epaq      pr1|stack_frame.return_ptr,*
205           ana       7,dl      " ring number to which we return
206           cmpa      .temp
207           tpl       .ring_alarm         " ring alarm will occur
208 
209 .return_code_return:
210           return
211 
212 .ring_alarm:                  " perhaps we can handle without faults?
213 
214           aos       bp|gate_entry_data.ring_alarms
215           stz       .temp     " return argument for ring_alarm$poll
216           ldaq      .one_arg_header
217           staq      .ring_alarm_arg_list
218           epp1      .temp
219           spri1     .ring_alarm_arg_list+2
220           eppap     .ring_alarm_arg_list
221           short_call ring_alarm$poll
222           szn       .temp
223           tze       .return_code_return
224           eppsp     sp|stack_frame.prev_sp,*
225           sprisp    pds$pre_empt_poll_return          " short-return from here
226           epp1      sb|stack_header.stack_begin_ptr,* " abandoning this stack frame.
227           spri1     sb|stack_header.stack_end_ptr
228 " Leave SB as stack_0, so pxss can get to operators.
229           tra       pxss$pre_empt_poll
230 
231           tempd     .ring_alarm_arg_list(2)
232           even
233 .one_arg_header:
234           vfd       17/2,1/0,18/4
235           vfd       18/0,18/0
236 
237 
238           maclist   restore
239           eject
240           maclist   restore
241 &end
242 
243 ^L
244 " BAD_DIR_HANDLER - code to setup and handle bad_dir_ condition
245 "                             put this after the last hgate macro
246 
247 macro     bad_dir_handler
248           maclist   on,save
249 
250           include   on_unit
251 
252           use       transfer_vector
253 .handler_entry:
254           tra       .handler
255 .handler_restart_entry:
256           tra       .handler_restart_point
257 
258           use       main
259 .set_dir_trap:
260           stx0      .entryp             save for restart
261 
262           mlr       (),(pr),fill(000)
263           desc9a    0,0
264           desc9a    .on_unit,10*4
265           eppbp     .bad_dir_name
266           spribp    .on_unit+on_unit.name
267           eppbp     .handler_entry
268           spribp    .on_unit+on_unit.body
269           lxl1      .bad_dir_desc
270           sxl1      .on_unit+on_unit.size
271           eaa       .on_unit            set up on-unit for bad_dir_
272           sbla      sp|0,du             .. make rel to sp
273           sta       sp|stack_frame.on_unit_rel_ptrs
274           lda       stack_frame.condition_bit,dl
275           orsa      sp|stack_frame.flag_word
276           tra       0,0
277 
278           string    bad_dir_
279 
280 ^L
281 
282 .handler: epaq      sp|0                verify that call came from ring 0
283           cana      -1,dl               check ring number in AL
284           tze       *+2
285           zero      0                   go way kid you bother me
286 
287           push                          " ok, we like the call
288           epplp     .my_lp,*
289           ldx0      ap|0                get display
290           eppbp     ap|2,0*
291           lda       bp|stack_frame.prev_sp
292           cana      =o700000,dl         from another ring?
293           tze       .continue_signal    if not, back to signal_
294           eppap     ap|2,*              Get mcptr
295           eppap     ap|0,*              ..
296           spriap    bp|.mcptr           .. save in gate frame
297           spribp    .label_variable+2
298           eppbp     .handler_restart_entry
299           spribp    .label_variable
300           eppbp     .label_variable
301           spribp    .unwinder_arglist+2
302           fld       =1b24,dl
303           staq      .unwinder_arglist
304           call      unwinder_$unwinder_(.unwinder_arglist)
305 
306 .continue_signal:
307           lda       =o400000,du         "1"b
308           sta       ap|10,*             set continue bit
309           return
310 
311 .handler_restart_point:
312           epaq      sp|0                check that call came from ring 0
313           cana      -1,dl
314           tze       *+2
315           zero      1
316           epplp     .my_lp,*
317           lca       stack_frame.condition_bit+1,dl  Vanish on-unit
318           ansa      sp|stack_frame.flag_word
319           eppbp     .mcptr
320           spribp    .vfl_arglist+2
321           fld       =1b24,dl
322           staq      .vfl_arglist
323           short_call  verify_lock$verify_lock_bad_dir(.vfl_arglist)
324           ldx0      .entryp
325           eppap     sp|stack_frame.arg_ptr,*
326           tra       0,0                 retry the call
327 
328           maclist   restore
329           eject
330           maclist   restore
331 &end
332 
333 ^L
334 " GATE_INFO - general info for non-hardcore gates
335 
336 macro     gate_info
337           maclist   on,save
338           use       transfer_vector
339           tra       .actor
340 
341           use       tv_end
342           entrybound
343 
344           use       main
345           join      /text/transfer_vector,tv_end,main
346 
347           maclist   restore
348           eject
349 
350 .actor:   getlp
351           maclist   restore
352           gate_actor
353 
354           maclist   restore
355           eject
356 
357 .setup:   push
358           getlp
359           maclist   restore
360           gcheck
361           tra       0,2
362 
363           maclist   restore
364           eject
365 
366           maclist   restore
367 &end
368 
369 ^L
370 " Macro to generate gate actor.
371 
372 macro     gate_actor
373           maclist   on,save
374           eppbp     ap|2,*
375           lda       bp|-1               get length of string
376           tze       .return_name        zero length => get name
377 
378           adla      1,dl                include length of acc
379           stz       ap|4,*
380           tsx0      .search_defs
381 
382           cmpc      (pr,rl),(pr,rl)     compare name
383           desc9a    bp|-1(3),al
384           desc9a    bb|0,al
385           tnz       .next_def
386 
387           lda       ab|1,2              return location
388           arl       18
389           sta       ap|4,*
390 
391           short_return
392 
393 .return_name:
394           lxl3      ap|4,*              get location
395           tsx0      .search_defs
396 
397           cmpx3     ab|1,2              compare location
398           tnz       .next_def
399 
400           lda       bb|0                get length of name
401           arl       27
402           sta       bp|-1               set length of varying string
403           mlr       (pr,rl),(pr,rl)     return string
404           desc9a    bb|0(1),al
405           desc9a    bp|0,al
406 
407           short_return
408 
409 .search_defs:
410           eax2      0
411           eppab     lp|0,*              ab -> defs
412 .defs_loop:
413           lxl1      ab|1,2              get class and flags
414           cmpx1     =o400000,du         must be class 0
415           tnz       .next_def
416 
417           ldx7      ab|2,2
418           eppbb     ab|0,7              bb -> name
419           tra       0,0                 test definition
420 .next_def:
421           ldx2      ab|0,2              chain to next def
422           tnz       .defs_loop
423 
424           short_return
425 
426 &end
427 
428 ^L
429 " Miscellaneous macros.
430 
431 macro     gcheck
432           maclist   on,save
433           ldx1      -2,2                get number of args expected
434           tze       .no_gate_error      if zero, none or doesn't matter
435           cmpx1     ap|0                compare against number given
436           tze       .no_gate_error      args match, call procedure
437 
438           call      signal_$signal_(signal_arglist)
439           oct       0
440 
441           even
442 signal_arglist:
443           zero      2,4
444           zero      2,0
445           arg       .gate_errorname
446           arg
447           arg       .gate_errordesc
448           arg
449 
450           string    gate_error
451 
452 
453 .no_gate_error:
454 &end
455 
456 macro     string
457 .&1name:
458           aci       "&1"
459 .&1desc:
460           vfd       o9/525,o27/&l1
461 
462 &end
463 
464 macro     eject
465           maclist   on,save
466 ^L
467 &end
468 
469 " END INCLUDE FILE ...... gate_macros.incl.alm
470 
471 "  To arrange the return it wants to return, it will have to reach back  2 frames.