/ machine language assist
/ for 11/23, 11/34, 11/40, & 11/60 CPUs
/ Fred Canter 10/7/80
/
/ Added a "bic" instruction after the symbol "start:".
/ This is required in order to allow the I space only
/ versions of unix v7 to be booted via the standalone
/ boot code, which enters unix with memory management
/ enabled after loading unix into memory.
/ This change allows the I space only unix monitors
/ to be booted via the standalone boot or
/ directly via the block zero boot.

/ Added core to tape dump code.
/
/ FORTYZ is also in param_i.h.  This macro says we are running
/ on an 11/40 class processor with the Able Corp. ENABLE 22 Bit
/ addressing board and extra memory.

FORTYZ = 41.


/ non-UNIX instructions
mfpi	= 6500^tst
mtpi	= 6600^tst
halt	= 0
wait	= 1
reset	= 5
rtt	= 6
nop	= 0240

/ Mag tape dump
/ save registers in locore and
/ write all core onto mag tape.
/ entry thru 44 abs

.globl	start, _end, _edata, _main, dump
dump:
	bit	$1,SSR0
	bne	dump

/ save regs r0,r1,r2,r3,r4,r5,r6,KIA6
/ starting at abs location 4
	inc	$-1	/ save reg's on first core
	bne	1f	/ dump attempt only.

	mov	r0,4
	mov	$6,r0
	mov	r1,(r0)+
	mov	r2,(r0)+
	mov	r3,(r0)+
	mov	r4,(r0)+
	mov	r5,(r0)+
	mov	sp,(r0)+
	mov	KISA6,(r0)+

1:

/ dump all of core (ie to first mt error)
/ onto mag tape. (9 track or 7 track 'binary')

/ The core dump tape hardware CSR addresses
/ and HTDUMP, TUDUMP, and TSDUMP are
/ defined in the mch0.s header file.

.if HTDUMP

	/reg 0 holds the CSR address for the tm02/3.

	/this section of code initializes the TM02/3

	mov	$HTCS1,r0	/get tm02/3 CSR addr
	mov	$40,10(r0)	/tm02/3 subsystem clear
	mov	$1300,32(r0)	/800 BPI + pdp11 mode
	clr	4(r0)		/clear unibus address
	mov	$1,(r0)		/nop command to tm02/3

	/This section does the write.

3:
	mov	$-512.,6(r0)	/set frame count
	mov	$-256.,2(r0)	/set word count
	movb	$61,(r0)	/set write comand + go
1:
	tstb	(r0)		/wait for tm02/3 ready
	bge	1b
	bit	$1,(r0)		/wait for go bit clear
	bne	1b
	bit	$40000,(r0)	/any error ?
	beq	3b		/no, continue xfer
	bit	$4000,10(r0)	/yes, must be MXM error
	beq	.		/hang here if not NXM
	mov	$27,(r0)	/error is NXM, write EOF
	halt			/halt on good dump !
.endif

.if TUDUMP
	/reg 0 holds the tm11 CSR address

	/this section of code initializes the TM11

	mov	$MTC,r0		/get tm11 CSR address
	mov	$60004,(r0)	/write command, no go
	clr	4(r0)		/set bus addr to 0

	/This section does the write.

3:
	mov	$-512.,2(r0)	/set byte count
	inc	(r0)		/start xfer
1:
	tstb	(r0)		/wait for tm11 ready
	bge	1b
	tst	(r0)		/any error ?
	bge	3b		/no, continue xfer
	bit	$200,-2(r0)	/yes, must be NXM error
	beq	.		/hang if not NXM error
	reset			/error is NXM,
	mov	$60007,(r0)	/write EOF
	halt			/halt on good dump
.endif

.if TSDUMP

	/reg 0 is used to calculate the current memory address
	/ for each 512 byte transfer.
	/reg 4 points to the command packet

	clr	weof		/clear write EOF indicator

	/this section of code initializes the TS11

2:
	tstb	*$TSSR		/make sure
	bpl	2b		/drive is ready
	mov	$comts,r4	/point to command packet
	add	$2,r4		/set up mod 4
	bic	$3,r4		/alignment
	mov	$140004,(r4)	/write characteristics command
	mov	$chrts,2(r4)	/characteristics buffer
	clr	4(r4)		/clear extended memory bits
	mov	$10,6(r4)	/set byte count for command
	mov	$mests,*$chrts	/show where message buffer is
	clr	*$chrts+2	/clear extended memory bits here too
	mov	$16,*$chrts+4	/set message buffer length
	mov	r4,*$TSDB	/start command
	clr	r0		/init r0 beginning memory address
1:
	tstb	*$TSSR		/wait for ready
	bpl	1b		/not yet
	cmp	$100011,(r4)	/was last command a write EOF
	bne	6f		/no, continue dumpping
	halt			/yes, halt on good dump completion
6:
	cmpb	$201,*$TSSR	/look at termination class code
	bhi	3f		/no error
	bit	$4000,*$TSSR	/is error NXM ?
	beq	.		/no, hang (not sure of good dump)
	inc	weof		/yes, set write EOF indicator
	reset			/clear the world (good dump)
	br	2b		/go write an EOF

3:
	/This section does the write.

	mov	r0,2(r4)	/load mem address
	mov	$512.,6(r4)	/set byte count
	mov	$100005,(r4)	/set write command
	tst	weof		/time to write EOF ?
	beq	5f		/no, still dumpping
	mov	$1,6(r4)	/yes, set word count
	mov	$100011,(r4)	/and write EOF command
5:
	mov	r4,*$TSDB	/initiate xfer
	add	$512.,r0	/bump address for no mapping
	adc	4(r4)		/carry to extended memory bits
	br	1b		/do again
.endif
start:
	bic	$1,SSR0	/ Insure memory management if off !
	mov	$trap,34

/ Set location 0 and 2 to catch traps and jumps to 0

	mov	$42,0		/ illegal instruction if jump
	mov	$777,2		/ trace trap at high priority if trap

/ initialize systems segments

	mov	$KISA0,r0
	mov	$KISD0,r1
	mov	$200,r4
	clr	r2
	mov	$6,r3
1:
	mov	r2,(r0)+
	mov	$77406,(r1)+		/ 4k rw
	add	r4,r2
	sob	r3,1b

/ initialize user segment

	mov	$_end+63.,r2
	ash	$-6,r2
	bic	$!1777,r2
	mov	r2,(r0)+		/ ksr6 = sysu
	mov	$usize-1\<8|6,(r1)+

/ initialize io segment
/ set up counts on supervisor segments

/	mov	$IO,(r0)+
.if FORTYZ
	mov	$IO,(r0)	/ We have TWO copies of this PAR
	mov	$KISA7,r0
	mov	$IO,(r0)		/ Turn On Able's IO Page
.endif
	mov	$77406,(r1)+		/ rw 4k

.if FORTYZ
.globl	 ablestrt, ablestop, ableon
/ initialize the enable board

ablestrt:
/	halt
	mov	$2,r3
	mov	$PAR1,r0		/ enable DEC USER PAR's
	mov	$2000,r1
	mov	$8.,r2			/ do for 8 EPAR's
	br	1f
2:	mov	$PAR2,r0		/ enable DEC KERNAL PAR's
	clr	r1			/ EPAR's increment
	mov	$7,r2

1:	mov	r1,(r0)+		/ set up the PAR
	add	$200,r1			/ increment to next page
	sob	r2,1b			/ are there more registers to do
	sob	r3,2b			/ do the Kernal space reg's
ablestop:
/	halt
	mov	$IO1,(r0)		/ DEC KA7 sets up the IO page
.endif


/ get a sp and start segmentation

	mov	$_u+[usize*64.],sp
	inc	SSR0			/ start DEC Memory Manager

.if FORTYZ
/.globl	halt1
/.globl	 halt2
/.globl	 halt3
/.globl	 halt4
/	KLUDGE!!!!	KLUDGE!!!	KLUDGE!!!
	bis	$IO22,SSR3		/ start relocation to 22 bits
					/ AND turn IO MAP
/	KLUDGE!!!!	KLUDGE!!!	KLUDGE!!!
/halt1:	halt
ableon:
	bis	$BIT0,SSR4		/ enable the ENABLE board
/halt2:	halt
.endif
/ test for floating point
	mov	$1f,nofault
	setd				/ jumps to 1f if no fpu
	inc	fpp
1:
	clr	nofault

/ clear bss

	mov	$_edata,r0
1:
	clr	(r0)+
	cmp	r0,$_end
	blo	1b

/ clear user block

	mov	$_u,r0
1:
	clr	(r0)+
	cmp	r0,$_u+[usize*64.]
	blo	1b

/ set up previous mode and call main
/ on return, enter user mode at 0R

/halt3:	halt
	mov	$30000,PS
/halt4:	halt
	jsr	pc,_main
	mov	$170000,-(sp)
	clr	-(sp)
	rtt

.globl	trap, call
.globl	_trap, taktrap

/ all traps and interrupts are
/ vectored thru this routine.

trap:
	mov	PS,saveps
	tst	nofault
	bne	1f
	mov	SSR0,ssr
	mov	SSR2,ssr+4
	mov	$1,SSR0
taktrap:	jsr	r0,call1; jmp _trap
	/ no return
1:
	mov	$1,SSR0
	mov	nofault,(sp)
	rtt
.text

.globl	_runrun
call1:
	mov	saveps,-(sp)
	bic	$HIPRI,PS
	br	1f

call:
	mov	PS,-(sp)
1:
	mov	r1,-(sp)
	mfpi	sp
	mov	4(sp),-(sp)
	bic	$!37,(sp)
	bit	$30000,PS
	beq	1f
	jsr	pc,(r0)+
	tstb	_runrun
	beq	2f
	mov	$12.,(sp)		/ trap 12 is give up cpu
	jsr	pc,_trap
2:
	tst	(sp)+
	mtpi	sp
	br	2f
1:
	bis	$30000,PS
	jsr	pc,(r0)+
	cmp	(sp)+,(sp)+
2:
	mov	(sp)+,r1
	tst	(sp)+
	mov	(sp)+,r0
	rtt
.globl	_savfp
_savfp:
	tst	fpp
	beq	8f
	mov	2(sp),r1
	stfps	(r1)+
	setd
	movf	fr0,(r1)+
	movf	fr1,(r1)+
	movf	fr2,(r1)+
	movf	fr3,(r1)+
	movf	fr4,fr0
	movf	fr0,(r1)+
	movf	fr5,fr0
	movf	fr0,(r1)+
8:
	rts	pc

.globl	_restfp
_restfp:
	tst	fpp
	beq	8f
	mov	2(sp),r1
	mov	r1,r0
	setd
	add	$8.+2.,r1
	movf	(r1)+,fr1
	movf	(r1)+,fr2
	movf	(r1)+,fr3
	movf	(r1)+,fr0
	movf	fr0,fr4
	movf	(r1)+,fr0
	movf	fr0,fr5
	movf	2(r0),fr0
	ldfps	(r0)
8:
	rts	pc

.globl	_addupc
_addupc:
	mov	r2,-(sp)
	mov	6(sp),r2		/ base of prof with base,leng,off,scale
	mov	4(sp),r0		/ pc
	sub	4(r2),r0		/ offset
	clc
	ror	r0
	mov	6(r2),r1
	clc
	ror	r1
	mul	r1,r0		/ scale
	ashc	$-14.,r0
	inc	r1
	bic	$1,r1
	cmp	r1,2(r2)		/ length
	bhis	1f
	add	(r2),r1		/ base
	mov	nofault,-(sp)
	mov	$2f,nofault
	mfpi	(r1)
	add	12.(sp),(sp)
	mtpi	(r1)
	br	3f
2:
	clr	6(r2)
3:
	mov	(sp)+,nofault
1:
	mov	(sp)+,r2
	rts	pc

.globl	_display
_display:
	rts	pc

/ Character list get/put

/.globl	_getc, _putc
/.globl	_cfreelist
/
/_getc:
/	mov	2(sp),r1
/	mov	PS,-(sp)
/	mov	r2,-(sp)
/	bis	$HIPRI,PS
/	bic	$40,PS
/	mov	2(r1),r2		/ first ptr
/	beq	9f		/ empty
/	movb	(r2)+,r0		/ character
/	bic	$!377,r0
/	mov	r2,2(r1)
/	dec	(r1)+		/ count
/	bne	1f
/	clr	(r1)+
/	clr	(r1)+		/ last block
/	br	2f
/1:
/	bit	$7,r2
/	bne	3f
/	mov	-10(r2),(r1)		/ next block
/	add	$2,(r1)
/2:
/	dec	r2
/	bic	$7,r2
/	mov	_cfreelist,(r2)
/	mov	r2,_cfreelist
/3:
/	mov	(sp)+,r2
/	mov	(sp)+,PS
/	rts	pc
/9:
/	clr	4(r1)
/	mov	$-1,r0
/	mov	(sp)+,r2
/	mov	(sp)+,PS
/	rts	pc
/
/_putc:
/	mov	2(sp),r0
/	mov	4(sp),r1
/	mov	PS,-(sp)
/	mov	r2,-(sp)
/	mov	r3,-(sp)
/	bis	$HIPRI,PS
/	bic	$40,PS
/	mov	4(r1),r2		/ last ptr
/	bne	1f
/	mov	_cfreelist,r2
/	beq	9f
/	mov	(r2),_cfreelist
/	clr	(r2)+
/	mov	r2,2(r1)		/ first ptr
/	br	2f
/1:
/	bit	$7,r2
/	bne	2f
/	mov	_cfreelist,r3
/	beq	9f
/	mov	(r3),_cfreelist
/	mov	r3,-10(r2)
/	mov	r3,r2
/	clr	(r2)+
/2:
/	movb	r0,(r2)+
/	mov	r2,4(r1)
/	inc	(r1)		/ count
/	clr	r0
/	mov	(sp)+,r3
/	mov	(sp)+,r2
/	mov	(sp)+,PS
/	rts	pc
/9:
/	mov	pc,r0
/	mov	(sp)+,r3
/	mov	(sp)+,r2
/	mov	(sp)+,PS
/	rts	pc

.globl	_backup
.globl	_regloc
_backup:
	mov	2(sp),ssr+2
	mov	r2,-(sp)
	jsr	pc,backup
	mov	r2,ssr+2
	mov	(sp)+,r2
	movb	jflg,r0
	bne	2f
	mov	2(sp),r0
	movb	ssr+2,r1
	jsr	pc,1f
	movb	ssr+3,r1
	jsr	pc,1f
	movb	_regloc+7,r1
	asl	r1
	add	r0,r1
	mov	ssr+4,(r1)
	clr	r0
2:
	rts	pc
1:
	mov	r1,-(sp)
	asr	(sp)
	asr	(sp)
	asr	(sp)
	bic	$!7,r1
	movb	_regloc(r1),r1
	asl	r1
	add	r0,r1
	sub	(sp)+,(r1)
	rts	pc

/ hard part
/ simulate the ssr2 register missing on 11/40

backup:
	clr	r2		/ backup register ssr1
	mov	$1,bflg		/ clrs jflg
	mov	ssr+4,r0
	jsr	pc,fetch
	mov	r0,r1
	ash	$-11.,r0
	bic	$!36,r0
	jmp	*0f(r0)
0:		t00; t01; t02; t03; t04; t05; t06; t07
		t10; t11; t12; t13; t14; t15; t16; t17

t00:
	clrb	bflg

t10:
	mov	r1,r0
	swab	r0
	bic	$!16,r0
	jmp	*0f(r0)
0:		u0; u1; u2; u3; u4; u5; u6; u7

u6:	/ single op, m[tf]pi, sxt, illegal
	bit	$400,r1
	beq	u5		/ all but m[tf], sxt
	bit	$200,r1
	beq	1f		/ mfpi
	bit	$100,r1
	bne	u5		/ sxt

/ simulate mtpi with double (sp)+,dd
	bic	$4000,r1	/ turn instr into (sp)+
	br	t01

/ simulate mfpi with double ss,-(sp)
1:
	ash	$6,r1
	bis	$46,r1		/ -(sp)
	br	t01

u4:	/ jsr
	mov	r1,r0
	jsr	pc,setreg	/ assume no fault
	bis	$173000,r2	/ -2 from sp
	rts	pc

t07:	/ EIS
	clrb	bflg

u0:	/ jmp, swab
u5:	/ single op
f5:	/ movei, movfi
ff1:	/ ldfps
ff2:	/ stfps
ff3:	/ stst
	mov	r1,r0
	br	setreg

t01:	/ mov
t02:	/ cmp
t03:	/ bit
t04:	/ bic
t05:	/ bis
t06:	/ add
t16:	/ sub
	clrb	bflg

t11:	/ movb
t12:	/ cmpb
t13:	/ bitb
t14:	/ bicb
t15:	/ bisb
	mov	r1,r0
	ash	$-6,r0
	jsr	pc,setreg
	swab	r2
	mov	r1,r0
	jsr	pc,setreg

/ if delta(dest) is zero,
/ no need to fetch source

	bit	$370,r2
	beq	1f

/ if mode(source) is R,
/ no fault is possible

	bit	$7000,r1
	beq	1f

/ if reg(source) is reg(dest),
/ too bad.

	mov	r2,-(sp)
	bic	$174370,(sp)
	cmpb	1(sp),(sp)+
	beq	u7

/ start source cycle
/ pick up value of reg

	mov	r1,r0
	ash	$-6,r0
	bic	$!7,r0
	movb	_regloc(r0),r0
	asl	r0
	add	ssr+2,r0
	mov	(r0),r0

/ if reg has been incremented,
/ must decrement it before fetch

	bit	$174000,r2
	ble	2f
	dec	r0
	bit	$10000,r2
	beq	2f
	dec	r0
2:

/ if mode is 6,7 fetch and add X(R) to R

	bit	$4000,r1
	beq	2f
	bit	$2000,r1
	beq	2f
	mov	r0,-(sp)
	mov	ssr+4,r0
	add	$2,r0
	jsr	pc,fetch
	add	(sp)+,r0
2:

/ fetch operand
/ if mode is 3,5,7 fetch *

	jsr	pc,fetch
	bit	$1000,r1
	beq	1f
	bit	$6000,r1
	bne	fetch
1:
	rts	pc

t17:	/ floating point instructions
	clrb	bflg
	mov	r1,r0
	swab	r0
	bic	$!16,r0
	jmp	*0f(r0)
0:		f0; f1; f2; f3; f4; f5; f6; f7

f0:
	mov	r1,r0
	ash	$-5,r0
	bic	$!16,r0
	jmp	*0f(r0)
0:		ff0; ff1; ff2; ff3; ff4; ff5; ff6; ff7

f1:	/ mulf, modf
f2:	/ addf, movf
f3:	/ subf, cmpf
f4:	/ movf, divf
ff4:	/ clrf
ff5:	/ tstf
ff6:	/ absf
ff7:	/ negf
	inc	fflg
	mov	r1,r0
	br	setreg

f6:
	bit	$400,r1
	beq	f1	/ movfo
	br	f5	/ movie

f7:
	bit	$400,r1
	beq	f5	/ movif
	br	f1	/ movof

ff0:	/ cfcc, setf, setd, seti, setl
u1:	/ br
u2:	/ br
u3:	/ br
u7:	/ illegal
	incb	jflg
	rts	pc

setreg:
	mov	r0,-(sp)
	bic	$!7,r0
	bis	r0,r2
	mov	(sp)+,r0
	ash	$-3,r0
	bic	$!7,r0
	movb	0f(r0),r0
	tstb	bflg
	beq	1f
	bit	$2,r2
	beq	2f
	bit	$4,r2
	beq	2f
1:
	cmp	r0,$20
	beq	2f
	cmp	r0,$-20
	beq	2f
	asl	r0
2:
	tstb	fflg
	beq	3f
	asl	r0
	stfps	r1
	bit	$200,r1
	beq	3f
	asl	r0
3:
	bisb	r0,r2
	rts	pc

0:	.byte	0,0,10,20,-10,-20,0,0

fetch:
	bic	$1,r0
	mov	nofault,-(sp)
	mov	$1f,nofault
	mfpi	(r0)
	mov	(sp)+,r0
	mov	(sp)+,nofault
	rts	pc

1:
 	mov	(sp)+,nofault
	clrb	r2			/ clear out dest on fault
	mov	$-1,r0
	rts	pc

.bss
bflg:	.=.+1
jflg:	.=.+1
fflg:	.=.+1
.text

.text

.globl	_fubyte, _subyte
.globl	_fuibyte, _suibyte
.globl	_fuword, _suword
.globl	_fuiword, _suiword
_fuibyte:
_fubyte:
	mov	2(sp),r1
	bic	$1,r1
	jsr	pc,gword
	cmp	r1,2(sp)
	beq	1f
	swab	r0
1:
	bic	$!377,r0
	rts	pc

_suibyte:
_subyte:
	mov	2(sp),r1
	bic	$1,r1
	jsr	pc,gword
	mov	r0,-(sp)
	cmp	r1,4(sp)
	beq	1f
	movb	6(sp),1(sp)
	br	2f
1:
	movb	6(sp),(sp)
2:
	mov	(sp)+,r0
	jsr	pc,pword
	clr	r0
	rts	pc
_fuiword:
_fuword:
	mov	2(sp),r1
fuword:
	jsr	pc,gword
	rts	pc

gword:
	mov	PS,-(sp)
	bis	$HIPRI,PS
	mov	nofault,-(sp)
	mov	$err,nofault
	mfpi	(r1)
	mov	(sp)+,r0
	br	1f

_suiword:
_suword:
	mov	2(sp),r1
	mov	4(sp),r0
suword:
	jsr	pc,pword
	rts	pc

pword:
	mov	PS,-(sp)
	bis	$HIPRI,PS
	mov	nofault,-(sp)
	mov	$err,nofault
	mov	r0,-(sp)
	mtpi	(r1)
1:
	mov	(sp)+,nofault
	mov	(sp)+,PS
	rts	pc

err:
	mov	(sp)+,nofault
	mov	(sp)+,PS
	tst	(sp)+
	mov	$-1,r0
	rts	pc
	rts	pc
.globl	_copyin, _copyout
.globl	_copyiin, _copyiout
_copyiin:
_copyin:
	jsr	pc,copsu
1:
	mfpi	(r0)+
	mov	(sp)+,(r1)+
	sob	r2,1b
	br	2f

_copyiout:
_copyout:
	jsr	pc,copsu
1:
	mov	(r0)+,-(sp)
	mtpi	(r1)+
	sob	r2,1b
2:
	mov	(sp)+,nofault
	mov	(sp)+,r2
	clr	r0
	rts	pc

copsu:
	mov	(sp)+,r0
	mov	r2,-(sp)
	mov	nofault,-(sp)
	mov	r0,-(sp)
	mov	10(sp),r0
	mov	12(sp),r1
	mov	14(sp),r2
	asr	r2
	mov	$1f,nofault
	rts	pc

1:
	mov	(sp)+,nofault
	mov	(sp)+,r2
	mov	$-1,r0
	rts	pc

.globl	_idle, _waitloc
_idle:
	mov	PS,-(sp)
	bic	$HIPRI,PS
	wait
waitloc:
	mov	(sp)+,PS
	rts	pc
	.data
_waitloc:
	waitloc
	.text

.globl	_save
_save:
	mov	(sp)+,r1
	mov	(sp),r0
	mov	r2,(r0)+
	mov	r3,(r0)+
	mov	r4,(r0)+
	mov	r5,(r0)+
	mov	sp,(r0)+
	mov	r1,(r0)+
	clr	r0
	jmp	(r1)

.globl	_resume
_resume:
	mov	2(sp),r0		/ new process
	mov	4(sp),r1		/ new stack
	bis	$HIPRI,PS
	mov	r0,KISA6		/ In new process
	mov	(r1)+,r2
	mov	(r1)+,r3
	mov	(r1)+,r4
	mov	(r1)+,r5
	mov	(r1)+,sp
	mov	$1,r0
	bic	$HIPRI,PS
	jmp	*(r1)+

.globl	_spl0, _spl1, _spl4, _spl5, _spl6, _spl7, _splx
_spl0:
	mov	PS,r0
	bic	$HIPRI,PS
	rts	pc

_spl1:
	mov	PS,r0
	bis	$HIPRI,PS
	bic	$300,PS
	rts	pc

_spl4:
	mov	PS,r0
	bis	$HIPRI,PS
	bic	$140,PS
	rts	pc

_spl5:
	mov	PS,r0
	bis	$HIPRI,PS
	bic	$100,PS
	rts	pc

_spl6:
	mov	PS,r0
	bis	$HIPRI,PS
	bic	$40,PS
	rts	pc

_spl7:
	mov	PS,r0
	bis	$HIPRI,PS
	rts	pc

_splx:
	mov	2(sp),PS
	rts	pc

.globl	_copyseg
_copyseg:
	mov	PS,-(sp)
	mov	UISA0,-(sp)
	mov	UISA1,-(sp)
	mov	$30340,PS
	mov	10(sp),UISA0
	mov	12(sp),UISA1
	mov	UISD0,-(sp)
	mov	UISD1,-(sp)
	mov	$6,UISD0
	mov	$6,UISD1
	mov	r2,-(sp)
	clr	r0
	mov	$8192.,r1
	mov	$32.,r2
1:
	mfpi	(r0)+
	mtpi	(r1)+
	sob	r2,1b
	mov	(sp)+,r2
	mov	(sp)+,UISD1
	mov	(sp)+,UISD0
	mov	(sp)+,UISA1
	mov	(sp)+,UISA0
	mov	(sp)+,PS
	rts	pc

.globl	_clearseg
_clearseg:
	mov	PS,-(sp)
	mov	UISA0,-(sp)
	mov	$30340,PS
	mov	6(sp),UISA0
	mov	UISD0,-(sp)
	mov	$6,UISD0
	clr	r0
	mov	$32.,r1
1:
	clr	-(sp)
	mtpi	(r0)+
	sob	r1,1b
	mov	(sp)+,UISD0
	mov	(sp)+,UISA0
	mov	(sp)+,PS
	rts	pc

.globl	_piget, _piput
_piget:
	mov	PS,-(sp)
	jsr	pc,2f
	mfpi	(r0)
	mov	(sp)+,r0
1:
	mov	(sp)+,PS
	rts	pc

_piput:
	mov	PS,-(sp)
	jsr	pc,2f
	mov	10(sp),r1
	mov	r1,-(sp)
	mtpi	(r0)
	br	1b
2:
	mov	6(sp),r0
	mov	10(sp),r1
	ashc	$-6,r0
	mov	HIPRI,PS
	mov	r1,KISA7
	mov	10(sp),r0
	bic	$!77,r0
	bis	$160000,r0
	rts	pc

/ Long quotient

	.globl	ldiv
ldiv:
	jsr	r5,csv
	mov	10.(r5),r3
	sxt	r4
	bpl	1f
	neg	r3
1:
	cmp	r4,8.(r5)
	bne	hardldiv
	mov	6.(r5),r2
	mov	4.(r5),r1
	bge	1f
	neg	r1
	neg	r2
	sbc	r1
	com	r4
1:
	mov	r4,-(sp)
	clr	r0
	div	r3,r0
	mov	r0,r4		/high quotient
	mov	r1,r0
	mov	r2,r1
	div	r3,r0
	bvc	1f
	sub	r3,r0		/ this is the clever part
	div	r3,r0
	tst	r1
	sxt	r1
	add	r1,r0		/ cannot overflow!
1:
	mov	r0,r1
	mov	r4,r0
	tst	(sp)+
	bpl	9f
	neg	r0
	neg	r1
	sbc	r0
9:
	jmp	cret

hardldiv:
	4

/ Long remainder

	.globl	lrem
lrem:
	jsr	r5,csv
	mov	10.(r5),r3
	sxt	r4
	bpl	1f
	neg	r3
1:
	cmp	r4,8.(r5)
	bne	hardlrem
	mov	6.(r5),r2
	mov	4.(r5),r1
	mov	r1,r4
	bge	1f
	neg	r1
	neg	r2
	sbc	r1
1:
	clr	r0
	div	r3,r0
	mov	r1,r0
	mov	r2,r1
	div	r3,r0
	bvc	1f
	sub	r3,r0
	div	r3,r0
	tst	r1
	beq	9f
	add	r3,r1
1:
	tst	r4
	bpl	9f
	neg	r1
9:
	sxt	r0
	jmp	cret

/ The divisor is known to be >= 2^15.	Only 16 cycles are
/ needed to get a remainder.
hardlrem:
	4

.globl	csv
csv:
	mov	r5,r0
	mov	sp,r5
	mov	r4,-(sp)
	mov	r3,-(sp)
	mov	r2,-(sp)
	jsr	pc,(r0)

.globl cret
cret:
	mov	r5,r2
	mov	-(r2),r4
	mov	-(r2),r3
	mov	-(r2),r2
	mov	r5,sp
	mov	(sp)+,r5
	rts	pc

.globl	_u
_u	= 140000
usize	= 16.

HIPRI	= 340

PS	= 177776
SSR0	= 177572
SSR2	= 177576
.if FORTYZ
SSR3	= 163676		/ addr of ENABLE's SSR3
SSR4	= 163674		/ addr of ENABLE's SSR4
KISA0	= 163700
KISA6	= 163714
KISA7	= 163776
UISA0	= 163720
UISA1	= 163722
PAR1	= 177640	/ the DEC user space PAR
PAR2	= 172340	/ the DEC kernal space PAR
BIT0	= 000001
BIT4	= 000020
IO22	= 000060	/ Turn both IO Mapping and 22 Bit Addressing
			/ This is sort of a crock but fixes a bug
			/ in the ENABLE board.  BOTH must be on for
			/ it to work.   ctc, sjh  03/20/81
IO	= 177600		/ ENABLE IO Register (16 bits wide)
IO1	= 7600			/ DEC IO Register (12 bits wide)
.endif
/ .if !FORTYZ
/ KISA0	= 172340
/ KISA6	= 172354
/ KISA7	= 172356
/ UISA0	= 177640
/ UISA1	= 177642
/ IO	= 7600
/ .endif
KISD0	= 172300
UISD0	= 177600
UISD1	= 177602
MTC	= 172522
TUC	= 172440


.data
.globl	_ka6
.globl	_cputype

_ka6:	KISA6
.if FORTYZ
_cputype: FORTYZ
.endif
/ .if !FORTYZ
/ _cputype: 40.
/ .endif
stk:	0

.bss
.globl	nofault
nofault:.=.+2
ssr:	.=.+6
saveps: .=.+2
power:	.=.+2
fpp:	.=.+2
.if TSDUMP
weof: .=.+2	/write EOF indicator
comts: .=.+12	/ts11 command packet
chrts: .=.+10	/ts11 characteristics
mests: .=.+16	/ts11 message buffer
.endif

.globl	_stst
.text
.globl	_stst
stst	= 170300^tst
_stst:
	tst	fpp
	beq	9f
	stst	r0
	mov	r0,*2(sp)
9:
	rts	pc
