|
|
1.1 root 1: page ,132
2: ;***************************************************************************
3: ; *
1.1.1.2 ! root 4: ; Created by Microsoft Corp. 1987 *
1.1 root 5: ; *
6: ;***************************************************************************
7: title SetScan - Set An EGA Scan to the Given Colors
8:
9:
10:
11:
12: .286c ;Allow iAPX80286 instructions
13:
14: memM equ 1 ;define middle model program
15: ?PLM=1
16: ?WIN=0
17:
18:
19:
20: .xlist
21: include cmacros.inc
22: include ega.inc
23: .list
24:
25:
26: ScreenWidthB equ 80 ;Width of screen in bytes
27: ScreenSize equ 14000 ;Size of screen plane in words
28:
29: ;** define segment for ring 2 IOPL code
30:
31: createSeg _SCRIO, SCRIO, byte, public, CODE
32: scrioOFFSET equ OFFSET _SCRIO:
33:
34: sBegin data
35:
36: ;** These routines assume that the following two external values are
37: ; initialized before any routine is called.
38:
39:
40: extrn _dpoffset:word ;EGA display page offset
41: extrn _psel:word ;selector array for EGA memory
42:
43: sEnd data
44:
45: sBegin scrio
46: assumes cs,_scrio
47: assumes ds,data
48:
49:
50:
51:
52: ;** SetDVideo - disable video
53: ;
54: ; SetDVideo disable video to prevent snow and flicker during state
55: ; changes of the EGA. A call to SetEVideo must be made to reenable
56: ; the video.
57: ;
58: ; SetDVideo ();
59: ;
60: ; Entry none
61: ; Exit EGA video blanked
62: ; Returns none
63: ; Calls dvideo
64:
65:
66: cProc SetDvideo,<FAR,PUBLIC>,<>
67:
68: cBegin
69: call bvd ;blank video display
70: cEnd
71:
72:
73:
74:
75: ;** SetEVideo - enable video
76: ;
77: ; SetEVideo renables video
78: ;
79: ; SetEVideo ();
80: ;
81: ; Entry none
82: ; Exit EGA video restored
83: ; Returns none
84: ; Calls evideo
85:
86:
87: cProc SetEvideo,<FAR,PUBLIC>,<>
88:
89: cBegin
90: call evd ;enable video display
91: cEnd
92:
93:
94:
95:
96: ;** SetScan - Set One Scan to Given Colors
97: ;
98: ; The given scan line is set to the colors passed in.
99: ;
100: ; SetScan (row, count, values);
101: ;
102: ; Entry row = row to write
103: ; count = number of bytes of display data
104: ; values = pointer to character array of bit values
105: ; Exit display page forced to 0
106: ; display row updated
107: ; Returns none
108: ; The display adapter must be initialized before invoking this
109: ; routine.
110:
111:
112:
113: cProc SetScan,<FAR,PUBLIC>,<si,di,es>
114: parmW Y
115: parmW count
116: parmW pMapped
117:
118: cBegin
119: cld
120: xor bx,bx ;force display to page 0
121: call sdp ;set display page
122: mov ax,Y ;Compute start of scan that will
123: mov di,ScreenWidthB ; be set to the passed colors
124: mul di
125: mov di,ax
126: mov si,_psel ;es:di --> scan on the EGA
127: mov es,word ptr [si]
128: mov dx,rGraphics ;Set the Graphics Controller's
129: mov al,rBitmask ; address register to point to
130: out dx,al ; the bitmask register
131: inc dx ;--> Graphics Controller's data register
132: mov ah,10000000b ;Set mask for initial pixel
133: mov cx,count ;Set count of pixels
134: jcxz ssr2 ;None, exit now
135: mov si,offset pMapped ;ds:si --> pixel colors
136: xor bx,bx ;Zero is always handy!
137:
138: ssr1: mov al,ah ;Set BitMask register to only alter
139: out dx,al ; pixel of interest
140: ror ah,1 ;Set up for next pixel
141: lodsb ;Get color for this pixel
142:
143:
144: ; The BitMask register allows bits to be protected from changes.
145: ; It works in conjunction with some internal EGA latches. Every
146: ; time a read operation from EGA memory is performed, the latches
147: ; are loaded with the data read from each plane (one 8-bit latch
148: ; per plane). Wherever the BitMask register is a "0", the EGA
149: ; writes data from the latches. Wherever the BitMask register is
150: ; a "1", the data from the host is written. This is not implemented
151: ; in the hardware as a read/modify/write operation, so the user
152: ; must load the latches explicitly.
153:
154:
155: xchg es:[di],al ;Load latches, write color to the pixel
156: adc di,bx ;Possibly --> next destination byte
157: loop ssr1 ;Until all pixels drawn.
158:
159: ssr2: mov al,0ffh ;Set mask for all pixel
160: out dx,al
161: cEnd
162:
163:
164:
165:
166: ;** SetScanClear - clear video display memory
167: ;
168: ; SetScanClear clears the 28000 bytes of video memory starting at
169: ; the page offset specified in _dpoffset.
170: ;
171: ; SetScanClear ();
172: ;
173: ; Entry none
174: ; Exit EGA video memory cleared
175: ; Returns none
176: ; Calls cdm
177:
178:
179: cProc SetScanClear,<FAR,PUBLIC>,<>
180:
181: cBegin
182: call bvd ;blank video display
183: mov cx,_dpoffset
184: call cdm ;clear display memory
185: call evd ;enable video display
186: cEnd
187:
188:
189:
190:
191: ;** SetScanRestore - restore graphics display
192: ;
193: ; Restore active EGA display page from saved image
194: ; SetScanRestore (ressel);
195: ;
196: ; Entry ressel = far pointer to array of selectors to segments
197: ; containing graphics image to be restored
198: ; _dpoffset = offset of active display page
199: ; Exit graphics image restored
200: ; Returns none
201:
202:
203: cProc SetScanRestore,<FAR,PUBLIC>,<si,di,es,ds>
204: parmD ressel
205:
206: cBegin
207: mov cx,_dpoffset ;(cx) = display page to clear
208: call cdm ;clear display memory
209: mov bx,_psel ;(es) = display selector
210: mov es,word ptr [bx]
211:
212: ; Restore graphics memory.
213: ; This is done by enabling each 32k bank of graphics memory
214: ; and copying memory from the restore segments.
215:
216: mov dx,rGraphics ;Set the Graphics Controller's
217: mov ax,0*256+rMode
218: out dx,ax
219: mov al,rBitmask ; address register to point to
220: mov ah,0ffh ;Set mask for initial pixel
221: out dx,ax ; the bitmask register
222: mov dx,rSequencer ;(dx) = sequencer register address
223: mov al,rMapMask ;write to sequencer map mask register
224: mov ah,C0 ;select plane C0
225: out dx,ax
226: push ds ;save (ds) for later
227: mov bx,_dpoffset ;move display offset to stack
228: push bx
229: lds bx,ressel ;(ds:bx) = address of restore selector
230: mov ds,[bx] ;(ds) = first selector
231: xor si,si ;(si) = offset into restore segment
232: pop di ;(di) = offset into display memory
233: push di
234: mov cx,ScreenSize ;copy image to plane C0
235: rep movsw
236: mov ah,C1 ;select plane C1
237: out dx,ax
238: pop di ;(di) = offset into display memory
239: push di
240: mov cx,ScreenSize ;copy image to plane C1
241: rep movsw
242: lds bx,ressel ;(ds:bx) = address of restore selector
243: mov ds,[bx+2] ;(ds) = second selector
244: xor si,si ;(si) = offset into restore segment
245: mov ah,C2 ;select plane C2
246: out dx,ax
247: pop di ;(di) = offset into display memory
248: push di
249: mov cx,ScreenSize ;copy image to plane C2
250: rep movsw
251: mov ah,C3 ;select plane C3
252: out dx,ax
253: pop di ;(di) = offset into display memory
254: mov cx,ScreenSize ;copy image to C3
255: rep movsw
256: pop ds
257:
258: ; set start address register
259:
260: mov bx,_dpoffset
261: call sdp ;set display page
262: cEnd
263:
264:
265:
266:
267: ;** SetScanRFont - restore EGA font table
268: ;
269: ; SetScanRFont restores the EGA font tables saved by SetScanSFont.
270: ;
271: ; SetScanRFont (fontsel);
272: ;
273: ; Entry fontsel = selector for font save memory
274: ; Exit EGA font table restored from font save segment
275: ; Returns none
276: ; Calls ifa, tfa
277:
278:
279: cProc SetScanRFont,<FAR,PUBLIC>,<si,di,es>
280: parmW frsel
281:
282: cBegin
283: mov si,_psel ;(es) = display selector
284: mov es,word ptr [si]
285: push ds
286: call ifa ;initialize font addressing
287: mov bx,frsel ;(bx) = font restore selector
288: mov ds,bx ;(ds) = font selector
289: xor si,si ;(si) = offset into restore segment
290: xor di,di ;(di) = offset into display
291: mov cx,08000h ;copy 32k words to plane C2
292: rep movsw ;copy memory
293: pop ds
294: call tfa ;terminate font table addressing
295: cEnd
296:
297:
298:
299: ;** SetScanSave - Save graphics display
300: ;
301: ; Copy active page of display memory to RAM save buffer.
302: ;
303: ; SetScanSave (savesel);
304: ;
305: ; Entry savsel = far pointer to array of selectors for segments
306: ; used to save graphics image
307: ; _dpoffset = offset of active EGA display page
308: ; Exit graphics image saved
309: ; Returns none
310:
311:
312: cProc SetScanSave,<FAR,PUBLIC>,<si,di,ds,es>
313: parmD savesel ;far pointer to array of save selectors
314:
315: cBegin
316: les bx,savesel ;(es:bx) = address of save selector
317: mov es,es:[bx] ;(es) = first selector
318: mov bx,_dpoffset ;(bx) = offset into display memory
319: push bx
320: mov dx,rGraphics ;(dx) = address of graphics controller
321: mov al,rReadMap
322: mov ah,rmC0 ;set read map select to plane 0
323: out dx,ax ;
324: mov si,_psel ;(ds) = display selector
325: mov ds,word ptr [si]
326: mov si,bx ;(si) = offset into display
327: xor di,di ;offset into save memory
328: mov cx,ScreenSize ;copy image from plane C0
329: rep movsw ;copy memory
330: mov ah,rmC1 ;select plane 1
331: out dx,ax
332: mov si,bx ;(si) = offset into display
333: mov cx,ScreenSize ;copy image from plane C1
334: rep movsw
335: les bx,savesel ;(es:bx) = address of save selector
336: mov es,es:[bx+2] ;(es) = second selector
337: pop bx ;(bx) = offset into display memory
338: mov ah,rmC2 ;select plane 2
339: out dx,ax
340: mov si,bx ;(si) = offset into display
341: xor di,di ;offset into save memory
342: mov cx,ScreenSize ;copy image from plane C2
343: rep movsw ;copy memory
344: mov ah,rmC3 ;select plane 3
345: out dx,ax
346: mov si,bx ;(si) = offset into display
347: mov cx,ScreenSize ;copy image from C3
348: rep movsw
349: mov ah,rmC0 ;set read map select to plane 0
350: out dx,ax ;
351: cEnd
352:
353:
354:
355:
356: ;** SetScanSFont - save font tables
357: ;
358: ; SetScanSFont (fontsel);
359: ;
360: ; Entry fontsel = selector for font save memory
361: ; Exit EGA font table saved in font save segment
362: ; Returns none
363: ; Calls ifa, tfa
364:
365:
366: cProc SetScanSFont,<FAR,PUBLIC>,<si,di,es>
367: parmW fssel
368:
369: cBegin
370: call ifa ;initialize font addressing
371: push ds
372: mov bx,fssel ;(bx) = font save selector
373: mov es,bx ;(es) = font save selector
374: mov si,_psel ;(ds) = display selector
375: mov ds,word ptr [si]
376: xor si,si ;(si) = offset into display
377: xor di,di ;offset into save memory
378: mov cx,8000h ;copy 32k words from plane C0
379: rep movsw ;copy memory
380: pop ds ;(ds) = data segment selector
381: cEnd
382:
383:
384:
385:
386: ;* bvd - blank video display
387: ;
388: ; bvd blanks the video display by preventing access to the
389: ; palette registers.
390: ;
391: ; Entry none
392: ; Exit display blanked
393: ; Returns none
394: ; Calls wvs
395: ; Uses al, dx
396:
397: cProc bvd,<NEAR>,<>
398:
399: cBegin
400: call wvs ;wait for vertical resynch
401: mov dx,rAttread ;read feature control to reset
402: in al,dx ;internal flipflop to force address
403: mov dx,rAttwrite
404: mov al,000H ;disable access to palette
405: out dx,al
406: cEnd
407:
408:
409:
410:
411: ;* cdm - clear display memory
412: ;
413: ; cdm clears the 28000 bytes of memory starting at the address
414: ; pointed to by (cx)
415: ;
416: ; Entry cx = offset of page to clear
417: ; Exit display memory cleared
418: ; Returns none
419: ; Calls sdm
420: ; Uses ax, bx, cx, dx
421:
422:
423: cProc cdm,<NEAR,PUBLIC>,<di, es>
424:
425: cBegin
426: mov bx,_psel ;(es) = display selector
427: mov es,word ptr [bx]
428: mov bx,cx ;(bx) = display offset
429:
430:
431: ; Clear graphics memory.
432: ; This is done by enabling each 32k bank of graphics memory
433: ; and storing zeroes.
434:
435: mov dx,rGraphics ;Set the Graphics Controller's
436: mov al,rBitmask ; address register to point to
437: mov ah,0ffh ;Set mask for initial pixel
438: out dx,ax ; the bitmask register
439: mov dx,rSequencer ;(dx) = sequencer register address
440: mov al,rMapMask ;write to sequencer map mask register
441: mov ah,C0 ;select plane C0
442: out dx,ax
443: mov di,bx ;(di) = offset into display memory
444: mov cx,ScreenSize ;copy image to plane C0
445: xor ax,ax
446: rep stosw
447: mov al,rMapMask ;write to sequencer map mask register
448: mov ah,C1 ;select plane C1
449: out dx,ax
450: mov di,bx ;(di) = offset into display memory
451: mov cx,ScreenSize ;copy image to plane C1
452: xor ax,ax
453: rep stosw
454: mov al,rMapMask ;write to sequencer map mask register
455: mov ah,C2 ;select plane C2
456: out dx,ax
457: mov di,bx ;(di) = offset into display memory
458: mov cx,ScreenSize ;copy image to plane C2
459: xor ax,ax
460: rep stosw
461: mov al,rMapMask ;write to sequencer map mask register
462: mov ah,C3 ;select plane C3
463: out dx,ax
464: mov di,bx ;(di) = offset into display memory
465: mov cx,ScreenSize ;copy image to C3
466: xor ax,ax
467: rep stosw
468: call sdm ;set display mode
469: cEnd
470:
471:
472:
473:
474: ;* evd - enable video display
475: ;
476: ; evd enables the video display by reenabling access to the
477: ; palette registers
478: ;
479: ; Entry none
480: ; Exit video display restored
481: ; Returns none
482: ; Calls none
483: ; Uses al, dx
484:
485:
486: cProc evd,<NEAR>,<>
487:
488: cBegin
489: mov dx,rAttread ;read feature control to reset
490: in al,dx ;internal flipflop to force address
491: mov dx,rAttwrite
492: mov al,020H ;allow access to palette
493: out dx,al
494: cEnd
495:
496:
497:
498:
499: ;** ifa - initialize font addressing
500: ;
501: ; initialize EGA to allow read of font tables
502: ;
503: ; Entry none
504: ; Exit EGA addressing set up
505: ; Returns none
506:
507:
508: cProc ifa,<NEAR>,<>
509:
510: cBegin
511: mov dx,rGraphics
512: mov ax,0204h
513: cli
514: out dx,ax ;Read Map Select register
515: mov ax,0005h
516: out dx,ax ;Graphics Mode register
517: mov ax,0406h
518: out dx,ax ;Graphics Misc register
519: mov dx,rSequencer
520: mov ax,0C02h
521: out dx,ax ;Write Map Select
522: mov ax,0404h
523: out dx,ax ;Turn on odd/even
524: sti
525: cEnd
526:
527:
528:
529:
530: ;* sdm - set display mode
531: ;
532: ; sdm restores the EGA to the default graphics mode
533: ;
534: ; Entry none
535: ; Exit default graphics display mode reestablished
536: ; Returns none
537: ; Calls none
538: ; Uses ax, dx
539:
540:
541: cProc sdm,<NEAR>,<si,di,es>
542:
543: cBegin
544: mov dx,rSequencer ;Enable all planes for writing
545: mov ah,C0+C1+C2+C3
546: mov al,rMapMask
547: out dx,ax
548: mov dx,rGraphics ;-->Graphics Controller
549: mov ax,0*256+rEnableSR ;Clear any set/reset enable
550: out dx,ax
551:
552:
553: ; Color Write Mode takes data from the host as a color. D0 of
554: ; the host data is taken as the color for plane C0, D1 for plane
555: ; C1, etc. The color for each plane is written to all bits of
556: ; the destination byte which are enabled in the BitMask Register.
557:
558:
559: mov ax,(mColorWrite+mDataRead)*256+rMode
560: out dx,ax
561:
562:
563: ; The Data Rotate register allows a boolean function between
564: ; the data from the host and the data in the EGA's latches
565: ; to occur. It also allows the data from the host to be
566: ; rotated by some count before the operation occurs.
567:
568:
569: mov ax,(drSet*256)+rDataRotate
570: out dx,ax
571: cEnd
572:
573:
574:
575:
576: ;* sdp - set display page
577: ;
578: ; sdp sets the current display page by setting the display offset
579: ; to the value in bx
580: ;
581: ; Entry bx = page offset
582: ; Exit disply page address set
583: ; Returns none
584: ; Calls wvs
585: ; Uses ax,dx
586:
587:
588: cProc sdp,<NEAR>,<>
589:
590: cBegin
591: call wvs ;wait for vertical synch
592: mov dx,rCRTC ;(dx) = CRT controller
593: mov al,rSahr ;(al) = high address register
594: mov ah,bh ;(ah) = upper byte of address
595: out dx,ax
596: mov al,rSalr
597: mov ah,bl ;(ah) = low byte of address
598: out dx,ax
599: cEnd
600:
601:
602:
603:
604: ;** tfa - terminate font addressing
605: ;
606: ; terminate font table addressing mode
607: ;
608: ; Entry none
609: ; Exit EGA returned to normal addressing mode
610: ; Returns none
611:
612:
613: cProc tfa,<NEAR>,<>
614:
615: cBegin
616: mov cx,0e06h ;Setup color buffer with chaining
617: mov dx,rGraphics
618: mov ax,0004h
619: cli
620: out dx,ax ;Read Map Select register
621: mov ax,1005h
622: out dx,ax ;Graphics Mode register
623: mov ax,0e06h ;Setup color buffer with chaining
624: out dx,ax ;Graphics Misc register
625: mov dx,rSequencer
626: mov ax,0302h
627: out dx,ax ;Write Map Select
628: mov ax,0004h
629: out dx,ax ;Turn off odd/even
630: sti
631: cEnd
632:
633:
634:
635:
636: ;* wvs - wait for vertical synch
637: ;
638: ; wvs waits for the leading edge of the vertical synch pulse
639: ;
640: ; Entry none
641: ; Exit leading edge of vertical synch encountered
642: ; Returns none
643: ; Calls none
644: ; Uses al, dx
645:
646:
647: cProc wvs,<NEAR>,<>
648:
649: cBegin
650: mov dx,rAttread ;read feature control to reset
651:
652: ; wait until not in vertical retrace
653:
654: wvs1: in al,dx ;internal flipflop to force address
655: test al,mVRetrace ;check for vertical retrace
656: jnz wvs1 ;if vertical retrace set
657:
658: ; wait for start of vertical retrace
659:
660: wvs2: in al,dx ;internal flipflop to force address
661: test al,mVRetrace ;check for vertical retrace
662: jz wvs2 ;if vertical retrace not set
663: cEnd
664:
665:
666: sEnd scrio
667: end
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.