mirror of
				https://github.com/SEPPDROID/Digital-Research-Source-Code.git
				synced 2025-10-26 01:44:21 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			487 lines
		
	
	
		
			10 KiB
		
	
	
	
		
			NASM
		
	
	
	
	
	
			
		
		
	
	
			487 lines
		
	
	
		
			10 KiB
		
	
	
	
		
			NASM
		
	
	
	
	
	
| $title('GETF  - CP/M 3.0 Input Redirection - August 1982')
 | ||
| 	name	getf
 | ||
| ;******************************************************************
 | ||
| ;
 | ||
| ;	get  'Input Redirection Initializer'  version 3.0
 | ||
| ;
 | ||
| ; 	11/30/82 - Doug Huskey
 | ||
| ;******************************************************************
 | ||
| ;
 | ||
| ;
 | ||
| ;	Copyright (c) 1982
 | ||
| ;	Digital Research
 | ||
| ;	P.O. Box 579
 | ||
| ;	Pacific Grove, Ca.
 | ||
| ;	93950
 | ||
| ;
 | ||
| ;
 | ||
| ;	generation procedure
 | ||
| ;
 | ||
| ;	seteof get.plm
 | ||
| ;	seteof getscan.dcl
 | ||
| ;	seteof getf.asm
 | ||
| ;	seteof getscan.plm
 | ||
| ;	seteof parse.asm
 | ||
| ;	is14
 | ||
| ;	asm80 getf.asm debug
 | ||
| ;	asm80 mcd80a.asm debug
 | ||
| ;	asm80 parse.asm debug
 | ||
| ;	plm80 get.plm pagewidth(100) debug optimize
 | ||
| ;	link mcd80a.obj,get.obj,parse.obj,getf.obj,plm80.lib to get.mod
 | ||
| ;	locate get.mod code(0100H) stacksize(100)
 | ||
| ;	era get.mod
 | ||
| ;	cpm
 | ||
| ;	objcpm get
 | ||
| ;	rmac getrsx
 | ||
| ;	link getrsx[op]
 | ||
| ;	era get.rsx
 | ||
| ;	ren get.rsx=getrsx.prl
 | ||
| ;	gencom get.com
 | ||
| ;	gencom get.com get.rsx 
 | ||
| ;	
 | ||
| ;
 | ||
| ;
 | ||
| ;	This module is called as an external routine by the
 | ||
| ;	PL/M routines GET and SUBMIT.  It is passed a structure
 | ||
| ;	with the following format:
 | ||
| ;
 | ||
| ;
 | ||
| ;		  declare getpb structure
 | ||
| ;		    (input$type   byte,
 | ||
| ;		     echo$flag     byte,
 | ||
| ;		     filtered$flag byte,
 | ||
| ;		     program$flag  byte);
 | ||
| ;
 | ||
| ;	input$type 	= 0     > console input (default)
 | ||
| ;		    	= 1     > auxiliary output
 | ||
| ;
 | ||
| ;	echo		= true  > echo input to real device
 | ||
| ;				  (default)
 | ||
| ;			= false > don't echo input (output is 
 | ||
| ;				  still echoed)
 | ||
| ;	filtered 	= true  > convert control characters
 | ||
| ;				  to a printable form 
 | ||
| ;			          preceeded by an ^ in echo
 | ||
| ;				  (default)
 | ||
| ;			= false > no character conversions
 | ||
| ;	program	 	= false > continue until EOF or 
 | ||
| ;				  GET INPUT FROM CONSOLE
 | ||
| ;			          command
 | ||
| ;			= true  > active only until program
 | ||
| ;				  termination
 | ||
| ;
 | ||
| 	public	getf
 | ||
| 	extrn	mon1,fcb,memsiz
 | ||
| ;
 | ||
| ;
 | ||
| true		equ	0ffffh
 | ||
| false		equ	00000h
 | ||
| ;
 | ||
| biosfunctions	equ	true		;intercept BIOS conin & constat 
 | ||
| ;
 | ||
| ;
 | ||
| ;	low memory locations
 | ||
| ;
 | ||
| wboot	equ	0000h
 | ||
| wboota	equ	wboot+1
 | ||
| ;
 | ||
| ;	equates for non graphic characters
 | ||
| ;
 | ||
| cr	equ	0dh	; carriage return
 | ||
| lf	equ	0ah	; line feed
 | ||
| ;
 | ||
| ;	BDOS function equates
 | ||
| ;
 | ||
| cinf	equ	1	;read character
 | ||
| coutf	equ	2	;output character
 | ||
| crawf	equ	6	;raw console I/O
 | ||
| creadf	equ	10	;read buffer
 | ||
| cstatf	equ	11	;status
 | ||
| pchrf	equ	5	;print character
 | ||
| pbuff	equ	9	;print buffer
 | ||
| openf	equ	15	;open file
 | ||
| closef	equ	16	;close file
 | ||
| delf	equ	19	;delete file
 | ||
| dreadf	equ	20	;disk read
 | ||
| dmaf	equ	26	;set dma function
 | ||
| curdrv	equ	25
 | ||
| userf	equ	32	;set/get user number
 | ||
| scbf	equ	49	;set/get system control block word
 | ||
| rsxf	equ	60	;RSX function call
 | ||
| initf	equ	128	;GET initialization sub-function no.
 | ||
| killf	equ	129	;GET delete sub-function no.
 | ||
| jkillf	equ	141	;JOURNAL delete sub-function no.
 | ||
| ;
 | ||
| ;	System Control Block definitions
 | ||
| ;
 | ||
| scba	equ	03ah	;offset of scbadr from SCB base
 | ||
| ccpflg2	equ	0b4h	;offset of 2nd ccp flag byte from pg bound
 | ||
| errflg	equ	0aah	;offset of error flag from page boundary
 | ||
| conmode	equ	0cfh	;offset of console mode from page boundary
 | ||
| listcp	equ	0d4h	;offset of ^P flag from page boundary
 | ||
| common	equ	0f9h	;offset of common memory base from pg. bound
 | ||
| wbootfx	equ	068h	;offset of warm boot jmp from page. bound
 | ||
| constfx	equ	06eh	;offset of constat jmp from page. bound
 | ||
| coninfx	equ	074h	;offset of conin jmp from page. bound
 | ||
| conoufx	equ	07ah	;offset of conout jmp from page. bound
 | ||
| listfx	equ	080h	;offset of list jmp from page. bound
 | ||
| realdos	equ	098h	;offset of real BDOS entry from pg. bound
 | ||
| ;
 | ||
| ;	Restore mode equates    (used with inr a, rz, rm, rpe, ret)
 | ||
| ;
 | ||
| norestore	equ	0ffh	;no BIOS interception
 | ||
| biosonly	equ	07fh	;restore BIOS jump table only
 | ||
| stfix	equ	080h	;restore BIOS jump table and
 | ||
| 				;restore JMP in RESBDOS for constat
 | ||
| everything	equ	0	;restore BIOS jump table and jmps in
 | ||
| 				;RESBDOS (default mode)
 | ||
| ;
 | ||
| ;	Instructions
 | ||
| ;
 | ||
| lxih		equ	21h	;LXI H, instruction
 | ||
| jmpi		equ	0c3h	;JMP instruction
 | ||
| shldi		equ	22h	;SHLD instruction
 | ||
| ;
 | ||
| ;******************************************************************
 | ||
| ;		START OF INITIALIZATION CODE
 | ||
| ;******************************************************************
 | ||
| 
 | ||
| 		cseg
 | ||
| 
 | ||
| getf:
 | ||
| 	;get parameters
 | ||
| 	mov	h,b
 | ||
| 	mov	l,c		;HL = .(parameter block)
 | ||
| 	mov	a,m		;input type 0=con:,1=aux:
 | ||
| 	cpi	1		;is it aux?
 | ||
| 	jz	notimp		;error if so
 | ||
| 	inx	h
 | ||
| 	mov	a,m		;echo/noecho mode
 | ||
| 	sta	echo
 | ||
| 	inx	h
 | ||
| 	mov	a,m		;cooked/raw mode	
 | ||
| 	sta	cooked	
 | ||
| 	inx	h
 | ||
| 	mov	a,m
 | ||
| 	sta	program
 | ||
| 	;
 | ||
| 	;check if enough memory
 | ||
| 	;
 | ||
| 	lhld	memsiz
 | ||
| 	mov	a,h
 | ||
| 	cpi	20h
 | ||
| 	jc	nomem
 | ||
| 	;
 | ||
| 	;close to get those blocks in the directory
 | ||
| 	;
 | ||
| 	lxi	d,fcb
 | ||
| 	mvi	c,closef
 | ||
| 	call	mon1
 | ||
| 	;
 | ||
| 	;check if drive specified
 | ||
| 	lxi	h,fcb
 | ||
| 	mov	a,m		;drive code
 | ||
| 	ora	a		;default?
 | ||
| 	jnz	movfcb
 | ||
| 	;
 | ||
| 	;set to current drive, if  not
 | ||
| 	;
 | ||
| 	push	h		;save .fcb
 | ||
| 	mvi	c,curdrv
 | ||
| 	call	mon1
 | ||
| 	pop	h		;a=current drive, hl=.fcb
 | ||
| 	inr	a
 | ||
| 	mov	m,a		;set fcb to force drive select
 | ||
| 	;
 | ||
| movfcb:	;copy default fcb up into data area for move to RSX
 | ||
| 	;
 | ||
| 	lxi	d,subfcb
 | ||
| 	lxi	b,32		;length of fcb
 | ||
| 	call	ldir		;move it to subfcb
 | ||
| 	;
 | ||
| 	;initialize other variables to be moved to RSX
 | ||
| 	;
 | ||
| 	call	getusr		;get current user number
 | ||
| 	sta	subusr		;save for redirection file I/O
 | ||
| 	call	getscbadr
 | ||
| 	shld	scbadr		;System Control Block address
 | ||
| 	;
 | ||
| 	;get real BDOS address (bypass chain to check for user break)
 | ||
| 	;
 | ||
| 	mvi	l,realdos
 | ||
| 	mov	e,m
 | ||
| 	inx	h
 | ||
| 	mov	d,m
 | ||
| 	xchg
 | ||
| 	shld	realbdos+1
 | ||
| 	;
 | ||
| 	;check for user abort
 | ||
| 	;
 | ||
| 	xchg
 | ||
| 	mvi	l,conmode
 | ||
| 	mov	a,m
 | ||
| 	ori	1		;set ^C status mode
 | ||
| 	mov	m,a
 | ||
| 	mvi	c,cstatf
 | ||
| 	call	realbdos	;check for user abort
 | ||
| 	ora	a
 | ||
| 	jnz	error1		;abort if so
 | ||
| 	;
 | ||
| 	;get address of initialization table in RSX
 | ||
| 	;
 | ||
| 	mvi	c,rsxf
 | ||
| 	lxi	d,journkill
 | ||
| 	call	mon1		;terminate any PUT INPUT commands
 | ||
| 	mvi	c,rsxf
 | ||
| 	lxi	d,rsxinit
 | ||
| 	call	mon1		;call GET.RSX initialization routine
 | ||
| 	push	h		;save for move at end of setup
 | ||
| 	mov	e,m
 | ||
| 	inx	h
 | ||
| 	mov	d,m		;DE = .RSXKILL flag 
 | ||
| 	push	d		;set flag to zero if successfull
 | ||
| 	inx	h		;HL = .(real bios status routine)
 | ||
| 	push	h
 | ||
| 	;
 | ||
| if biosfunctions
 | ||
| 	;
 | ||
| 	;check if BIOS jump table looks valid (jmp in right places)
 | ||
| 	lhld	wboota
 | ||
| 	lxi	d,3
 | ||
| 	dad	d		;HL = .(jmp constat address)
 | ||
| 	mov	a,m
 | ||
| 	cpi	jmpi		;should be a jump
 | ||
| 	jnz	bioserr		;skip bios redirection if not
 | ||
| 	dad	d		;HL = .(jmp conin address)
 | ||
| 	mov	a,m
 | ||
| 	cpi	jmpi
 | ||
| 	jnz	bioserr		;skip bios redirection if not
 | ||
| 	;
 | ||
| 	;fix up RESBDOS to do BIOS calls to intercepted functions
 | ||
| 	;
 | ||
| 	lhld	scbadr
 | ||
| 	mvi	l,common+1
 | ||
| 	mov	a,m		;get high byte of common base
 | ||
| 	ora	a		
 | ||
| 	jnz	fix0		;high byte = zero if non-banked
 | ||
| 	mvi	a,biosonly
 | ||
| 	sta	biosmode
 | ||
| 	jmp	trap		;skip code that fixes resbdos
 | ||
| 	;fix BIOS constat
 | ||
| fix0:	mvi	l,constfx		;hl = .constfx in SCB
 | ||
| 	mov	a,m
 | ||
| 	cpi	jmpi		;is it a jump instruction?
 | ||
| 	jz	fix1		;jump if so
 | ||
| 	mvi	a,biosonly	;whoops already changed
 | ||
| 	sta	biosmode	;restore jump table only
 | ||
| fix1:	mvi	m,lxih
 | ||
| 	;fix BIOS conin
 | ||
| 	mvi	l,coninfx	;hl = .coninfx in SCB
 | ||
| 	mov	a,m
 | ||
| 	cpi	jmpi		;is it a jump instruction?
 | ||
| 	lda	biosmode
 | ||
| 	jz	fix2		;jump if so
 | ||
| 	cpi	biosonly
 | ||
| 	jnz	bioserr		;error if conin is LXI but not constat
 | ||
| 	xra	a		;zero accumulator to jnz below
 | ||
| fix2:	cpi	biosonly	;was const already an LXI h?
 | ||
| 	jnz	fix3		;jmp if not
 | ||
| 	mvi	a,stfix	;restore constat jmp but not conin
 | ||
| 	sta	biosmode
 | ||
| fix3:	mvi	m,lxih
 | ||
| 	;get addresses of RSX const and conin traps
 | ||
| trap:	pop	h
 | ||
| 	mov  	c,m		;HL = .(.bios constat trap)
 | ||
| 	inx	h
 | ||
| 	mov	b,m		;BC = .bios constat trap in RSX
 | ||
| 	inx	h
 | ||
| 	push	h		;save for CONIN setup
 | ||
| 	;
 | ||
| 	;patch RSX constat entry into BIOS jump table 
 | ||
| 	;save real constat address in RSX exit table
 | ||
| 	;
 | ||
| 	lhld	wboota
 | ||
| 	lxi	d,4
 | ||
| 	dad	d		;HL = .(jmp constat address)
 | ||
| 	shld	constjmp	;save for RSX restore at end
 | ||
| 	mov	e,m
 | ||
| 	mov	m,c
 | ||
| 	inx	h
 | ||
| 	mov	d,m		;DE = constat address
 | ||
| 	mov	m,b		;BIOS constat jumps to RSX
 | ||
| 	xchg
 | ||
| 	shld	biosta		;save real constat address
 | ||
| 	;
 | ||
| 	;get address of RSX bios conin entry point
 | ||
| 	;
 | ||
| 	pop	h		;HL = .(RSX BIOS conin trap)
 | ||
| 	mov	c,m
 | ||
| 	inx	h
 | ||
| 	mov	b,m
 | ||
| 	;
 | ||
| 	;patch RSX conin entry into BIOS jump table 
 | ||
| 	;save real conin address in RSX exit table
 | ||
| 	;
 | ||
| 	xchg
 | ||
| 	inx	h		;past jmp instruction
 | ||
| 	inx	h		;HL = .(conin address)
 | ||
| 	shld	coninjmp
 | ||
| 	mov	e,m
 | ||
| 	mov	m,c
 | ||
| 	inx	h
 | ||
| 	mov	d,m		;DE = conin address
 | ||
| 	mov	m,b		;BIOS conin jumps to RSX
 | ||
| 	xchg
 | ||
| 	shld	biosin		;save real conin address
 | ||
| endif
 | ||
| 	;
 | ||
| 	;move data area to RSX
 | ||
| 	;
 | ||
| rsxmov:
 | ||
| 	pop	h		;HL = .Kill flag in RSX
 | ||
| 	inr	m		;switch from FF to 0
 | ||
| 	lxi	h,movstart
 | ||
| 	pop	d		;RSX data area address
 | ||
| 	lxi	b,movend-movstart
 | ||
| 	call	ldir
 | ||
| 	mvi	c,crawf
 | ||
| 	mvi	e,0fdh		;raw console input
 | ||
| 	call	mon1		;prime RSX by reading a char
 | ||
| 	jmp	wboot
 | ||
| 
 | ||
| if biosfunctions
 | ||
| ;
 | ||
| ;	can't do BIOS redirection
 | ||
| ;
 | ||
| bioserr:
 | ||
| 	lxi	d,nobios
 | ||
| 	mvi	c,pbuff
 | ||
| 	call	mon1
 | ||
| 	lxi	h,biosmode
 | ||
| 	mvi	m,norestore	;no bios redirection 
 | ||
| 	pop	h		;throw away bios constat trap adr
 | ||
| 	jmp	rsxmov
 | ||
| endif
 | ||
| ;
 | ||
| ;	auxiliary redirection
 | ||
| ;
 | ||
| notimp:
 | ||
| 	lxi	d,notdone
 | ||
| error:
 | ||
| 	mvi	c,pbuff
 | ||
| 	call	mon1	
 | ||
| error1:	mvi	c,closef
 | ||
| 	lxi	d,fcb
 | ||
| 	call	mon1
 | ||
| 	mvi	c,delf
 | ||
| 	lxi	d,fcb
 | ||
| 	call	mon1
 | ||
| 	jmp	wboot
 | ||
| ;
 | ||
| ;	insufficient memory
 | ||
| ;
 | ||
| nomem:	lxi	d,memerr
 | ||
| 	jmp	error
 | ||
| 	
 | ||
| ;
 | ||
| ;	get/set user number
 | ||
| ;
 | ||
| getusr:	mvi	a,0ffh		;get current user number
 | ||
| setusr:	mov	e,a		;set current user number (in A)
 | ||
| 	mvi	c,userf
 | ||
| 	jmp	mon1
 | ||
| ;
 | ||
| ;	get system control block address 
 | ||
| ;	(BDOS function #49)
 | ||
| ;
 | ||
| ;	exit:	hl = system control block address
 | ||
| ;
 | ||
| getscbadr:
 | ||
| 	mvi	c,scbf
 | ||
| 	lxi	d,data49
 | ||
| 	jmp	mon1
 | ||
| ;
 | ||
| data49:	db	scba,0		;data structure for getscbadd
 | ||
| ;
 | ||
| ;	copy memory bytes (emulates z80 ldir instruction)
 | ||
| ;
 | ||
| ldir:	mov	a,m		;get byte
 | ||
| 	stax	d		;store it at destination
 | ||
| 	inx	h		;advance pointers
 | ||
| 	inx	d
 | ||
| 	dcx	b		;decrement byte count
 | ||
| 	mov	a,c		;loop if non-zero
 | ||
| 	ora	b
 | ||
| 	jnz	ldir
 | ||
| 	ret
 | ||
| ;
 | ||
| ;******************************************************************
 | ||
| ;		DATA AREA
 | ||
| ;******************************************************************
 | ||
| 
 | ||
| 	;
 | ||
| journkill:	db	jkillf
 | ||
| rsxinit:	db	initf
 | ||
| nobios:		db	'WARNING: Cannot redirect from BIOS',cr,lf,'$'
 | ||
| notdone:
 | ||
| 	db 'ERROR: Auxiliary device redirection not implemented',cr,lf,'$'
 | ||
| memerr:
 | ||
| 	db 'ERROR: Insufficient Memory',cr,lf,'$'
 | ||
| 	;	
 | ||
| ;******************************************************************
 | ||
| ;	Following variables are initialized by GET.COM
 | ||
| ;	and moved to the GET RSX - Their order must not be changed
 | ||
| ;******************************************************************
 | ||
| 	;
 | ||
| 	;
 | ||
| 	;
 | ||
| movstart:
 | ||
| inittable:			;addresses used by GET.COM for 
 | ||
| scbadr:	dw	0		;address of System Control Block
 | ||
| 	;
 | ||
| 	if biosfunctions	;GET.RSX initialization
 | ||
| 	;
 | ||
| biosta:	dw	0		;set to real BIOS routine
 | ||
| biosin:	dw	0		;set to real BIOS routine
 | ||
| 	;
 | ||
| 				;restore only if changed when removed.
 | ||
| biosmode:
 | ||
| 	db	0		;if non-zero change LXI @jmpadr to JMP
 | ||
| 				;when removed.
 | ||
| restorebios:
 | ||
| 	;hl = real constat routine
 | ||
| 	;de = real conin routine
 | ||
| 	db	shldi
 | ||
| constjmp:
 | ||
| 	dw	0		;address of const jmp initialized by COM
 | ||
| 	xchg
 | ||
| 	db	shldi
 | ||
| coninjmp:
 | ||
| 	dw	0		;address of conin jmp initialized by COM
 | ||
| 	ret
 | ||
| 	endif
 | ||
| 	;
 | ||
| realbdos:
 | ||
| 	jmp	0		;address filled in by COM
 | ||
| 	;
 | ||
| echo:	db	1
 | ||
| cooked:	db	0
 | ||
| 	;
 | ||
| program:
 | ||
| 	db	0		;true if only program input 
 | ||
| subusr:	db	0		;user number for redirection file
 | ||
| subfcb:	db	1		;a:
 | ||
| 	db	'SYSIN   '
 | ||
| 	db	'SUB'
 | ||
| 	db	0,0
 | ||
| submod:	db	0
 | ||
| subrc:	db	0
 | ||
| 	ds	16		;map
 | ||
| subcr:	db	0
 | ||
| 	;
 | ||
| movend:
 | ||
| ;*******************************************************************
 | ||
| 	end
 | ||
| EOF
 | ||
| 
 | ||
|  |