[comp.sys.apple] Updating the System Global Page- ProDOS8

stern@dory.cis.ohio-state.edu (jeffrey a stern) (04/26/89)

I am writing my first system program and can execute the ProDOS MLI
QUIT call at the end pretty easily, but I am having trouble grasping
Apple's explanation of what I have to do at the *beginning* of the
program with the system bit map (I can install a version number of
my program-- it feels great!  Small time developer, here...).  Can
anyone explain how the system bit map is configured?  I'd greatly
appreciate it!

Thanks,

Jeff Stern

matthew@sunpix.UUCP ( Sun NCAA) (04/29/89)

In article <45357@tut.cis.ohio-state.edu}, stern@dory.cis.ohio-state.edu (jeffrey a stern) writes:
} 
} I am writing my first system program and can execute the ProDOS MLI
} QUIT call at the end pretty easily, but I am having trouble grasping
} Apple's explanation of what I have to do at the *beginning* of the
} program with the system bit map (I can install a version number of
} my program-- it feels great!  Small time developer, here...).  Can
} anyone explain how the system bit map is configured?  I'd greatly
} appreciate it!
} 
} Thanks,
} 
} Jeff Stern

What your asking about is quite simple.  ProDOS has a crude memory managment system
built into it.  There is a group of 18 bytes in the ProDOS Global page that the
ProDOS kernal can check to see if it is okay to read information into a particular
page of memory (the reference of 'page' is to a 256 byte area. I.E. page 0, page1,
page 2, ....).  This prevents ProDOS from overwriting things like Zero page, 
page 1 (the stack), pages 4 thru 7 (the text screen), etc, etc, etc.  System 
programs like 'BASIC.SYSTEM' use the ProDOS Global page's bitmap to protect 
themselves for overwriting.  Often these programs do not cleanup this bitmap upon 
execution, and since the ProDOS kernal leaves ProDOS Global page bitmap managment 
up to the system program, its up to the system program to cleanup the bitmap to 
its needs.


Each bit in the bitmap has its corresponding page in memory. With 8 bits per
byte, and 18 bytes in the bitmap, show that only the memory from $0000 thru $BFFF
is covered. The bitmap physically resides at $BF58 thru $BF6F. It will always 
reside at this address, and there are no pointers to it. The correlation is 
the bit 7 of $BF58 is page 0, bit 6 of $BF58 is page 1, ...., bit 0 of $BF6F is
page $BF. A 1 in a bit position means that that page is protected. A 0 means that
that page is unprotected.  The pages 0, 1, 4, 5, 6, 7, and $BF should normally
stay protected. The other pages may be protected as your system program needs.


This bitmap can be initialized several ways.  The two popular ways are default-
copy-from-table, and default-on-the-fly. The first way is the fastest, and most 
flexible in including your own protected pages in the default bitmap. It is simply 
the copy of a 18 byte table from your program to $BF58. The code is in example 1.  
The second is slightly slower and smaller, and does not require a default table in 
the program, but is inflexible if you need to set more than the default bitmap. 
The code is in example 2.

Example #1 ----------------------------- 37 bytes ---------------------------

		ldy	#$11		;point to the last item in the list
	mvloop	lda	table,y		;get a byte
		sta	$BF58,y		;put it in the bitmap
		dey
		bpl	mvloop		;if not done....
 
	table	dc	$CF, $00, $00, $00, $00, $00, $00, $00 
		dc	$00, $00, $00, $00, $00, $00, $00, $00 
		dc	$00, $00, $00, $00, $00, $00, $00, $01 


Example #2 ----------------------------- 16 bytes --------------------------

		ldy	#$11		;point to the last item in the list
		lda	#$01		;set $BF page
	setloop	sta	$BF58,y		;put it in the bitmap
		lsr	a		;zero the accumulator
		dey
		bne	setloop		;set all byte but $BF58
		lda	$CF		;get the mask for $BF58
		sta	$BF58		;and set it.


Others function you may want to have are PROTECT-PAGE, UNPROTECT-PAGE, and 
TEST-PAGE.  These functions, would do as requested, and either set or clear
the bit in the bitmap for a particular page, or return the status of a 
particular page. Here is some sample code:



	test	jsr	locate		;get the byte offset and mask
		lda	$BF58,y		;get the byte from the bitmap
		and	mask		;isolate to the individual bit
		rts			;if zero, page is unprotected

	set	jsr	locate		;get the byte offset and mask
		lda	$BF58,y		;get the byte from the bitmap
		or 	mask		;Set the individual bit
		sta	$BF58,y		;and put it back
		rts

	clear	jsr	locate		;get the byte offset and mask
		lda	mask		;get the mask
		eor	#$FF		;and complement is
		and	$BF58,y		;get the byte from the bitmap
		sta	$BF58,y		;clear the individual bit
		rts			;and put it back

	locate	pha			;save the page number
		and 	#$07		;get the index for the bitmask
		tay	
		lda	bitmask,y	;get the bitmask
		sta	mask		;and save it
		pla			;restore the page number
		lsr	a		;divide by 8 to get the bitmap byte
		lsr	a
		lsr	a
		tay
		rts

	mask	ds	1
	bitmask	dc	$80, $40, $20, $10, $08, $04, $02, $01	



I've rambled on long enough about this, and probably feed you more than you wanted
to know.


-- 
Matthew Lee Stier                         |
Sun Microsystems ---  RTP, NC  27709-3447 |        "Wisconsin   Escapee"
uucp: { sun, mcnc!rti }!sunpix!matthew    |
phone: (919) 469-8300 fax: (919) 460-8355 |