home *** CD-ROM | disk | FTP | other *** search
- TTL AmigaDOS 68000 overlay supervisor
- **********************************************************
- * *
- * This version of the overlay supervisor is callable *
- * from C or Assembler; it will not work for MCC Pascal *
- * or BCPL which use a calling sequence where the called *
- * routine's address is saved on the stack. A different *
- * version of the overlay supervisor is available for *
- * case. *
- * *
- * The main overlay algorithm used here was originally *
- * described by Richard Evans at Cambridge University *
- * in about 1979. This code implementation was done by *
- * Tim King of Metacomco. *
- * *
- * Two main data structures are used: *
- * *
- * 1. The hunk table *
- * *
- * This table, giving the base addresses of all *
- * hunks currently loaded, is manufactured by *
- * the loader. Its address is planted in HTAB, *
- * and its first word is the address of hunk 0. *
- * Note that the addresses it contains are those *
- * of the link word of each hunk - not the first *
- * data word. *
- * *
- * 2. The overlay table *
- * *
- * This table is manufactured by the linkage *
- * editor, and its address is planted in OVTAB *
- * by the loader. It consists of two main *
- * parts, the ordinate table, and the overlay *
- * data table. The former is a table which is *
- * used to remember the ordinate number of each *
- * segment that is currently loaded. If n is the *
- * maximum level number, then the table contains *
- * n+1 entries, and the first word is n+2. The *
- * extra entry is required because a scan *
- * through the table below is terminated by a *
- * zero entry. All the entries are initially *
- * cleared by the linkage editor. The address *
- * of the overlay table, plus the contents of *
- * its first word (n+2), gives the address of *
- * the overlay data table, which is indexed by *
- * overlay number. Each entry in this table *
- * contains the following information, not *
- * necessarily in this order: *
- * *
- * 1. A file mark, generated by 'note', giving *
- * the position of the segment to be *
- * loaded. *
- * 2. The overlay level of the segment. *
- * 3. The overlay ordinate of the segment. *
- * 4. The initial hunk number of the segment. *
- * 5. The number of the hunk containing the *
- * symbol. *
- * 6. The offset of the symbol in the hunk. *
- * *
- * If an error is detected during overlaying, there is a *
- * limited choice of sensible actions, since the overlay *
- * supervisor can make no assumptions concerning the *
- * environment it was entered from. The action on an *
- * error is to call an Alert with the code for invalid *
- * overlay request. *
- * *
- * Note that the value in HTAB is a long word address, *
- * whilst that in OVTAB is a machine address. Each entry *
- * in the table is four bytes long. *
- * *
- **********************************************************
- * Change History:
- *
- * CARL 05SEP85
- * 1) Changes made (suggested by Paul) to the handling
- * of seek and loadseg errors. When an error
- * occurs, the program will retry until it is
- * successful.
- * 2) Changed bra.s to just bra in OVENT and OVENT2
- * macro definitions.
- * 3) Added the OVERLAYS equate and the necessary OVENT2
- * table entries (conditionally assembled).
- * 4) Eliminated unnecessary include files.
- * CARL 06SEP85
- * 1) CALL macro modified.
- * 2) CALL use modified.
- * DTM 15JUN87
- * 1) modified to either define or use static OCVs, or
- * Overlay Call Vectors, as we now call them.
- * 2) changed entry name to "_ovlyMgr" (note that the
- * underscore is added automatically, and case IS
- * very important
- * 3) added instruction to make sure that only lower
- * 16 bits of d0 are used in indexing into table;
- * the new dynamic OCVs only pass a word in d0,
- * although it's still multiplied by 8 and > 0.
- * 4) Basically all of this increase the total number
- * of OCVs to 8k, and furthermore makes it
- * possible to put this code into a library
-
- IFD NEWOCV
- IDNT newovs
- xdef @ovlyMgr
- ELSE
- IDNT ovs
- xdef ovlyMgr
- ENDC
-
-
- section NTRYHUNK,CODE
-
- INCLUDE "exec/types.i"
- INCLUDE "exec/tasks.i"
- INCLUDE "exec/libraries.i"
- INCLUDE "exec/alerts.i"
- INCLUDE "libraries/dos.i"
-
-
-
- FUNCDEF MACRO * function
- _LVO\1 EQU FUNC_CNT
- FUNC_CNT SET FUNC_CNT-6
- ENDM
-
- FUNC_CNT SET LIB_NONSTD
-
- INCLUDE "exec/exec_lib.i"
- INCLUDE "libraries/dos_lib.i"
-
-
- * Offsets within the overlay table.
- SysBase EQU 4
-
- OTMARK EQU 0 File position
- OTLEVL EQU 12 Level
- OTORD EQU 16 Ordinate
- OTIHNK EQU 20 Initial hunk for load
- OTRHNK EQU 24 Hunk containing symbol
- OTOFF EQU 28 Offset of symbol
- LIBWORD EQU 23456
-
-
- * A macro to call a LIBRARY routine:
- CALLS MACRO
- MOVEA.L SysBase.w,A6
- JSR _LVO\1(A6)
- ENDM
-
- * Call a library, save and restore A6.
- CALL MACRO ; CALL <library_vector_offset>,<library_pointer>
- MOVE.L A6,-(SP)
- MOVE.L \2,A6
- JSR _LVO\1(A6)
- MOVE.L (SP)+,A6
- ENDM
-
-
- * Now for the first word of the program.
-
- FIRST BRA.W NextModule
-
- * This next word serves to identify the overlay
- * supervisor to 'unloader'.
-
- DC.L $ABCD Special value
-
-
- * The loader plants values in the next locations.
-
- STREAM DC.L 0 Overlay input stream
- OVTAB DC.L 0 Overlay table (Machine address)
- HTAB DC.L 0 Hunk table (BCPL address)
- GLBVEC DC.L 0 Global vector (Machine address)
-
-
- *
- * The main code of the program.
- *
- CNOP 0,4
- DC.L LIBWORD
- DC.B 7,'Overlay'
-
- IFD NEWOCV
- @ovlyMgr
- OV1 movem.l a0-a6/d0-d7,-(sp)
- ELSE
- ovlyMgr
- OV1 MOVEM.L A2-A7/D2-D7,-(SP)
- ENDC
- MOVE.L OVTAB(PC),A3 Address of overlay table
- MOVEA.L A3,A4
- IFD NEWOCV
- moveq.l #0,d0
- move.l 4*15(a7),a0
- move.w (a0),d0
- ELSE
- AND.L #$0FFFF,D0 Make SURE that upper word is ZERO
- ENDC
- ADD.L (A3),D0 Add value in first word of table
- LSL.L #2,D0
- ADDA.L D0,A3 Address of overlay entry
- MOVE.L OTLEVL(A3),D0 Get required level
- LSL.L #2,D0
- ADDA.L D0,A4 Pointer to entry in ordinate table
- MOVE.L OTORD(A3),D0 Get required ordinate
- CMP.L (A4),D0 Compare with actual
- BEQ GOTSEG Branch if no load required
-
- * Now clear other entries in the ordinate table
-
- MOVE.L D0,(A4)+
- OV2 TST.L (A4) Table terminated by zero
- BEQ.S OV3
- CLR.L (A4)+
- BRA.S OV2
- *
- OV3 MOVE.L OTIHNK(A3),D0 First hunk number of overlay segment
- ADD.L HTAB(PC),D0
- LSL.L #2,D0 Address of entry in hunk table
- MOVEA.L D0,A4
- MOVE.L -4(A4),D0 Previous hunk
- BEQ.S OV5
- LSL.L #2,D0
- MOVEA.L D0,A6
- CLR.L (A6) Clear link field in case of error
-
- * Now free all the unwanted hunks ...
-
- OV4 TST.L (A4) Scan is terminated by zero
- BEQ OV5
- MOVE.L (A4)+,D1 Address as argument for 'freevec'
- FREEVEC TST.L D1
- BEQ.S FVC1 Return if V = 0
- ASL.L #2,D1 Back to mc address
- MOVEA.L D1,A1
- MOVE.L -(A1),D0 D0 = size
- MOVE.L D0,D1 Take copy
- ANDI.L #$FF000003,D1 Top byte and bottom 2 bits..
- BNE OVERR .. must be clear to be valid length
- CALL FreeMem,SysBase.w
- FVC1 BRA.S OV4 and again
-
- * Now save CIS and point the file
-
- OV5
- LEA.L LIBNAME(PC),A1
- MOVEQ #0,D0
- CALL OpenLibrary,SysBase.w
- MOVE.L D0,D7
- BEQ.S OVERR
-
- ADDA.L #OTMARK,A3 Address of file mark
-
- * Now seek to the segment and load it. If we fail (probably because
- * the user removed the disk, then retry until successful. This has
- * the effect of continually reprompting the user to insert the disk
- * until he obeys.
-
- OV_RETRY:
- MOVE.L STREAM(PC),D1 New stream
- MOVE.L (A3),D2
- MOVEQ #OFFSET_BEGINNING,D3 Offset to be from beginning
- CALL Seek,D7 Call 'point(scb,mark,o)'
- TST.L D0 Check result
- BMI.S OV_RETRY Branch if error
-
- ; Now call the loader again:
- MOVE.L HTAB(PC),D2 Hunk table (second parameter)
- MOVEQ #0,D1 Zero parameter for overlay
- MOVE.L STREAM(PC),D3
- CALL LoadSeg,D7
- TST.L D0 Check result
- BMI.S OV_RETRY Branch if error
-
- * Add new list to chain after previous one
-
- MOVE.L D1,(A6) Add new chain
-
- * Here when segment is in store: A3 holds table entry, A1 and D0 are free
-
- GOTSEG MOVE.L OTRHNK(A3),D0 Number of hunk containing symbol
- ADD.L HTAB(PC),D0
- LSL.L #2,D0 Machine address of entry in hunk table
- MOVEA.L D0,A4
- MOVE.L (A4),D0 BCPL address of hunk
- LSL.L #2,D0
- ADD.L OTOFF(A3),D0 Add in offset of symbol
-
- IFD NEWOCV
- * The address to jump to is now in D0. Place it on the stack so the RTS uses it.
- move.l d0,15*4(a7)
- movem.l (sp)+,a0-a6/d0-d7 * restore regs
- RTS * Jump to new code
- ELSE
- * The address to jump to is now in D0. Place it in A1 and jump to it.
- MOVEA.L D0,A1
- MOVEM.L (SP)+,A2-A7/D2-D7 restore regs
- JMP (A1) Jump to new code
- ENDC
-
- * Come here on an error during the overlay
-
- OVERR
- MOVE.L #AN_BadOverlay,D7
- CALLS Alert
- RTS
-
- * The code here will cause us to jump to the next segment in the list,
- * which should be the intended entry point.
-
- NextModule
- LEA.L FIRST(PC),A3 Pointer to start of module
- MOVE.L -4(A3),D7 Next BCPL word ptr
- ASL.L #2,D7 MC ptr to next module
- MOVE.L D7,A3 Into address register
- JMP 4(A3) Tally ho!
-
- * Data Area
-
- LIBNAME DC.B 'dos.library',0
- CNOP 0,4
-
-
- END
-