home *** CD-ROM | disk | FTP | other *** search
- PAGE 60, 132
- NAME expanded_memory_dispatcher_kernal
-
- ;-----------------------------------------------------------------------------;
- ; Placing null segment declarations at this point forces the segment ;
- ; order for the remainder of the program. ;
- ;-----------------------------------------------------------------------------;
-
- CODE SEGMENT PARA PUBLIC 'CODE'
- ORG 100h
- CODE ENDS
-
- DATA SEGMENT PARA PUBLIC 'DATA'
- DATA ENDS
-
- STACK SEGMENT PARA 'STACK'
- STACK ENDS
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; E Q U A T E S & M A C R O S ;
- ;-----------------------------------------------------------------------------;
- cr EQU 0Dh
- lf EQU 0Ah
-
- DISPLAY MACRO msg
- MOV AH, 09h
- LEA DX, msg
- INT 21h
- ENDM
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; D A T A S E G M E N T F O R T H E K E R N A L ;
- ;-----------------------------------------------------------------------------;
-
- DATA SEGMENT PARA PUBLIC 'DATA'
-
- ;-----------------------------------------------------------------------------;
- ; Messages. ;
- ;-----------------------------------------------------------------------------;
- signon_msg DB 'Intel Expanded Memory Code Load & Execute Demo', cr, lf
- DB '. ', cr, lf, '$'
- emm_check_msg DB '. Checking for EMM loaded', cr, lf, '$'
- emm_not_loaded_msg DB '. EMM not loaded', cr, lf, '$'
- alloc_exp_mem_msg DB '. Allocating & mapping expanded memory', cr, lf, '$'
- load_overlay_msg DB '. Loading overlay into expanded memory', cr, lf, '$'
- calling_overlay_msg DB '. Calling loaded code in expanded memory', cr, lf, '$'
- dealloc_exp_mem_msg DB '. Deallocating expanded memory', cr, lf, '$'
- emm_err_msg DB '. EMM error occurred', cr, lf, '$'
-
- ;-----------------------------------------------------------------------------;
- ; Name of pseudo-overlay. ;
- ;-----------------------------------------------------------------------------;
- pseudo_overlay_name DB 'OVERLAY.EXE', 0
-
- ;-----------------------------------------------------------------------------;
- ; Standard EMM device name. ;
- ;-----------------------------------------------------------------------------;
- EMM_device_name DB 'EMMXXXX0'
-
- ;-----------------------------------------------------------------------------;
- ; Miscellaneous temps. ;
- ;-----------------------------------------------------------------------------;
- exp_mem_segment DW ?
- EMM_handle DW ?
- com_file_entry_point DD ?
-
- ;-----------------------------------------------------------------------------;
- ; Structure definition for a DOS "load overlay" parameter block. ;
- ;-----------------------------------------------------------------------------;
- parm_block_struct STRUC
- load_segment DW ?
- reloc_factor DW ?
- parm_block_struct ENDS
- parm_block parm_block_struct <>
-
- DATA ENDS
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; C O D E S E G M E N T F O R T H E K E R N A L ;
- ;-----------------------------------------------------------------------------;
-
- CODE SEGMENT PARA PUBLIC 'CODE'
-
- ASSUME CS:CODE, DS:DATA, ES:NOTHING, SS:STACK
-
- ;-----------------------------------------------------------------------------;
- ; We will establish a convention in which the first object located at the ;
- ; expanded memory page frame will be a data structure which describes ;
- ; the data & extra segments of the loaded overlay, the number of procedure ;
- ; entry points in the loaded overlay, and a list of far pointers to ;
- ; each of the procedures contained in the pseudo-overlay which is to be ;
- ; loaded in expanded memory. The developer must establish a convention ;
- ; for the sequence of the far pointers and what the procedures they point ;
- ; to do. Other information could be passed in this structure as well. ;
- ; Such as, number and types of parameters which are be passed by the ;
- ; calling procedures to the called procedures in the pseudo-overlay. ;
- ; ;
- ; This example uses a literal to determine the maximum number of far ;
- ; pointers which may be passed. To allocate additional space for a larger ;
- ; number of entries, simply increase the value of max_proc_entries. The ;
- ; example assumes a MAXIMUM of 64 entries can be returned. ;
- ;-----------------------------------------------------------------------------;
-
- max_proc_entries EQU 64
-
- pseudo_overlay_entry_struct STRUC
- proc_data_segment DW ?
- proc_extra_segment DW ?
- proc_entry_count DW ?
- proc_entry_ptr DD max_proc_entries DUP (?)
- pseudo_overlay_entry_struct ENDS
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; This is an example of how a set of procedures may be loaded into ;
- ; expanded memory and invoked any time it is desired. The procedures ;
- ; contained in the loaded program may be called at any time the main ;
- ; program desires to do so. In this example, the program will be a ;
- ; collection of four procedures written in assembler. They could also be ;
- ; written in a high level language provided that the language is able to ;
- ; generate COM style files with the initialization code located at offset ;
- ; 100h. The language must also be able to perform a far return because ;
- ; the calls made to the loaded procedures are inter-segment calls. ;
- ; ;
- ; We will refer to this collection of loaded procedures as a ;
- ; pseudo-overlay. The program which loads the pseudo-overlay will be ;
- ; referred to as the kernal. This example kernal loads only a single ;
- ; pseudo-overlay and immediately invokes all the procedures contained in ;
- ; the overlay. A programmer could as easily load as many overlays as ;
- ; desired simply by allocating additional pages, mapping in four or fewer ;
- ; pages (depending on the length of the pseudo-overlay code), and then ;
- ; loading the pseudo-overlay. A key point to remember is that the ;
- ; maximum size of the expanded memory page frame is 64K bytes. So, the ;
- ; overlays loaded cannot exceed 64K bytes in length. However, the ;
- ; programmer can load as many of them as is desired by allocating the ;
- ; expanded memory required up to a maximum of 8M bytes. Another key point ;
- ; to remember is that although the DOS "load & execute" function was used ;
- ; to load the overlays, the code and any data which was loaded remains ;
- ; present after the load takes place. The procedures contained in the ;
- ; pseudo-overlay may be accessed by the use of the list of pointers ;
- ; returned to the kernal. ;
- ; ;
- ; What functions are contained in the overlays is left as an excercise of ;
- ; the fertile imaginations of developers. ;
- ;-----------------------------------------------------------------------------;
-
- main PROC NEAR
- ;---------------------------------------------------------------------;
- ; Initialization ;
- ;---------------------------------------------------------------------;
- MOV AX, DATA
- MOV DS, AX
- DISPLAY signon_msg
-
- check_for_emm_loaded:
- ;---------------------------------------------------------------------;
- ; Use the "interrupt vector" technique to determine whether ;
- ; EMM is loaded. ;
- ;---------------------------------------------------------------------;
- DISPLAY emm_check_msg
- CALL test_for_EMM
- JE get_emm_page_frame
- DISPLAY emm_not_loaded_msg
- JMP exit
-
- get_emm_page_frame:
- ;---------------------------------------------------------------------;
- ; Allocating expanded memory for overlay. ;
- ;---------------------------------------------------------------------;
- DISPLAY alloc_exp_mem_msg
-
- ;---------------------------------------------------------------------;
- ; Get the page frame base address from EMM. ;
- ;---------------------------------------------------------------------;
- MOV AH, 41h
- INT 67h
- OR AH, AH
- JZ allocate_64K
- JMP emm_err_exit
-
- allocate_64K:
- ;---------------------------------------------------------------------;
- ; Allocate 4 pages of expanded memory for this example. More can ;
- ; be allocated depending on the number of overlays to be loaded. ;
- ; Actually, in the case of this example, only a single page is ;
- ; required because the example pseudo-overlay is extremely small. ;
- ;---------------------------------------------------------------------;
- MOV exp_mem_segment, BX
- MOV AH, 43h
- MOV BX, 4
- INT 67h
- OR AH, AH
- JZ map_64K
- JMP emm_err_exit
-
- map_64K:
- ;---------------------------------------------------------------------;
- ; Map in the first 4 logical pages at physical pages 0 thru 3. ;
- ; logical page 0 at physical page 0 ;
- ; logical page 1 at physical page 1 ;
- ; logical page 2 at physical page 2 ;
- ; logical page 3 at physical page 3 ;
- ; If additional overlays were required, each overlay would be ;
- ; loaded after mapping and a new set of logical pages would be ;
- ; mapped at the same phisical pages. ;
- ;---------------------------------------------------------------------;
- MOV EMM_handle, DX
- MOV CX, 4
- map_pages_loop:
- MOV AH, 44h
- MOV BX, CX
- DEC BX
- MOV AL, BL
- MOV DX, EMM_handle
- INT 67h
- OR AH, AH
- LOOPE map_pages_loop
- JE initialize_load_structure
- JMP emm_err_exit
-
- initialize_load_structure:
- ;---------------------------------------------------------------------;
- ; Load the overlay. ;
- ;---------------------------------------------------------------------;
- DISPLAY load_overlay_msg
-
- ;---------------------------------------------------------------------;
- ; Initialize pseudo-overlay environment and procedure pointer area. ;
- ; This structure begins at the page frame segment address. ;
- ;---------------------------------------------------------------------;
- MOV ES, exp_mem_segment
- MOV DI, 0
- MOV CX, (SIZE pseudo_overlay_entry_struct)
- MOV AL, 0
- REP STOSB
-
- ;---------------------------------------------------------------------;
- ; Compute the load address within expanded memory for the overlay. ;
- ; The address is rounded up to the next higher paragraph boundary ;
- ; immediately following the pseudo-overlay environment & procedure ;
- ; pointer structure. This computation takes into account the ;
- ; maximum number of procedure entry points which the pseudo-overlay ;
- ; is going to return to this program. ;
- ;---------------------------------------------------------------------;
- MOV AX, (SIZE pseudo_overlay_entry_struct)
- ADD AX, 000Fh
- AND AX, 0FFF0h
- MOV CX, 4
- SHR AX, CL
- ADD AX, exp_mem_segment
- MOV parm_block.load_segment, AX
- MOV parm_block.reloc_factor, AX
-
- ;---------------------------------------------------------------------;
- ; Build the entry point for the .COM file in this example. ;
- ;---------------------------------------------------------------------;
- MOV WORD PTR com_file_entry_point[0], 100h
- MOV WORD PTR com_file_entry_point[2], AX
-
- ;---------------------------------------------------------------------;
- ; Load the pseudo-overlay using the DOS "load overlay" function. ;
- ;---------------------------------------------------------------------;
- MOV AH, 4Bh
- MOV AL, 03h
- LEA DX, pseudo_overlay_name
- PUSH DS
- POP ES
- LEA BX, parm_block
- INT 21h
- JC emm_err_exit
-
- ;---------------------------------------------------------------------;
- ; Transfer control to the loaded pseudo-overlays initialization ;
- ; code. ;
- ;---------------------------------------------------------------------;
- PUSH DS
- PUSH ES
- CALL DWORD PTR com_file_entry_point
- POP ES
- POP DS
- OR AH, AH
- JZ call_overlay_procedures
- JMP emm_err_exit
-
- call_overlay_procedures:
- ;---------------------------------------------------------------------;
- ; As an example of passing control to a procedure existing in ;
- ; expanded memory, each procedure contained in the overlay will be ;
- ; called in sequence. Obviously, a single procedure could be ;
- ; called just as easily. ;
- ;---------------------------------------------------------------------;
- MOV ES, exp_mem_segment
- MOV BX, 0
- MOV DI, 0
- MOV CX, ES:[BX].proc_entry_count
- JCXZ deallocate_exp_memory
-
- pseudo_overlay_call_loop:
- ;---------------------------------------------------------------------;
- ; Indicate that code in expanded memory is being called. ;
- ;---------------------------------------------------------------------;
- DISPLAY calling_overlay_msg
-
- ;---------------------------------------------------------------------;
- ; Call the procedures loaded in the overlay. ;
- ;---------------------------------------------------------------------;
- PUSH BX
- PUSH CX
- PUSH DI
- PUSH ES
- PUSH DS
-
- LDS AX, ES:[BX+DI].proc_entry_ptr
- MOV WORD PTR CS:temp_proc_entry_ptr[0], AX
- MOV WORD PTR CS:temp_proc_entry_ptr[2], DS
-
- ;---------------------------------------------------------------------;
- ; Pass 2 numbers to the procedures. ;
- ;---------------------------------------------------------------------;
- MOV AX, 123
- MOV DX, 23
-
- ;---------------------------------------------------------------------;
- ; Set up pseudo-overlays segment environment. Call each procedure. ;
- ;---------------------------------------------------------------------;
- MOV DS, ES:[BX].proc_data_segment
- MOV ES, ES:[BX].proc_extra_segment
- CALL DWORD PTR CS:temp_proc_entry_ptr
-
- POP DS
- POP ES
- POP DI
- POP CX
- POP BX
-
- ;---------------------------------------------------------------------;
- ; Adjust index to the next procedure (4 bytes long) pointer & loop ;
- ; till all have been called. ;
- ;---------------------------------------------------------------------;
- ADD DI, 4
- LOOP pseudo_overlay_call_loop
-
- deallocate_exp_memory:
- ;---------------------------------------------------------------------;
- ; Dellocating expanded memory for overlay. ;
- ;---------------------------------------------------------------------;
- DISPLAY dealloc_exp_mem_msg
-
- ;---------------------------------------------------------------------;
- ; Return the allocated pages to the expanded memory manager. ;
- ;---------------------------------------------------------------------;
- MOV AH, 45h
- MOV DX, EMM_handle
- INT 67h
- OR AH, AH
- JNZ emm_err_exit
-
- exit:
- ;---------------------------------------------------------------------;
- ; Return a normal exit code. ;
- ;---------------------------------------------------------------------;
- MOV AH, 4Ch
- MOV AL, 0
- INT 21h
-
- emm_err_exit:
- ;---------------------------------------------------------------------;
- ; Display the fact that an EMM error occurred & exit. ;
- ;---------------------------------------------------------------------;
- DISPLAY emm_err_msg
- MOV AH, 4Ch
- MOV AL, 1
- INT 21h
-
- ;---------------------------------------------------------------------;
- ; CS relative far pointer used for transfer to the procedures in ;
- ; the pseudo_overlay. ;
- ;---------------------------------------------------------------------;
- temp_proc_entry_ptr DD ?
-
- main ENDP
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; The following procedure tests for the presence of the EMM in the system. ;
- ; It returns the CARRY FLAG SET if the EMM is present. It returns the ;
- ; CARRY FLAG CLEAR if the EMM is not present. ;
- ;-----------------------------------------------------------------------------;
-
- test_for_EMM PROC NEAR
-
- ;---------------------------------------------------------------------;
- ; Issue "get interrupt vector" DOS call. ;
- ;---------------------------------------------------------------------;
- MOV AX, 3567h
- INT 21h
-
- ;---------------------------------------------------------------------;
- ; Use the SEGMENT in ES returned by DOS, place the "device name ;
- ; field" OFFSET in DI. ;
- ;---------------------------------------------------------------------;
- MOV DI, 000Ah
-
- ;---------------------------------------------------------------------;
- ; Place the OFFSET of the EMM device name string in SI, the SEGMENT ;
- ; is already in DS. ;
- ;---------------------------------------------------------------------;
- LEA SI, EMM_device_name
-
- ;---------------------------------------------------------------------;
- ; Compare the name strings. Return the status of the compare in ;
- ; the ZERO flag. ;
- ;---------------------------------------------------------------------;
- MOV CX, (SIZE EMM_device_name)
- CLD
- REPE CMPSB
- RET
-
- test_for_EMM ENDP
-
-
- CODE ENDS
-
-
- PAGE
- ;-----------------------------------------------------------------------------;
- ; S T A C K S E G M E N T F O R T H E K E R N A L ;
- ; A N D T H E P S E U D O - O V E R L A Y ;
- ;-----------------------------------------------------------------------------;
-
- STACK SEGMENT PARA STACK 'STACK'
- local_stack DW 256 DUP ('^^')
- STACK ENDS
-
- END main
-