mirror of
https://github.com/SEPPDROID/Digital-Research-Source-Code.git
synced 2025-10-24 17:04:19 +00:00
438 lines
12 KiB
Plaintext
438 lines
12 KiB
Plaintext
|
||
;*****************************************************
|
||
;*
|
||
;* Program Load
|
||
;*
|
||
;*****************************************************
|
||
|
||
;===========
|
||
cload_entry: ; entry point to load for a chain command
|
||
;===========
|
||
; Assumes UDA is set in passed PD.
|
||
|
||
push bx ! mov bx,1
|
||
jmps load
|
||
|
||
;==========
|
||
load_entry: ; User entry point to load .CMD file for execution
|
||
;==========
|
||
; input: DX = address of open FCB in u_wrkseg
|
||
; output: BX = segment addr of Base Page
|
||
; = 0ffffh if error
|
||
; CX = Error Code
|
||
|
||
sub bx,bx
|
||
;jmp load
|
||
;====
|
||
load: ; Intermodule entry point to load .CMD file
|
||
;====
|
||
; input: DX = addr of open FCB in u_wrkseg
|
||
; BX = addr of unused PD to initialize
|
||
; 0 - do not init PD
|
||
; 1 - chain load (PD addr on stack)
|
||
; output: BX = seg addr of Base Page
|
||
; = 0ffffh if error
|
||
; CX = Error Code
|
||
|
||
; Get MXLoad Queue
|
||
|
||
push dx ! push bx
|
||
mov cx,f_qread ! mov dx,offset mxloadqpb
|
||
call mpmif
|
||
mov load_chain,false
|
||
pop load_pd ! pop load_fcb
|
||
cmp load_pd,1 ! jne ld_read
|
||
pop load_pd ! mov load_chain,true
|
||
|
||
; Read the Header
|
||
|
||
ld_read:
|
||
mov bx,load_fcb
|
||
mov fcb_nxtrec[bx],0 ;read 1st record
|
||
mov dx,offset load_dma
|
||
mov cx,sysdat
|
||
call diskread ! jcxz have_header
|
||
jmp load_exit
|
||
have_header:
|
||
mov load_indma,0
|
||
|
||
; Initialize ldtab
|
||
|
||
; Zero ldtab
|
||
mov cx,ldtabsiz/2 ! sub ax,ax
|
||
mov di,offset ldtab
|
||
push es ! mov es,sysdat
|
||
rep stos ax ! pop es
|
||
; 1st ldtab entry is UDA and LSTK
|
||
; if a PD was specified...
|
||
mov load_nldtabents,0
|
||
mov si,offset ldtab
|
||
cmp load_pd,0 ! jne form_uda
|
||
jmp get_ch_info
|
||
form_uda: mov ldtab_min[si],(lstklen+ulen)/16 ;min=max=UDA+STK paragraphs
|
||
mov ldtab_max[si],(lstklen+ulen)/16
|
||
mov ax,load_pd ! mov ldtab_pd[si],ax
|
||
mov ldtab_attrib[si],mf_load
|
||
add si,ldtablen
|
||
inc load_nldtabents
|
||
cmp load_chain,true ! jne get_ch_info
|
||
|
||
;free any memory obtained by process
|
||
;except uda,ldstack segment
|
||
|
||
push si
|
||
mov bx,load_pd ! mov ax,p_uda[bx]
|
||
mov bx,rlr ! mov bx,p_mem[bx]
|
||
ld_fnext: cmp bx,0 ! je ld_freeit
|
||
cmp ms_start[bx],ax ! je ld_freenxt
|
||
and ms_flags[bx],not mf_load
|
||
ld_freenxt: mov bx,ms_link[bx] ! jmps ld_fnext
|
||
ld_freeit: push ax ! mov cl,0ffh ! push cx
|
||
push cx ! push cx
|
||
mov dx,sp ! mov cx,ss ! mov ds,cx
|
||
mov cx,f_freemem ! call mpmif
|
||
pop cx ! pop cx ! pop cx
|
||
mov ds,sysdat ! pop ax
|
||
|
||
; free load memory except uda,ldstack
|
||
|
||
mov bx,offset ldtab ! mov ldtab_start[bx],ax
|
||
sub cx,cx ! push cx
|
||
add ax,(lstklen+ulen)/16 ! push ax
|
||
mov dx,sp ! mov ax,ss ! mov ds,ax
|
||
mov cx,f_memfree ! call mpmif
|
||
pop ax ! pop ax
|
||
mov ds,sysdat
|
||
|
||
;transfer memory to new pd
|
||
|
||
mov bx,rlr
|
||
mov ax,p_mem[bx] ! mov p_mem[bx],0
|
||
mov bx,load_pd ! mov p_mem[bx],ax
|
||
pop si
|
||
|
||
get_ch_info:
|
||
;go through CMD header and init
|
||
;a ldtab entry per header entry.
|
||
;alloc abs mem
|
||
|
||
mov cx,ch_entmax ! mov bx,offset load_dma
|
||
mov dx,8 ; DX = position in file
|
||
ch_more:cmp ch_form[bx],0 ! jne ch_doit
|
||
jmp ch_next
|
||
ch_doit: mov al,ch_form[bx] ! mov ldtab_type[si],al ;type of seg
|
||
mov ax,ch_length[bx] ! mov ldtab_flen[si],ax ;length
|
||
mov ldtab_fstrt[si],dx ! add dx,ax ;pos in file
|
||
mov ax,ch_base[bx] ! mov ldtab_start[si],ax ;abs seg
|
||
mov ax,ch_min[bx] ! mov ldtab_min[si],ax ;min needed
|
||
mov ax,ch_max[bx]
|
||
cmp ax,0 ! jne setmax
|
||
mov ax,ch_min[bx]
|
||
setmax: mov ldtab_max[si],ax ;max wanted
|
||
mov ax,load_pd ! mov ldtab_pd[si],ax ;pd to alloc to
|
||
cmp ax,0 ! je not_load
|
||
mov ax,mf_load
|
||
jmps not_load
|
||
skipjmp:jmps ch_more
|
||
not_load: cmp ch_form[bx],1 ! jne try_shared
|
||
add ax,mf_code ! jmps set_attrib
|
||
try_shared: cmp ch_form[bx],9 ! jne set_attrib
|
||
add ax,mf_code+mf_share
|
||
set_attrib: mov ldtab_attrib[si],ax ;memory flags
|
||
;if abs, allocate memory
|
||
cmp ldtab_start[si],0 ! je ch_notabs ;see if abs mem
|
||
jmps ch_alloc
|
||
ch_notabs: cmp ldtab_type[si],9 ! jne ch_nxt ;see if shared code
|
||
ch_alloc: push bx ! push dx ! push cx ! push si
|
||
mov cx,f_malloc ! mov dx,si
|
||
call mpmif ! pop si
|
||
mov ax,ldtab_start[si] ! mov ldtab_id[si],ax
|
||
cmp cx,0 ! pop cx ! pop dx ! pop bx
|
||
je ch_nxt
|
||
;couldn't find memory
|
||
mov bx,0ffffh ! mov cx,e_no_memory
|
||
jmp load_giveup
|
||
ch_nxt: add si,ldtablen
|
||
inc load_nldtabents
|
||
ch_next:add bx,chlen
|
||
loop skipjmp
|
||
|
||
; alloc all other memory
|
||
; SI -> mpb for non_abs mem req.
|
||
;add all parts together for a single malloc
|
||
mov bx,offset ldtab
|
||
mov cx,load_nldtabents
|
||
mov load_nrelsegs,0
|
||
lt_more:cmp ldtab_min[bx],0 ! je lt_next
|
||
cmp ldtab_start[bx],0 ! jne lt_next
|
||
mov ax,ldtab_min[bx] ! add ldtab_min[si],ax
|
||
mov ax,ldtab_max[bx] ! add ldtab_max[si],ax
|
||
inc load_nrelsegs
|
||
lt_next:add bx,ldtablen ! loop lt_more
|
||
;malloc
|
||
mov ax,ldtab_max[si] ! mov load_maxwanted,ax
|
||
mov ax,ldtab_min[si] ! mov load_minwanted,ax
|
||
cmp load_pd,0 ! je noloadf
|
||
mov ldtab_attrib[si],mf_load
|
||
noloadf:mov ax,load_pd ! mov ldtab_pd[si],ax
|
||
push si ! mov dx,si ! mov cx,f_malloc
|
||
call mpmif ! pop si
|
||
mov ax,ldtab_start[si] ! mov ldtab_id[si],ax
|
||
cmp bx,0ffffh ! jne lt_spread
|
||
;Not Enough Memory - release any
|
||
; memory already allocated
|
||
load_giveup:push cx
|
||
mov bx,offset ldtab
|
||
mov cx,load_nldtabents ! inc cx
|
||
lg_more: cmp ldtab_id[bx],0 ! je lg_next
|
||
push cx ! push bx ! push ds
|
||
;push MFPB on stack
|
||
push ldtab_pd[bx]
|
||
push ldtab_id[bx]
|
||
mov dx,sp ! push ss ! pop ds
|
||
mov cx,f_memfree
|
||
call mpmif
|
||
pop cx ! pop cx
|
||
|
||
pop ds ! pop bx ! pop cx
|
||
lg_next: add bx,ldtablen ! loop lg_more
|
||
mov bx,0ffffh ! pop cx ! jmp load_exit
|
||
lt_spread:
|
||
;spread the memory allocated
|
||
;amongst the nrelsegs
|
||
ls_spread1: ;1st give everyone the minimum
|
||
mov bx,offset ldtab
|
||
mov cx,load_nldtabents
|
||
ls_more:cmp ldtab_start[bx],0 ! jne ls_next
|
||
mov ax,ldtab_min[bx]
|
||
sub ldtab_min[si],ax
|
||
cmp ax,ldtab_max[bx] ! jne ls_next
|
||
mov dx,ldtab_start[si] ! mov ldtab_start[bx],dx
|
||
add ldtab_start[si],ax
|
||
dec load_nrelsegs
|
||
ls_next:add bx,ldtablen ! loop ls_more
|
||
;spread whats left amongst those that need more
|
||
mov bx,offset ldtab
|
||
mov cx,load_nldtabents
|
||
lsl_mre:cmp ldtab_start[bx],0 ! jne lsl_nxt
|
||
mov ax,ldtab_start[si] ! mov ldtab_start[bx],ax
|
||
mov ax,ldtab_min[si]
|
||
cmp ax,0 ! je adj_start
|
||
push cx ! sub cx,cx
|
||
mov dx,cx ! mov cl,load_nrelsegs
|
||
div cx ! pop cx
|
||
cmp dx,0 ! je evendiv
|
||
inc ax
|
||
evendiv: mov dx,ldtab_max[bx] ! sub dx,ldtab_min[bx]
|
||
cmp ax,dx ! jbe nottoomuch
|
||
mov ax,dx
|
||
nottoomuch: add ldtab_min[bx],ax ! sub ldtab_min[si],ax
|
||
adj_start: mov ax,ldtab_min[bx] ! add ldtab_start[si],ax
|
||
dec load_nrelsegs
|
||
lsl_nxt:add bx,ldtablen ! loop lsl_mre
|
||
|
||
; fill memory from file
|
||
|
||
mov si,offset ldtab
|
||
mov cx,load_nldtabents
|
||
lf_mre: cmp ldtab_flen[si],0 ! je lf_nxt
|
||
push cx ! push ldtab_start[si] ! push si
|
||
call load_group
|
||
pop si ! pop ldtab_start[si]
|
||
cmp cx,0 ! pop cx
|
||
je lf_nxt
|
||
jmp load_giveup
|
||
lf_nxt: add si,ldtablen ! loop lf_mre
|
||
|
||
; init Base Page
|
||
; 1st Data Group has Base Page
|
||
; if none then first nonshared
|
||
; Code Group (8080 model)
|
||
|
||
mov load_8080,0
|
||
mov si,offset ldtab
|
||
mov cx,load_nldtabents
|
||
lb_more:cmp ldtab_type[si],2 ! je lb_found
|
||
add si,ldtablen ! loop lb_more
|
||
mov si,offset ldtab
|
||
mov cx,load_nldtabents
|
||
lbc_mre: cmp ldtab_type[si],1 ! je lb_found8080
|
||
add si,ldtablen ! loop lbc_mre
|
||
mov cx,e_no_cseg ! jmp load_giveup
|
||
lb_found8080: mov load_8080,1
|
||
lb_found:
|
||
push es ! mov es,ldtab_start[si]
|
||
mov load_basep,es
|
||
sub ax,ax ! mov di,ax
|
||
mov cx,05bh/2 ! rep stos ax
|
||
mov al,load_8080 ! mov es:.5,al
|
||
mov si,offset ldtab
|
||
mov cx,load_nldtabents
|
||
lbb_mre:cmp ldtab_type[si],0 ! je lbb_nxt
|
||
mov ax,6 ! mov bl,ldtab_type[si]
|
||
dec bl ! mul bl ! mov bx,ax
|
||
mov dx,ldtab_min[si] ! push dx
|
||
mov cl,12 ! shr dx,cl ! mov es:2[bx],dl
|
||
pop dx ! mov cl,4 ! shl dx,cl
|
||
dec dx ! mov es:[bx],dx
|
||
mov ax,ldtab_start[si] ! mov es:3[bx],ax
|
||
lbb_nxt:add si,ldtablen ! loop lbb_mre
|
||
|
||
;if 8080 model, copy CS info into DS info
|
||
|
||
cmp load_8080,1 ! jne lnot8080
|
||
push ds ! push es ! pop ds ! mov si,0
|
||
mov di,6 ! mov cx,3
|
||
rep movsw ! pop ds
|
||
lnot8080:
|
||
pop es
|
||
|
||
; init PD ,UDA and LDSTK
|
||
|
||
mov bx,load_basep
|
||
cmp load_pd,0 ! jne lip_1
|
||
jmp load_exit
|
||
lip_1: mov si,offset ldtab
|
||
mov bx,load_pd
|
||
mov ax,ldtab_start[si]
|
||
mov p_uda[bx],ax
|
||
; remember where lstk,uda are
|
||
mov load_uda,ax
|
||
push es ! mov es,ax
|
||
add ax,(ulen/16) ! mov load_lstk,ax
|
||
; initialize UDA,LDSTK with zeros
|
||
sub di,di ! mov ax,di
|
||
mov cx,(ulen + lstklen)/2
|
||
rep stos ax ! pop es
|
||
; setup p_uda for creat_proc
|
||
mov ax,sysdat
|
||
sub p_uda[bx],ax
|
||
mov p_stat[bx],ps_run
|
||
mov p_prior[bx],200
|
||
; init load disk/user
|
||
mov al,p_user[bx] ! mov p_luser[bx],al
|
||
mov al,p_dsk[bx] ! mov p_ldsk[bx],al
|
||
push es ! mov es,u_wrkseg
|
||
mov di,load_fcb
|
||
cmp es:byte ptr [di],0 ! je ldisk_set
|
||
mov al,es:[di] ! mov p_ldsk[bx],al
|
||
ldisk_set:
|
||
pop es
|
||
; init UDA
|
||
push es ! mov es,load_uda
|
||
mov u_dma_ofst,(offset bpg_dma)
|
||
mov bx,load_basep
|
||
mov u_dma_seg,bx
|
||
mov ax,load_lstk
|
||
push ds ! mov ds,bx
|
||
mov u_initds,bx
|
||
mov u_inites,bx
|
||
mov u_initss,ax
|
||
mov ax,bpg_cseg
|
||
cmp ax,0 ! jne have_cs
|
||
pop ds ! pop es ! mov cx,e_no_cseg
|
||
jmp load_giveup
|
||
have_cs:mov u_initcs,ax
|
||
mov ax,bpg_eseg
|
||
cmp ax,0 ! je noes
|
||
mov u_inites,ax
|
||
noes: mov u_stack_sp,(offset ls_sp)
|
||
sub dx,dx ! mov al,bpg_8080
|
||
cmp al,0 ! je not8080mod
|
||
mov dx,0100h
|
||
not8080mod:
|
||
mov ds,u_initss
|
||
mov ls_offset,dx
|
||
mov ls_flags,0200h
|
||
mov ls_roffset,offset user_retf
|
||
mov ls_rcseg,cs
|
||
pop ds ! pop es
|
||
mov bx,load_basep
|
||
sub cx,cx
|
||
load_exit:
|
||
push cx ! push bx
|
||
mov cx,f_qwrite ! mov dx,offset mxloadqpb
|
||
call mpmif ! pop bx ! pop cx ! ret
|
||
|
||
load_giveup1: jmp load_giveup
|
||
|
||
load_group: ;load a group described in ldtab
|
||
;----------
|
||
; input: SI = addr of ldtab entry
|
||
; output: CX = Error Code
|
||
|
||
; see if first part already in DMA
|
||
mov bx,si
|
||
mov ax,load_indma
|
||
mov cx,ldtab_fstrt[bx]
|
||
;CX = starting paragraph to transfer
|
||
;BX -> ldtab entry
|
||
cmp cx,load_indma ! jb read_first
|
||
;starts at or after the pp. in dma
|
||
sub cx,load_indma
|
||
cmp cx,8 ! jae read_first
|
||
;starts in the dma
|
||
mov dx,8 ! sub dx,cx
|
||
;CX = # of pp. to skip
|
||
;DX = length of remaining buffer
|
||
cmp dx,ldtab_flen[bx] ! jbe transfer
|
||
mov dx,ldtab_flen[bx]
|
||
transfer: mov si,offset load_dma
|
||
mov ax,cx ! mov cl,4 ! shl ax,cl
|
||
add si,ax
|
||
;SI -> beginning of transfer area
|
||
; in load_dma
|
||
mov ax,dx ! mov cl,3 ! shl ax,cl
|
||
mov cx,ax
|
||
;CX = number of words to transfer
|
||
sub di,di
|
||
push es ! mov es,ldtab_start[bx]
|
||
rep movsw ! pop es
|
||
add ldtab_start[bx],dx
|
||
sub ldtab_flen[bx],dx ! add ldtab_fstrt[bx],dx
|
||
read_first:
|
||
cmp ldtab_flen[bx],0 ! jne read_1st
|
||
sub cx,cx ! ret
|
||
read_1st:
|
||
cmp ldtab_flen[bx],8 ! jae xfer_direct
|
||
push bx ! mov dx,offset load_dma
|
||
mov cx,sysdat
|
||
call diskread ! pop bx
|
||
jcxz read_again
|
||
ret
|
||
read_again: mov ax,ldtab_fstrt[bx]
|
||
mov load_indma,ax
|
||
mov si,bx ! jmp load_group
|
||
xfer_direct:
|
||
push bx ! sub dx,dx
|
||
mov cx,ldtab_start[bx]
|
||
call diskread ! pop bx
|
||
jcxz xfer_1
|
||
ret
|
||
xfer_1: add ldtab_start[bx],8
|
||
add ldtab_fstrt[bx],8
|
||
sub ldtab_flen[bx],8
|
||
jmp read_first
|
||
|
||
diskread:
|
||
; input: DX = dma offset
|
||
; CX = dma segment
|
||
|
||
push es ! xchg dx,cx ! push cx
|
||
mov cx,f_setdmab ! call mpmif
|
||
|
||
pop dx ! mov cx,f_setdma
|
||
call mpmif ! pop es
|
||
|
||
mov cx,f_freadseq ! mov dx,load_fcb
|
||
push ds ! mov ds,u_wrkseg
|
||
push es ! call mpmif ! pop es ! pop ds
|
||
|
||
sub cx,cx
|
||
cmp bl,0ffh ! jne dr_ret
|
||
mov cx,e_bad_read ! mov bx,0ffffh ! ret
|
||
dr_ret: mov bx,rlr
|
||
test p_flag[bx],pf_ctlc ! jz dr_r1
|
||
mov cx,e_abort ! mov bx,0ffffh
|
||
dr_r1: ret
|
||
|