⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 excontxt.asm

📁 Dos6.0
💻 ASM
📖 第 1 页 / 共 2 页
字号:
					;  RUN is given from UI. Don't bother
					;  to init. stack in RunInit, since
					;  we will go back into UI and init.
					;  the stack on exit when we actually
					;  start running this program.
RunMain1:
	cCall	RunInit 		;context mgmt work to prepare to RUN
	and	[b$CtrlFlags],NOT NoSTACKINIT
					;reset to default
	mov	si,di			;put oTx in si where it belongs
	mov	bp,[b$mainframe]	;reset frame and stack pointers
 	mov	word ptr [bp],0		;reinitialize end of bp chain
 	mov	word ptr [bp].FR_basBpLink,0	
					; reinitialize end of BASIC bp chain
	mov	sp,bp
	mov	[b$curframe],bp	;required by RT error handling code
	mov	bx,[grs.GRS_oMrsCur]	
	RS_BASE add,bx			
	GETRS_SEG es			
	mov	cx,PTRRS[bx.MRS_cbFrameTemp]	
	add	cx,PTRRS[bx.MRS_cbFrameVars]	
	sub	sp,cx			;make room for module level frame stuff
	DbAssertTst   sp,z,1,CODE,<excontxt.asm: (1) SP contains an odd number>
	or	ax,ax			;error return from RunInit?
	jz	ContOTx1		;  brif not
	jmp	short J1_RtErrorCODE	;error occured in RunInit - abort RUN

ContOtx1:
	mov	[grs.GRS_fDirect],FALSE ;Move to program mode
	jmp	Start			;Load segment & msv, check BosFlags & go

;***
; Cont_Otx
; Entry:
;	si = otx to start executing pcode
;****
PUBLIC	Cont_Otx
Cont_Otx:
DbAssertRel grs.GRS_oRsCur,z,grs.GRS_oRsCONT,CODE,<excontxt.asm: attempt to CONTinute where oRsCur != oRsCONT>
	mov	al,ER_CN		;"Cannot Continue" error
	inc	si			;test for UNDEFINED
	je	J1_RtErrorCODE		;brif otx = FFFF (can't continue)
	dec	si			;ax = otx
	call	ContReinit		;compress Bd's & Bdl's, reinit 80[2]87
	jmp	SHORT ContOtx1

page


;***
;SetProgramMode
;Purpose:
;	Common initialization for all executors which (could) cause
;	start of execution in the current text table from Direct Mode.
;Input:
;	global state variables grs.GRS_fDirect, grs.GRS_otxCONT,
;	mrsCur
;Output:
;	CX is set to what grs.GRS_fDirect HAD been on input (fDirect is always
;	set false).
;	ES & DI set by a call to GetEsDi.
;Modifies:
;	ES, DI, BX, CX
;Preserves:
;	ax, si
;**********************************************************************
PUBLIC	SetProgramMode
SetProgramMode	PROC NEAR
	cmp	[grs.GRS_fDirect],FALSE
	jz	Direct_Exit		;brif fDirect already was false

	push	ax			;preserve across call
	call	ContReinit
	pop	ax
Direct_Exit:
	xor	cx,cx
	xchg	cl,[grs.GRS_fDirect]	;set fDirect to FALSE, cl to previous
	call	GetEsDi 		;es = text segment, di = pTVar
					; ax, cx and dx unmodified
					;  fDirect value
	ret
SetProgramMode	ENDP

;***
;exStRunLabel - RUN <line #> executor
;Purpose:
;	Run the current module from the given line number.
;Input:
;	An oTxt in the pcode stream at which to begin execution.
;Output:
;	none.
;Modifies:
;***************************************************************************
MakeExe exStRunLabel,opStRunLabel
	LODSWTX 			;ax = oTx of Ln|Label
	xchg	ax,di			;put oTx in di (not si, in case a
					;  runtime error occurs in Run_Otx)
	mov	ax,[grs.GRS_oMrsCur]	;in case we're in a procedure
	jmp	Run_Otx			;oTx set - start program

J4_RtErrorCODE: 			
; If we have gotten an error from LoadFile before we threw away
; our current context then the error is still trappable.  We
; don't want to reset the stack because an error handler could
; be invoked.
; otxRunSave = otxCur before LoadFile  si = otxCur after LoadFile.
; If they are the same then LoadFile didn't toss our context.

	cmp	[otxRunSave],si 	;can we trap this error?
	je	J1_RtErrorCODE		;brif so, don't blast stack

	mov	[b$ErrNum],ax		;preserve error code across call
	call	DoFBosResetStk		;bash stack so we don't try to
					;  return to code we've thrown out
	mov	ax,[b$ErrNum]		;restore error code

J1_RtErrorCODE:
	call	RtErrorCODE		;error code already in ax

;	Note: Above call does not return

GrabFailed:				
	mov	ax,ER_OM		; set up out of memory return value
	cmp	[fInitialized],FALSE	
J5_RTErrorCODE: 			
	jnz	J4_RtErrorCODE		; brif not a command-line run
	push	ax			; save error code
	call	ShowOutScr		; erase debug screen
	pop	ax			; restore ax = error code
	call	RtError_INI		

;	Note: Above call does not return


;***
;exStChain - CHAIN <filename> executor
;Purpose:
;	Chain to the given program
;Input:
;	psdFileName is on the stack
;Output:
;	none.
;Modifies:
;***************************************************************************
MakeExe exStChain,opStChain
	mov	[fChaining],TRUE
	call	ChainCommon		;replace all user-defined oTyps in
					;  blank COMMON type table with the
					;  size of the record (since we trash
					;  all existing module type tables
					;  prior to loading the new program)
	SkipExHeader			;fall into exStRunFile
;***
;exStRunFile - RUN <filename> executor
;Purpose:
;	Reset the existing context, Load the given file, and run it.
;
;	NOTE: There are two ways into this code -
;		(1) Normal pcode dispatch of 'RUN <filename>'
;		(2) From init.asm in the case that the user specified a
;		    filename on the command line.
;	      In case (2), we must handle an error from LoadFile as a
;	      fatal error.
;Input:
;	psdFileName is on the stack (used by LoadFile).
;Output:
;	none.
;Modifies:
;***************************************************************************
MakeExe exStRunFile,opStRunFile
	call	EnStaticStructs 	;activate static prsCur, mrsCur, txdCur
					; (required for calling LoadFile)
	mov	[grs.GRS_otxCur],si	;LoadFile will reset this to 0002
					; if an error occurs after the existing
					; text table is discarded.
	mov	[otxRunSave],si 	;remember otxCur for error recov
	or	[conFlags],F_CON_RunFile
					;don't make debug screen active

	call	GrabSpace		; make sure we don't overcommit
	jz	GrabFailed		; brif GrabSpace didn't work

	mov	ax,LF_NewDoc		; assume document file
	call	fEditorActive		; is the editor active?
	jnz	RunFileLoad		; brif so, load a document
	mov	ax,LF_NewProg		; else it is a program
RunFileLoad:				
	push	ax			; tell LoadFile what type of file
	call	LoadFile		; and all loaded programs should be
					; discarded before the load
	and	[conFlags],NOT F_CON_RunFile	;reset to default
	mov	si,[grs.GRS_otxCur]
	push	ax			;save retval across call
	call	DisStaticStructs	;ensure static structs deactivated again
	call	ReleaseSpace		; release space grabbed above
	pop	ax
	xor	cx,cx			
	xchg	[fChaining],cl		; ensure flag is set to FALSE here,
					;   and remember (in cx) whether
					;   or not we're chaining
	or	ax,ax			;0 if no error in load/save
	jz	RunFile_No_Error

	cmp	[fInitialized],FALSE
	jnz	J5_RtErrorCODE		;brif not a command-line run [17]
	push	ax			;save error code
	call	ShowOutScr		;erase debug screen before reporting err
	pop	ax			;restore ax = error code
	call	RtError_INI		;fatal error

RunFile_No_Error:
	cmp	[fInitialized],FALSE	;did we get here direct from init.asm?
	jnz	Not_Initializing	;  brif not

	and	[BosFlags],not FBOSRESETSTK
	mov	[fInitialized],TRUE	 ;ensure this flag gets set in case
					 ;we're command-line loading [& running]
					 ;a program
	test	[cmdSwitches],CMD_SW_RUN ;Want to Run program, or just load it?
	jnz	Not_Initializing	 ;  brif we do want to run it
	jmp	EndProg1		 ;just wanted to load program
Not_Initializing:
	mov	ax,codeOFFSET exStRunMain
	jcxz	Run_Or_Chain		;brif this is for RUN, not CHAIN
	mov	ax,codeOFFSET exCont	;so RunInit won't take place
Run_Or_Chain:
	;Don't bother to realloc the direct mode buffer - - - assume there's at
	;  least 2-bytes there, for an opEot which we can simply replace.
	DbAssertRel grs.GRS_bdlDirect_cbLogical,ae,2,CODE,<exStRunFile error>
	GETSEG	es,grs.GRS_bdlDirect_seg ; ax = seg adr of far heap entry
	mov	es:[0],ax
	or	[debugFlags],DEBUG_EXEC_CMD
					;Tell UserInterface to execute what it
					;  finds in the direct mode buffer
	and	[grs.GRS_flagsDir],NOT FDIR_cleared
					;note that world is no longer clear
	mov	[grs.GRS_fDirect],TRUE	;must set this back in case of
					;  something like NEW : PRINT
	jmp	EndProg1		;ends up triggering UserInterface

;***
;exCont - (pseudo) executor for CONTinue
;Purpose:
;	CONTinue program execution.  NOTE: This is not really a
;	statement, and there is no opcode for it.  The only time
;	this can ever execute is after the CHAIN stmt executor
;	stuffs exCont into the direct-mode buffer.
;Entry:
;	grs.oRsCONT, grs.otxCONT indicates where next statement
;	to be executed is.
;Exit:
;	none
;Uses:
;	none
;Exceptions:
;	Can cause "Cant continue" error
;
;***************************************************************************
MakeExe exCont,opStRunMain
;NOTE: opStRunMain for exCont is no mistake; there is no CONT opcode, but
;NOTE: we need this MakeExe because the executor is inserted into the Direct
;NOTE: mode buffer, and there is code which needs the MakeExe to properly
;NOTE: (and safely) determine if exCont can cause execution or not (so the
;NOTE: output screen is made active as appropriate, I believe ... see tomc)
	mov	si,[grs.GRS_otxCONT]
	jmp	Cont_Otx

;***
;exStClear - CLEAR statement executor
;Purpose:
;	Perform the CLEAR statement.
;Input:
;	all of the arguments are already on the stack, except for the
;		(2-byte) count of arguments.
;	Note that both flags and values are I4's. The count of arguments
;	is a count of I4's on the stack.
;
;Input Examples (Stack contents):
;
;	CLEAR ,2000				CLEAR 1000,,3000
;
;              +----+                                 +----+
;              |0000|                                 |FFFF|
;              +----+  Flag  (FALSE)                  +----+  Flag  (TRUE)
;              |0000|                                 |FFFF|
;              +----+                                 +----+
;              |FFFF|                                 |0000|
;              +----+  Flag  (TRUE)                   +----+  Value (1000)
;              |FFFF|                                 |03E8|
;              +----+                                 +----+
;              |0000|                                 |0000|
;              +----+  Value (2000)                   +----+  Flag  (FALSE)
;              |07D0|                                 |0000|
;              +----+                                 +----+
;                                                     |FFFF|
;                                                     +----+  Flag  (TRUE)
;                                                     |FFFF|
;                                                     +----+
;                                                     |0000|
;                                                     +----+  Value (3000)
;                                                     |0BB8|
;                                                     +----+
;
;	Note that this executor blasts and possibly alters the location
;	of the stack.
;Output:
;	none.
;Modifies:
;	sp, bp, b$mainframe, b$curframe, b$pend, b$pendchk
;***************************************************************************
MakeExe exStClear,opStClear
	;must check for Illegal Function Call due to current frame not being
	;set for main level code - - - this duplicates runtime functionality,
	;but we do it here so we don't end up in a partially cleared state
	;when the error occurs (and this way, user can still continue).
	mov	bx,bp
	cmp	[b$inonerr],FALSE	;in an error handler?
	jz	Got_Frame_Ptr		;  brif not

	mov	bx,[bx]			;if so, account for the fact that we've
					;  pushed a frame for the handler
Got_Frame_Ptr:
	cmp	bx,[b$mainframe]
	jz	Clear_Cont

	mov	al,ER_FC		;"Illegal Function Call"
J3_RtErrorCODE:
	jmp	J1_RtErrorCODE

Clear_Cont:
	call	WatchRelease		
	call	GetEsDi			
	call	PStepReset		;If stackSize changes, and user
					; is pStepping (F10) through a
					; CLEAR ,,0 stmt, make sure we stop.
					; Assumes CLEAR stmt never occurs within
					; a procedure (very safe assumption)
	xor	cx,cx			;assume no stack parameter
	xor	bl,bl			;count of parm flags seen so far
	LODSWTX 			;fetch count of args on stack
	or	ax,ax
	jz	StClear1		;brif no parms

	shl	ax,1
	shl	ax,1			;convert cI4Parms to cbParms on stack
	mov	di,sp
	add	di,ax			;di points to word above 1st parm

	;Stack contains I4 flags and I4 values - - - when I4 flag is FALSE,
	;I4 value is not present. The below code moves to the first flag
	;and loops for each flag, fetching or skipping value as appropriate
	;when flag is non-zero.
	;At this point, ONLY the cbStack value is kept, and CX is set to
	;non-zero if it is found.
Clear_Parm_Loop:
	dec	di
	dec	di
	mov	dx,[di]			;get high word of I4 flag
	dec	di
	dec	di
	mov	ax,[di]			;get low word of I4 flag
	inc	bl			;inc count of parm flags seen
	cmp	bl,4			;More than 3 parms?
	jb	Clear_Parm_Cont		;  brif not

	mov	al,ER_ADF		;Advanced feature unavailable error
	jmp	J3_RtErrorCODE
Clear_Parm_Cont:
	or	ax,dx			;test to see if I4 flag is zero or not
					;  if it is, ax will end up non-zero
	jz	No_Value		;brif flag is zero; no value to fetch

	cmp	bl,3			;is cbStack value available?
	jz	Fetch_CbStack		;brif so

	sub	di,4
	jmp	short No_Value		;ignore this value
Fetch_CbStack:
	dec	di
	dec	di
	mov	dx,[di]			;get high word of I4 value
	dec	di
	dec	di
	mov	ax,[di]			;get low word of I4 value
	push	dx
	push	ax
	call	I4toU2			;replace I4 on stack with U2
	pop	ax
	mov	cx,sp			;set fStack non-zero
No_Value:
	cmp	di,sp
	ja	Clear_Parm_Loop		;brif more parms to fetch

	DbAssertRel di,z,sp,CODE,<exStClear: sp and di not the same>
StClear1:
	push	ax			;cbStack or garbage
	push	cx			;fStack
	call	ClearStmt
	call	GrabSpace		;don't let the user grab ALL of avail.
					;  DGROUP for his stack
	mov	[grs.GRS_otxCur],si	;update in case of runtime error
	call	B$SCLR
	mov	[b$mainframe],sp	;reset the main level frame ptr - -
					; (other reset tasks are done by
					;  exBos/exBol)
	mov	bp,sp			;sp set to start of stack by B$SCLR
					;  (whether the stack parm given or not)
	call	ReleaseSpace		;return temporarily grabbed space to
					;  system
	jmp	DispMov			;jump to common dispatch point

sEnd	CODE
end

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -