Google
 

Trailing-Edge - PDP-10 Archives - mit_emacs_170_teco_1220 - emacs/xjsys.mid
There are 2 other files named xjsys.mid in the archive. Click here to see a list.
;-*-MIDAS-*-

;XJSYS makes TENEX JSYS's look like ITS symbolic system calls.
;In general, load T with <inlist addr>,,<outlist addr>
;where the inlist contains the JSYS followed by the input args
;(1 word each) followed by -1, and the outlist contains the
;addresses to store the values, followed by a -1.  An input arg
;can be either the address of the value or 1000,,immediate value.
;Input and output args can all be indexed or indirect.
;Then PUSHJ to XJSYS.  It will fetch the input args, do the JSYS,
;store the values, and then skip if the JSYS skipped.
;The accumulators 1-4 are not clobbered unless output addresses
;specify them (which works).  T isn't clobbered either.

;XJSYSP must be defined to be the accumulator XJSYS uses as its PDL.
;If P is not between 1 and 4, XJSYSP may be the same as P.
;Otherwise, it must be an accumulator not between 1 and 4, distinct
;from T.  It will be clobbered.

;Example:
;	MOVE T,[[GTJFN ? ARG1 ? 1000,,IMARG2 ? -1],,[2 ? 1 ? BAR ? -1]]
;	PUSHJ P,XJSYS
;	 error return
;	success return
;Note that it puts the first value in AC 2 and the second in AC 1!
;The ACs are already restored by the time values are handed out.

;Using the SYSCAL macro, the example above becomes
;	SYSCAL GTJFN,[ARG1 ? 1000,,IMARG2][2 ? 1 ? BAR]
;	 error return
;	success return
DEFINE SYSCAL NAME,IN,OUT
	MOVE T,[[NAME ? IN ? -1],,[OUT ? -1]]
	PUSHJ P,XJSYS
TERMIN

DEFINE SYSBLK NAME,IN,OUT
[[NAME ? IN ? -1],,[OUT ? -1]]!TERMIN

IFNDEF XJSYSP,XJSYSP==P
IFLE XJSYSP-4,.ERR XJSYSP must be greater than 4
IFE XJSYSP-T,.ERR XJSYSP must be distinct from T
.HKILL XJSYSP
IFLE T-4,.ERR T must be greater than 4

XJSYS:
IFN XJSYSP-P, MOVE XJSYSP,P
	ADD XJSYSP,[5,,5]	; Make room for 4 saved acs/args/vals and T
	MOVSM T,(XJSYSP)
REPEAT 4,[
	MOVE T,(XJSYSP)		; Get address of input arg block
	SKIPGE T,1+.RPCNT(T)	; Are there any more args?
	 JRST XJSYS1
	HRRI T,@T		; Yes => compute address of next arg
	TLZ T,37
	TLZN T,1000		; Get contents if not immediate.
	 MOVE T,(T)
	MOVEM T,-<1+.RPCNT>(XJSYSP) ; Store arg in resting place on stack,
]				; 1st is closest to top.

	; Now put original acs 1-4 on stack and get JSYS args out.
XJSYS1:
REPEAT 4,EXCH 1+.RPCNT,-<1+.RPCNT>(XJSYSP)
	POP XJSYSP,T
	XCT (T)			;Do the JSYS.
	 JRST XJSYS2		;Propagate 0, 1 or 2 skips
	  CAIA			;back to our caller.
	   AOS -4(XJSYSP)
	AOS -4(XJSYSP)

XJSYS2:	; Restore ACs and put results on stack.
REPEAT 4,EXCH 1+.RPCNT,-.RPCNT(XJSYSP)
	MOVSS T
REPEAT 4,[
	SKIPGE .RPCNT(T)
IFE XJSYSP-P, JRST XJSYSX+.RPCNT
.ELSE	      POPJ P,
	POP XJSYSP,@.RPCNT(T)
]
	POPJ P,

IFE XJSYSP-P,[
XJSYSX:	SUB P,[1,,1]
	SUB P,[1,,1]
	SUB P,[1,,1]
	SUB P,[1,,1]
	POPJ P,
]