 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	1-1
RHBOOT -- BOOTSTRAP LOAD PROGRAM


 	 	 	 	;
 	 	 	 	 	page	86,131
 	 	 	 	 	title	RHBOOT -- BOOTSTRAP LOAD PROGRAM
 	 	 	 	;* -------------------------------------------------------------------
 	 	 	 	;*	RHBOOT.COM is a sample Remote Program Load program.
 	 	 	 	;*
 	 	 	 	;*	(C) Copyright IBM Corp., 1986
 	 	 	 	;*	This program is the property of IBM.  All rights reserved.
 	 	 	 	;*
 	 	 	 	;*	RHBOOT.COM is exactly 512.  The last 6 bytes contain
 	 	 	 	;*	a diskette header initialized to the default values
 	 	 	 	;*	for a single sided 8 sector per track 160K diskette.
 	 	 	 	;*	Refer to the IBM Token-Ring Remote Program Load User's
 	 	 	 	;*	Guide for more details on the diskette header.
 	 	 	 	;*
 	 	 	 	;*	RHBOOT.COM is designed to have a DOS system diskette image
 	 	 	 	;*	appended to it.  Refer to documentation on GEMIMAG.COM
 	 	 	 	;*	for instructions on how to create this image.
 	 	 	 	;*
 	 	 	 	;*	RHBOOT.COM computes the diskette image size from the
 	 	 	 	;*	data in the header; reduces memory size for DOS
 	 	 	 	;*	the amount of space required for the diskette image
 	 	 	 	;*	and header; moves the diskette image and header to
 	 	 	 	;*	high memory; initializes the pointer to the diskette
 	 	 	 	;*	image header for the disk drive emulator; issues a
 	 	 	 	;*	DIR.CLOSE.ADAPTER command; and transfers control
 	 	 	 	;*	through  XFER.ADDR  to force a reboot from the
 	 	 	 	;*	relocated system diskette image.
 	 	 	 	;*
 	 	 	 	;*
 	 	 	 	;* -------------------------------------------------------------------
 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	1-2
RHBOOT -- BOOTSTRAP LOAD PROGRAM


 	 	 	 	 	page
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 EQUATES
 	 	 	 	;**********************************************************************
 = 0006	 	 	 	HDR_SIZE	equ	6
 = 0012	 	 	 	MEM_SIZE	equ	12h
 = 0120	 	 	 	DISK_ADDR	equ	0120h
 = 0413	 	 	 	DOS_MEM 	equ	0413h
 = 068C	 	 	 	XFER_ADDR	equ	068ch
 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	1-3
RHBOOT -- BOOTSTRAP LOAD PROGRAM


 	 	 	 	 	page
 0000	 	 	 	code	segment 	public
 	 	 	 	 	public	rhboot
 0000	 	 	 	rhboot	proc	far
 	 	 	 	 	assume	cs:code,ds:code
 	 	 	 	;
 0000	 	 	 	start:
 0000  E8 0003 R	 	 	call	setds	 	; GET INSTRUCTION POINTER
 0003	 	 	 	setds:
 0003  5E	 	 	 	pop	si	 	; SI = INSTRUCTION POINTER
 0004  8B C6	 	 	 	mov	ax,si	 	; AX = INSTRUCTION POINTER
 0006  D1 E8	 	 	 	shr	ax,1	 	; AX = IP / 02
 0008  D1 E8	 	 	 	shr	ax,1	 	; AX = IP / 04
 000A  D1 E8	 	 	 	shr	ax,1	 	; AX = IP / 08
 000C  D1 E8	 	 	 	shr	ax,1	 	; AX = IP / 16
 000E  8C CF	 	 	 	mov	di,cs	 	; DI = CODE SEGMENT
 0010  03 F8	 	 	 	add	di,ax	 	; DI = NORMALIZED SEGMENT
 0012  81 E6 000F	 	 	and	si,0fh	 	; DI:SI = NORMALIZED HEADER @
 	 	 	 	 	 	 	 	; SI = DISKETTE HEADER OFFSET
 0016  81 C6 01F7	 	 	add	si,offset header-setds
 001A  8E DF	 	 	 	mov	ds,di	 	; DS:SI = DISKETTE IMAGE HEADER @
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 CALCULATE SIZE OF DISKETTE IMAGE IN BYTES	 	      *
 	 	 	 	;**********************************************************************
 001C  A0 01FA R	 	 	mov	al,heads	; AL = NUMBER OF HEADS
 001F  F6 26 01FC R	 	 	mul	sectors 	; AX = HEADS * SECTORS
 0023  F6 26 01FB R	 	 	mul	tracks	 	; AX = HEADS * SECTORS * TRKS
 0027  F7 26 01FD R	 	 	mul	sec_size	; DX:AX = DISK IMAGE SIZE w/o header
 002B  05 0006	 	 	 	add	ax,HDR_SIZE	; DX:AX = DISK IMAGE SIZE w/ header
 002E  83 D2 00	 	 	 	adc	dx,0	 	; ADJUST FOR THE CARRY FLAG
 0031  8B D8	 	 	 	mov	bx,ax	 	; BX = SEGMENT SIZE
 0033  8B EA	 	 	 	mov	bp,dx	 	; BP:BX = SIZE OF DISK IMAGE
 0035  B9 0010	 	 	 	mov	cx,16	 	; CX = DIVISOR
 0038  F7 F1	 	 	 	div	cx	 	; AX = SEGMENT; DX = OFFSET
 003A  03 C7	 	 	 	add	ax,di	 	; AX = LAST DATA SEGMENT
 003C  03 F2	 	 	 	add	si,dx	 	; SI = LAST DATA OFFSET
 003E  73 03	 	 	 	jnc	rhboot01	; CF = 1 ==> OVERFLOW
 0040  80 C4 10	 	 	 	add	ah,16	 	; ADJUST FOR NEXT 64K SEGMENT
 0043	 	 	 	rhboot01:
 0043  8E D8	 	 	 	mov	ds,ax	 	; DS:DX = LAST @ OF DISK IMAGE
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 GET MEMORY SIZE IN K BYTES	 	 	 	      *
 	 	 	 	;**********************************************************************
 0045  CD 12	 	 	 	int	MEM_SIZE	; AX = # OF K BYTES OF MEMORY
 0047  B9 0040	 	 	 	mov	cx,1024/16	; CONVERT AX TO A SEGMENT
 004A  F7 E1	 	 	 	mul	cx	 	; AX = LAST VALID SEGMENT OF MEMORY
 004C  8B FA	 	 	 	mov	di,dx	 	; AX:DI = DESTINATION @
 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	1-4
RHBOOT -- BOOTSTRAP LOAD PROGRAM


 	 	 	 	 	page
 	 	 	 	;**********************************************************************
 	 	 	 	;	 ADJUST SEGMENT REGISTERS	 	 	 	      *
 	 	 	 	;**********************************************************************
 004E  FD	 	 	 	std	 	 	; DF = 1 ==> BACKWARD
 004F  4E	 	 	 	dec	si	 	; DS:SI = SOURCE @
 0050  4F	 	 	 	dec	di	 	; ES:DI = DESTINATION @
 0051	 	 	 	rhboot02:
 0051  B9 FFFF	 	 	 	mov	cx,0ffffh	; CX = COMPARE VALUE
 0054  8B D0	 	 	 	mov	dx,ax	 	; DX = CURRENT DEST SEGMENT VALUE
 0056  3B F9	 	 	 	cmp	di,cx	 	; DI = NEXT DESTINATION @
 0058  75 03	 	 	 	jnz	rhboot03	; DON'T ADJUST FOR NOW
 005A  80 EC 10	 	 	 	sub	ah,16	 	; AX = PREVIOUS SEGMENT VALUE
 005D	 	 	 	rhboot03:
 005D  8E C0	 	 	 	mov	es,ax	 	; ES:DI = DESTINATION @
 005F  3B F1	 	 	 	cmp	si,cx	 	; SI ON A BOUNDARY ??
 0061  75 07	 	 	 	jnz	rhboot04	; SI NOT ON A BOUNDARY
 0063  8C D9	 	 	 	mov	cx,ds	 	; CX = SOURCE SEGMENT
 0065  80 ED 10	 	 	 	sub	ch,16	 	; ADJUST SOURCE SEGMENT
 0068  8E D9	 	 	 	mov	ds,cx	 	; DS:SI = SOURCE ADDRESS
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 CALCULATE THE MOVE SIZE	 	 	 	      *
 	 	 	 	;**********************************************************************
 006A	 	 	 	rhboot04:
 006A  8B CF	 	 	 	mov	cx,di	 	; CX = DEFAULT MOVE SIZE
 006C  3B CE	 	 	 	cmp	cx,si	 	; CHECK FOR SMALLER VALUE
 006E  72 02	 	 	 	jc	rhboot05	; DI IS SMALLER THAN SI
 0070  8B CE	 	 	 	mov	cx,si	 	; SI IS SMALLER THAN DI
 0072	 	 	 	rhboot05:
 0072  0B ED	 	 	 	or	bp,bp	 	; BP = OVERFLOW REGISTER
 0074  75 09	 	 	 	jnz	rhboot06	; BP HAS A VALUE IN IT
 0076  3B D9	 	 	 	cmp	bx,cx	 	; BX = REMAINING MOVE SIZE
 0078  77 05	 	 	 	ja	rhboot06	; MOVE COMPLETE IF SIZE EQUAL ZERO
 007A  8B CB	 	 	 	mov	cx,bx	 	; CX = NEW MOVE SIZE
 007C  E3 0A	 	 	 	jcxz	rhboot07	; NO MORE DATA TO MOVE
 007E  49	 	 	 	dec	cx	 	; CX = MOVE SIZE
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 NOW MOVE THE DATA	 	 	 	 	      *
 	 	 	 	;**********************************************************************
 007F	 	 	 	rhboot06:
 007F  41	 	 	 	inc	cx	 	; MOVE AT LEASE ONE BYTE
 0080  2B D9	 	 	 	sub	bx,cx	 	; BX = NEW MOVE SIZE
 0082  F3/ A4	 	 	 	rep	movsb	 	; MOVE BLOCK OF DISKETTE IMAGE
 0084  1B E9	 	 	 	sbb	bp,cx	 	; BP = OVERFLOW VALUE
 0086  EB C9	 	 	 	jmp	rhboot02	; LOOP AGAIN
 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	1-5
RHBOOT -- BOOTSTRAP LOAD PROGRAM


 	 	 	 	 	page
 	 	 	 	;**********************************************************************
 	 	 	 	;	 ADJUST MEMORY SIZE AND EXIT	 	 	 	      *
 	 	 	 	;**********************************************************************
 0088	 	 	 	rhboot07:
 0088  47	 	 	 	inc	di	 	; DX:DI = DISKETTE IMAGE @
 0089  8E D9	 	 	 	mov	ds,cx	 	; DS = SEGMENT 0000
 008B  BE 0120	 	 	 	mov	si,disk_addr	; ES:DI = DISKETTE IMAGE @
 008E  92	 	 	 	xchg	ax,dx	 	; AX = DISKETTE IMAGE SEGMENT
 008F  89 3C	 	 	 	mov	0[si],di	; DISKETTE IMAGE OFFSET
 0091  89 44 02	 	 	 	mov	2[si],ax	; DISKETTE IMAGE SEGMENT
 0094  BB 0010	 	 	 	mov	bx,16	 	; BX = MULTIPLIER
 0097  2B D2	 	 	 	sub	dx,dx	 	; PREPARE FOR MULTIPLY
 0099  F7 E3	 	 	 	mul	bx	 	; DX:AX = SEGMENT * 16
 009B  03 C7	 	 	 	add	ax,di	 	; ADD IN THE OFFSET
 009D  13 D1	 	 	 	adc	dx,cx	 	; DX:AX = SEGMENT * 16 + OFFSET
 009F  BB 0400	 	 	 	mov	bx,1024 	; BX = DIVISOR
 00A2  F7 F3	 	 	 	div	bx	 	; AX = # OF K BYTES OF MEMORY
 00A4  BE 0413	 	 	 	mov	si,DOS_MEM
 00A7  89 04	 	 	 	mov	0[si],ax	; UPDATE MEMORY SIZE
 00A9  BE 068C	 	 	 	mov	si,XFER_ADDR	; REBOOT FROM RAM DISKETTE IMAGE
 00AC  FF 2C	 	 	 	jmp	dword ptr 0[si]
 	 	 	 	;
 	 	 	 	;
 	 	 	 	;**********************************************************************
 	 	 	 	;	 DISKETTE IMAGE HEADER	 	 	 	 	      *
 	 	 	 	;**********************************************************************
 00AE  28 43 29 20 43 6F	 	db	'(C) Copyright IBM Corp., 1986',13,10
       70 79 72 69 67 68	
       74 20 49 42 4D 20	
       43 6F 72 70 2E 2C	
       20 31 39 38 36 0D	
       0A	 	 	
 00CD  54 68 69 73 20 70	 	db	'This program is the property of IBM.',13,10
       72 6F 67 72 61 6D	
       20 69 73 20 74 68	
       65 20 70 72 6F 70	
       65 72 74 79 20 6F	
       66 20 49 42 4D 2E	
       0D 0A	 	 	
 01FA	 	 	 	 	org	$+512-($-rhboot+HDR_SIZE)
 01FA	 	 	 	header	label	byte
 01FA  01	 	 	heads	 	db	1
 01FB  28	 	 	tracks	 	db	40
 01FC  08	 	 	sectors 	db	8
 01FD  0200	 	 	sec_size	dw	512
 01FF  00	 	 	status	 	db	0
 0200	 	 	 	rhboot	  endp
 0200	 	 	 	code	ends
 	 	 	 	 	end	start

 The IBM Personal Computer MACRO Assembler 10-15-86    	PAGE	Symbols-1
RHBOOT -- BOOTSTRAP LOAD PROGRAM


Segments and groups:

	 	N a m e	 	 	Size	align	combine	class

CODE . . . . . . . . . . . . . .	0200	PARA  	PUBLIC	

Symbols:            

	 	N a m e	 	 	Type	Value	Attr         

DISK_ADDR. . . . . . . . . . . .	Number	0120	
DOS_MEM. . . . . . . . . . . . .	Number	0413	
HDR_SIZE . . . . . . . . . . . .	Number	0006	
HEADER . . . . . . . . . . . . .	L BYTE 	01FA	CODE
HEADS. . . . . . . . . . . . . .	L BYTE 	01FA	CODE
MEM_SIZE . . . . . . . . . . . .	Number	0012	
RHBOOT . . . . . . . . . . . . .	F PROC	0000	CODE	Global	Length =0200
RHBOOT01 . . . . . . . . . . . .	L NEAR 	0043	CODE
RHBOOT02 . . . . . . . . . . . .	L NEAR 	0051	CODE
RHBOOT03 . . . . . . . . . . . .	L NEAR 	005D	CODE
RHBOOT04 . . . . . . . . . . . .	L NEAR 	006A	CODE
RHBOOT05 . . . . . . . . . . . .	L NEAR 	0072	CODE
RHBOOT06 . . . . . . . . . . . .	L NEAR 	007F	CODE
RHBOOT07 . . . . . . . . . . . .	L NEAR 	0088	CODE
SECTORS. . . . . . . . . . . . .	L BYTE 	01FC	CODE
SEC_SIZE . . . . . . . . . . . .	L WORD 	01FD	CODE
SETDS. . . . . . . . . . . . . .	L NEAR 	0003	CODE
START. . . . . . . . . . . . . .	L NEAR 	0000	CODE
STATUS . . . . . . . . . . . . .	L BYTE 	01FF	CODE
TRACKS . . . . . . . . . . . . .	L BYTE 	01FB	CODE
XFER_ADDR. . . . . . . . . . . .	Number	068C	

Warning Severe
Errors	Errors 
0	0
