home *** CD-ROM | disk | FTP | other *** search
- ;* GCRELOC.ASM
- ;************************************************************************
- ;* *
- ;* PC Scheme/Geneva 4.00 Borland TASM code *
- ;* *
- ;* (c) 1985-1988 by Texas Instruments, Inc. See COPYRIGHT.TXT *
- ;* (c) 1992 by L. Bartholdi & M. Vuilleumier, University of Geneva *
- ;* *
- ;*----------------------------------------------------------------------*
- ;* *
- ;* Relocate items to compact free space *
- ;* *
- ;*----------------------------------------------------------------------*
- ;* *
- ;* Created by: John Jensen Date: 1985 *
- ;* Revision history: *
- ;* - 18 Jun 92: Renaissance (Borland Compilers, ...) *
- ;* *
- ;* ``In nomine omnipotentii dei'' *
- ;************************************************************************
- IDEAL
- %PAGESIZE 60, 132
- MODEL medium
- LOCALS @@
-
- INCLUDE "scheme.ash"
-
- CODESEG
-
- ;************************************************************************
- ;* Garbage Collection -- Pointer Relocation Phase *
- ;************************************************************************
- PROC C srelocat USES si di
- LOCAL $$savedpage
-
- mov bx, DEDPAGES*2 ; relocate all pages except first
- @@pageloop:
- test [attrib+bx], NOMEMORY
- jnz @@pagedone
- mov di, [word ptype+bx]
- cmp di, FREETYPE ; Free Page?
- je @@pagedone
- push bx
- call rel_page ; relocate pointers in current page
- pop bx
- @@pagedone:
- add bx, 2 ; increment page counter
- cmp bx, NUMPAGES*2 ; all pages processed?
- jb @@pageloop
-
- lea di, [reg1] ; relocate registers R1-R63
- mov cx, NUM_REGS-1
- xor bx, bx
- @@regloop:
- call rel_reg C, di
- add di, size REG ; increment pointer to next register
- loop @@regloop ; loop until R1-R63 relocated
- call @REG@relocate$qv C ; relocate other internal registers
- mov cx, HT_SIZE ; relocate system oblist & property lists
- xor di, di
- @@tabloop:
- mov bl, [hash_page+di] ; fetch hash table entry
- shl di, 1
- mov si, [hash_disp+di]
- call rel_ptr
- mov [hash_disp+di], si ; store the relocated pointer
- shr di, 1
- mov [hash_page+di], bl
- mov bl, [prop_page+di] ; fetch property list entry
- shl di, 1
- mov si, [prop_disp+di]
- call rel_ptr
- mov [prop_disp+di], si ; store the relocated pointer
- shr di, 1
- mov [prop_page+di], bl
- inc di ; increment the loop index
- loop @@tabloop
-
- lea di, [s_stack] ; Relocate in the runtime stack
- mov dx, [topofstack]
- add dx, di ; compute stack's ending address
- @@stkloop:
- mov bl, [(POINTER di).page]; fetch next stack entry
- mov si, [(POINTER di).disp]
- call rel_ptr
- mov [(POINTER di).page], bl; store the relocated pointer
- mov [(POINTER di).disp], si
- add di, size POINTER ; increment the stack buffer pointer
- cmp di, dx ; top of stack ?
- jbe @@stkloop
-
- mov bl, [obj_hlist.page]
- mov si, [obj_hlist.disp]
- call rel_ptr
- mov [obj_hlist.page], bl ; store the relocated pointer
- mov [obj_hlist.disp], si
- @@return:
- ret
- ENDP srelocat
-
- ;************************************************************************
- ;* Local Support-- Relocate pointers in a single page *
- ;************************************************************************
- PROC rel_page near
- mov [$$savedpage], bx
- ldpage es, bx
- mov dx, [psize+bx]
- sub dx, SIZE POINTER ; adjust size of page boundary
- mov si, [word ptype+bx]
- xor di, di ; zero the page index
- xor bx, bx
- jmp [@@table+si]
- DATASEG
- @@table DW @@list ; [0] List cells
- DW @@fixnum ; [1] Fixnums
- DW @@flonum ; [2] Flonums
- DW @@bignum ; [3] Bignums
- DW @@symbol ; [4] Symbols
- DW @@string ; [5] Strings
- DW @@array ; [6] Arrays
- DW @@continuation ; [7] Continuations
- DW @@closure ; [8] Closures
- DW @@free ; [9] Free space (unallocated)
- DW @@code ; [10] Code
- DW @@inline ; [11] Inline code
- DW @@port ; [12] Port data objects
- DW @@char ; [13] Characters
- DW @@environment ; [14] Environments
- CODESEG
-
- @@list:
- sub dx, size LISTDEF - size POINTER
- @@listloop:
- mov bl, [(FREELISTDEF es:di).tag]
- cmp bl, SPECFREE*2
- je @@listdone
- test [(LISTDEF es:di).gc], GC_BIT
- jnz @@listdone
- ; mov bl, [(LISTDEF es:di).car.page] ; assuming the page is also here...
- mov si, [(LISTDEF es:di).car.disp]
- call rel_ptr ; relocate the CAR
- ldpage es, [$$savedpage]
- mov [(LISTDEF es:di).car.page], bl
- mov [(LISTDEF es:di).car.disp], si
- mov bl, [(LISTDEF es:di).cdr.page]
- mov si, [(LISTDEF es:di).cdr.disp]
- call rel_ptr ; relocate the CDR
- ldpage es, [$$savedpage]
- mov [(LISTDEF es:di).cdr.page], bl
- mov [(LISTDEF es:di).cdr.disp], si
- @@listdone:
- add di, SIZE LISTDEF ; increment the page index
- cmp di, dx ; end of page?
- jbe @@listloop
- jmp @@return
-
- @@symbol:
- @@port:
- @@symloop:
- cmp [(SYMDEF es:di).tag], FREETYPE ; free block?
- je @@symdone
- test [(SYMDEF es:di).gc], GC_BIT
- jnz @@symdone
- mov bl, [(SYMDEF es:di).link.page]
- mov si, [(SYMDEF es:di).link.disp]
- call rel_ptr ; relocate the link pointer
- ldpage es, [$$savedpage]
- mov [(SYMDEF es:di).link.page], bl
- mov [(SYMDEF es:di).link.disp], si
- @@symdone:
- add di, [(SYMDEF es:di).len] ; increment the page index
- cmp di, dx ; end of page?
- jbe @@symloop
- jmp @@return
-
- @@code:
- @@codeloop:
- cmp [(CODEDEF es:di).tag], FREETYPE ; is this a free block?
- je @@codedone
- test [(CODEDEF es:di).gc], GC_BIT
- jnz @@codedone
- push di ; save starting offset of object
- mov cx, [(CODEDEF es:di).entry.val] ; get ending offset
- add cx, di
- sub cx, OFFSET (TYPE CODEDEF).consts
- jmp @@codetest
- @@codemore:
- mov bl, [(CODEDEF es:di).consts.page]
- mov si, [(CODEDEF es:di).consts.disp]
- call rel_ptr ; relocate constant pointer
- ldpage es, [$$savedpage]
- mov [(CODEDEF es:di).consts.page], bl
- mov [(CODEDEF es:di).consts.disp], si
- add di, SIZE POINTER ; increment the page index
- @@codetest:
- cmp di, cx ; all pointers updated?
- jb @@codemore
- pop di ; restore starting offset of object
- @@codedone:
- add di, [(CODEDEF es:di).len] ; adjust index for free area
- cmp di, dx ; end of page?
- jbe @@codeloop
- jmp @@return
-
- @@array:
- @@continuation:
- @@closure:
- @@environment:
- @@anyloop:
- cmp [(FREEDEF es:di).tag], FREETYPE ; free block?
- je @@anydone
- test [(ANYDEF es:di).gc], GC_BIT
- jnz @@anydone
- mov ax, di ; save starting offset of object
- mov cx, [(ANYDEF es:di).len]; get ending offset
- add cx, di
- sub cx, OFFSET (TYPE STRDEF).buffer ; adjust ending offset for block header
- jmp @@anytest
- @@anymore:
- mov bl, [(ANYDEF es:di).data.page]
- mov si, [(ANYDEF es:di).data.disp]
- call rel_ptr ; relocate vector item
- ldpage es, [$$savedpage]
- mov [(ANYDEF es:di).data.page], bl
- mov [(ANYDEF es:di).data.disp], si
- add di, SIZE POINTER ; increment the page index
- @@anytest:
- cmp di, cx ; all pointers updated?
- jb @@anymore
- mov di, ax ; restore starting offset of object
- @@anydone:
- add di, [(ANYDEF es:di).len]
- cmp di, dx ; end of page?
- jbe @@anyloop
- jmp @@return
-
- @@fixnum:
- @@flonum:
- @@bignum:
- @@string:
- @@inline:
- @@free:
- @@char:
- @@return:
- ret
- ENDP rel_page
-
- ;************************************************************************
- ;* Local Support-- Relocate a pointer contained in a register *
- ;* *
- ;* Parameters: address of register *
- ;************************************************************************
- PROC C rel_reg USES si di, @@reg
- xor bx, bx
- mov di, [@@reg]
- mov bl, [(REG di).bpage]
- mov si, [(REG di).disp]
- call rel_ptr
- mov [(REG di).bpage], bl
- mov [(REG di).disp], si
- ret
- ENDP rel_reg
-
- ;************************************************************************
- ;* Local Support-- Relocate a single pointer *
- ;* *
- ;* Parameters: bx - page number index (page*2) *
- ;* si - displacement *
- ;************************************************************************
- PROC rel_ptr near
- cmp bx, DEDPAGES*2 ; is this a special non-GCed page?
- jl @@return
- push es di
- ldpage es, bx ; load the paragraph address for ptr's page
- mov di, [WORD ptype+bx]
- cmp di, NUMTYPES*2
- jae @@invalid
- jmp [@@table+di]
- DATASEG
- @@table DW @@list ; [0] List cells
- DW @@fixnum ; [1] Fixnums
- DW @@flonum ; [2] Flonums
- DW @@bignum ; [3] Bignums
- DW @@symbol ; [4] Symbols
- DW @@string ; [5] Strings
- DW @@array ; [6] Arrays
- DW @@continuation ; [7] Continuations
- DW @@closure ; [8] Closures
- DW @@free ; [9] Free space (unallocated)
- DW @@code ; [10] Code
- DW @@inline ; [11] Inline code
- DW @@port ; [12] Port data objects
- DW @@char ; [13] Characters
- DW @@environment ; [14] Environments
- CODESEG
-
- @@invalid:
- push ax cx dx
- lea ax, [@@msg]
- DATASEG
- @@msg DB "[VM INTERNAL ERROR] rel_ptr: invalid %x:%04x (unadjusted)", LF, 0
- CODESEG
- call zprintf C, ax, bx, si ; print the error message (page:disp)
- call force_debug ; invoke the VM debugger with next instr.
- pop dx cx ax
- jmp @@exit
-
- @@list:
- test [(LISTDEF es:si).gc], GC_BIT
- jz @@exit
- mov bl, [(LISTDEF es:si).ptr.page]
- mov si, [(LISTDEF es:si).ptr.disp]
- and bl, NOT GC_BIT
- jmp @@exit
-
- @@flonum:
- test [(FLODEF es:si).gc], GC_BIT
- jz @@exit
- mov bl, [(FLODEF es:si).ptr.page]
- mov si, [(FLODEF es:si).ptr.disp]
- jmp @@exit
-
- @@bignum:
- @@symbol:
- @@string:
- @@inline:
- @@array:
- @@continuation:
- @@closure:
- @@code:
- @@port:
- @@environment:
- test [(ANYDEF es:si).gc], GC_BIT
- jz @@exit
- mov bl, [(ANYDEF es:si).data.page]
- mov si, [(ANYDEF es:si).data.disp]
- ; jmp @@exit ; fall thru
-
- @@fixnum:
- @@free:
- @@char:
- @@exit:
- pop di es
- @@return:
- ret
- ENDP rel_ptr
-
- ;************************************************************************
- ;* Complement GC (forwarding) Bits *
- ;************************************************************************
- PROC C togglegc USES si di
- mov bx, DEDPAGES*2 ; initialize page counter
- @@loop:
- test [attrib+bx], NOMEMORY
- jnz @@done
- mov di, [WORD ss:ptype+bx] ; get data type for page
- cmp di, FREETYPE
- je @@done
- push bx
- call dopage ; complement GC bits in current page
- pop bx
- @@done:
- add bx, 2
- cmp bx, NUMPAGES*2 ; all pages processed?
- jb @@loop
- ret
-
- PROC dopage near
- ldpage es, bx
- mov dx, [psize+bx]
- sub dx, SIZE POINTER ; adjust for end of page boundary
- mov si, [WORD ptype+bx]
- xor di, di ; clear the page index
- xor bx, bx
- jmp [@@table+si]
- DATASEG
- @@table DW @@list ; [0] List cells
- DW @@fixnum ; [1] fixnums
- DW @@flonum ; [2] flonums
- DW @@bignum ; [3] bignums
- DW @@symbol ; [4] symbols
- DW @@string ; [5] strings
- DW @@array ; [6] Arrays
- DW @@continuation ; [7] continuations
- DW @@closure ; [8] closures
- DW @@free ; [9] Free space (unallocated)
- DW @@code ; [10] Code
- DW @@inline ; [11] Inline code
- DW @@port ; [12] Port data objects
- DW @@char ; [13] Characters
- DW @@environment ; [14] environmentironments
- CODESEG
-
- @@list:
- sub dx, SIZE LISTDEF - SIZE POINTER
- @@listloop:
- cmp [(FREELISTDEF es:di).tag], SPECFREE*2
- je @@listskip
- xor [(LISTDEF es:di).gc], GC_BIT
- @@listskip:
- add di, SIZE LISTDEF ; increment the page index
- cmp di, dx ; end of page?
- jbe @@listloop
- jmp @@return
-
- @@flonum:
- sub dx, SIZE FLODEF - SIZE POINTER
- @@flonumloop:
- cmp [(FREEFLODEF es:di).tag], FREETYPE
- je @@flonumskip
- xor [(FLODEF es:di).gc], GC_BIT
- @@flonumskip:
- add di, SIZE FLODEF ; increment the page index
- cmp di, dx ; end of page?
- jbe @@flonumloop
- jmp @@return
-
- @@string:
- @@inline:
- @@bignum:
- @@symbol:
- @@array:
- @@continuation:
- @@closure:
- @@code:
- @@port:
- @@environment:
- @@anyloop:
- cmp [(FREEDEF es:di).tag], FREETYPE
- je @@anyskip
- xor [(ANYDEF es:di).gc], GC_BIT
- @@anyskip:
- mov cx, [(ANYDEF es:di).len] ; adjust index for free area
- or cx, cx ; check for small stringing
- jge @@bigstring
- mov cx, OFFSET (TYPE STRDEF).buffer + SIZE POINTER
- @@bigstring:
- add di, cx
- cmp di, dx ; end of page?
- jbe @@anyloop
- jmp @@return
- @@fixnum:
- @@free:
- @@char:
- @@return:
- ret
- ENDP dopage
-
- ENDP togglegc
-
- END