📄 llhgc.asm
字号:
TITLE LLHGC - HGC screen mode support
;***
;LLHGC - HGC screen mode support
;
; Copyright <C> 1986, Microsoft Corporation
;
;Purpose:
; Support for Hercules Graphics Card (HGC) graphics
; screen mode (BIOS 8).
;
; This module sets hooks in the mode-independent
; modules to routines here for mode-dependent
; graphics support. See the mode-independent
; modules for more precise descriptions of the
; purposes and interfaces of these routines.
;
; The following table summarizes the information for
; the modes and configurations covered:
;
; C | A B
; O | B T I
; L | I T P T
; O A M | O R A C S
; S R D O | S I C G H / P
; C B A N | B O E A P P L
; R U C R P I | M U L X Y S R A I A
; E R O O T T | O T O R R I B G X N
; E S L W E O | D E R E E Z O E E E
; N T S S R R | E S S S S E X S L S
; -- - -- -- - -- | -- --- ---- --- --- --- ---- --- - -
; 3 x 80 25 H M | 8 2 N/A 720 348 32 9x14 2* 1 1
;
; * only 1 page allowed if color card installed
;
; Discussion of HGC memory interleave line archtecture:
; HGC video memory is organized into four interleaved banks of 8K
; each.
;
; Scan Offset
; Line from B800
; ---- ---------
; 0 0
; 1 8K
; 2 16K
; 3 24K
; 4 90
; 5 8K+90
; 6 16K+90
; 7 24K+90
; . .
; . .
; . .
;
; To move from scan line to scan line add to current address
; ------- -------------- ------------ ----------------------
; UP MOD 0 MOD 3 24K-90
; UP MOD 1 MOD 0 -8K
; UP MOD 2 MOD 1 -8K
; UP MOD 3 MOD 2 -8K
; DOWN MOD 0 MOD 1 8K
; DOWN MOD 1 MOD 2 8K
; DOWN MOD 2 MOD 3 8K
; DOWN MOD 3 MOD 0 -24K+90
;
;******************************************************************************
INCLUDE switch.inc ;feature switches
INCLUDE rmacros.inc
USESEG _DATA
USESEG _BSS
USESEG GR_TEXT
USESEG CN_TEXT
USESEG XIB
USESEG XI
USESEG XIE
INCLUDE seg.inc
INCLUDE ibmunv.inc
INCLUDE llgrp.inc ;Constant definitions
INCLUDE idmac.inc
INCLUDE grmac.inc ;ModeData macros
INITIALIZER B$xINITHERC ;Put B$xINITHERC in initializer list
sBegin _BSS
;
; ***************************************************************************
; External variables
; ***************************************************************************
;
externB b$BiosMode
externB b$Adapter
externW b$VideoBase
externB b$MaskC
externW b$OffC
externW b$SegC
externW b$CurrPSize
externW b$CurPages
externW b$UpSub
externW b$DnSub
externW b$UpDnAdd
externB b$MaxPage ; maximum number of pages allowed - 1
externW b$VideoMem ; used to calculate b$MaxPage
externW b$ScreenTab
sEnd _BSS
assumes CS,GR_TEXT
sBegin GR_TEXT
externNP B$SCNIO ;used in SCNIO macro
externNP B$InitModeData
externNP B$ErrorReturn
externNP B$CgaSetAttr
externNP B$CgaLeftC1
externNP B$CgaChkUpC
externNP B$CgaUpC
externNP B$CgaChkDownC
externNP B$CgaDownC
externNP B$CgaReadC
externNP B$CgaSetC
externNP B$CgaSetPixC
externNP B$CgaSetPixFirstC
externNP B$CgaSetPixLastC
externNP B$CgaPutAction
externNP B$CgaNReadL
externNP B$CgaNWriteL
externNP B$CgaNSetC
externNP B$CgaSetTile
externNP B$CgaPaintBound
externNP B$CgaScanL
externNP B$CgaScanR
externNP B$CgaLineX
externNP B$CgaLineY
externNP B$CgaLineV
;===========================================================================
mModeData Mode3Data
;
; SCREEN 3, BIOS mode 8
;
; Mode-dependent data follows to initialize the the "b$ModeData" table
; in LLCGRP.
;
;===========================================================================
mScreenMode 3
mBiosMode 8
mBurst 0
mScrWidth 80
mScrHeight 25
mHorzRes 720
mVertRes 348
mVideoBase 0B000H
mMaxAttr 1
mMaxColor -1 ;no palette
mPageSize 32 ;page size in K
mCurrPSize <(32*1024) shr 4> ;page size in paragraphs (1 plane)
mMaxPage 1
mNullColor 0
mForeColor 1
mBackColor 0
mEgaWrMd 0
mInitPalette 0
mInitVgaPal 0
mAlphaDim AlphaDim3
mSetMode SetMode3
mSetPages SetPages
mPalReset B$ErrorReturn
mPalPut B$ErrorReturn
mPalTrans B$ErrorReturn
mPalSet B$ErrorReturn
mSetColor B$ErrorReturn
mForeMapped 1
mBitsPerPixel 1
mPlanes 1
mMapXYC MapXYC3
mLeftC B$CgaLeftC1
mChkUpC B$CgaChkUpC
mUpC B$CgaUpC
mChkDownC B$CgaChkDownC
mDownC B$CgaDownC
mSetAttr B$CgaSetAttr
mReadC B$CgaReadC
mSetC B$CgaSetC
mSetPixC B$CgaSetPixC
mSetPixFirstC B$CgaSetPixFirstC
mSetPixLastC B$CgaSetPixLastC
mLineX B$CgaLineX
mLineY B$CgaLineY
mLineV B$CgaLineV
mPutAction B$CgaPutAction
mNReadL B$CgaNReadL
mNWriteL B$CgaNWriteL
mNSetC B$CgaNSetC
mPaintBound B$CgaPaintBound
mSetTile B$CgaSetTile
mScanL B$CgaScanL
mScanR B$CgaScanR
mEnd GraphDataLen
;===========================================================================
labelNP <PUBLIC, B$HRCUSED>
;***
; B$Screen3
;
;Purpose:
; Establish all relevent mode dependent data values and function
; vectors for BASIC screen mode 3.
;Entry:
; AL = screen mode (3)
; AH = burst (N/A)
; CL = alpha columns
;Exit:
; PSW.C = set indicates error
;Uses:
; per conv.
;Exceptions:
;******************************************************************************
cProc B$Screen3,<PUBLIC,NEAR>
cBegin
test b$Adapter,HGC ;check for adapter support
stc
jz ScrExit ;exit w/error if not supported
mov bx,GR_TEXTOFFSET Mode3Data ;mode-specific data
mov cx,GraphDataLen
call B$InitModeData ;initialize table data
mov b$UpSub,8192
mov b$DnSub,24576-90
mov b$UpDnAdd,8192+24576-90
mov ax,[b$VideoMem]
rol al,1 ; divide by 32K
rol al,1
and [b$MaxPage],al ; Max pages = b$Videomem / 32K
; NOTE: Clear carry here -- currently done by the AND instruction
; clc ;indicate no error
ScrExit:
cEnd
;***
; AlphaDim3
;
;Purpose:
; Validate the proposed text dimensions for Screen 3.
; If 80x25 is requested, this mode satisfies the request
; else suggest screen mode 0.
;Entry:
; BH = number of lines
; BL = number of columns
;Exit:
; AL = -1 if this mode satisfies the request, otherwise
; AL is suggested screen mode to invoke for desired dimensions
;Uses:
; per conv.
;Exceptions:
;******************************************************************************
DbPub AlphaDim3
cProc AlphaDim3,<NEAR>
cBegin
mov al,-1 ;flag request satisfied (maybe)
cmp bx,80+25*256 ;80x25?
je ADim3Exit ;exit if so, standard stuff
xor al,al ;flag request for screen 0, let text mode try
ADim3Exit:
clc ;no error
cEnd
;***
; SetMode3
;
;Purpose:
; Set the screen mode according to the characteristics established
; by previous call to B$Screenx and b$AlphaDim.
;Entry:
;
;Exit:
;
;Uses:
; per conv.
;Exceptions:
;******************************************************************************
DbPub SetMode3
cProc SetMode3,<NEAR>
cBegin
mov al,b$BiosMode ;set BIOS mode 8
SCNIOS vSetMode
cEnd
;***
; SetPages
;
;Purpose:
; Set the current active and visual pages and calculate page size
; and video segment offset for EGA modes.
;Entry:
; AL = active page
; AH = visual page
;Exit:
; b$CurPages set to new active and visual pages.
; b$SegC set to start of new active page.
;Uses:
; per conv.
;Exceptions:
;******************************************************************************
cProc SetPages,<NEAR>
cBegin
mov b$CurPages,ax ;save page numbers
push ax
mov al,ah
SCNIO vSelActivePage ;set visual page
pop ax
cbw ;extend active page to word
mul b$CurrPSize ;times page size in paras
add ax,b$VideoBase ;set video segment
mov b$SegC,ax
cEnd
;***
; MapXYC3
;
;Purpose:
; May given X and Y coordinates to the graphics cursor for Screen 3.
;Entry:
; CX = X coordinate
; DX = Y coordinate
;Exit:
; b$OffC, b$MaskC updated
;Uses:
; per conv.
;Exceptions:
;******************************************************************************
DbPub MapXYC3
cProc MapXYC3,<NEAR>
cBegin
xor ax,ax
shr dx,1 ;dx=row within quadrant
rcr ax,1 ;ax=8K multiple for quadrant displacement
shr dx,1
rcr ax,1
shr ax,1
mov bx,dx ;multiply y by 90 to compute row displacement
shl dx,1 ;dx=2*Y
shl dx,1 ;dx=4*Y
add dx,bx ;dx=5*Y
shl dx,1 ;dx=10*Y
mov bx,dx
shl dx,1 ;dx=20*Y
shl dx,1 ;dx=40*Y
shl dx,1 ;dx=80*Y
add dx,bx ;dx=90*Y
add dx,ax ;add in quadrant displacement
mov ax,cx ;save x
shr ax,1 ;div by PixelsPerByte (8)
shr ax,1 ; to get byte index
shr ax,1
add dx,ax ;add x byte offset to y row address
mov b$OffC,dx ;save byte offset
and cl,7 ;mask in x bit addr
mov ch,10000000B ;leftmost pixel on in shift mask
shr ch,cl ;move over to get mask
mov b$MaskC,ch ;store cursor mask
cEnd
;***
; B$xINITHERC - initialize HERC modes
;
;Purpose:
; Added with revision [2].
; Put the address of Hercules screen mode support routine into the
; dispatch table used by the screen statement.
;
;Entry:
; None
;Exit:
; ScreenTab updated
;Uses:
; None
;Exceptions:
;******************************************************************************
cProc B$xINITHERC,<FAR,PUBLIC>
cBegin
MOV WORD PTR [b$ScreenTab + (3*2) + 1],OFFSET B$Screen3
cEnd
sEnd GR_TEXT
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -