]> 4ch.mooo.com Git - 16.git/blob - 16/PCGPE10/MODEX.TXT
new file: 16/SCRC/FUNPTR.EXE
[16.git] / 16 / PCGPE10 / MODEX.TXT
1 \r
2                       ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿\r
3                       ³ INTRODUCTION TO MODE X ³\r
4                       ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ\r
5 \r
6                  By Robert Schmidt <robert@stud.unit.no>\r
7 \r
8 \r
9 \r
10 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ\r
11 ³ XINTRO18.TXT ³\r
12 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ\r
13 \r
14 Title:          INTRODUCTION TO MODE X\r
15 \r
16 Version:        1.8\r
17 \r
18 Author:         Robert Schmidt <robert@stud.unit.no>\r
19 \r
20 Copyright:      (C) 1993 of Ztiff Zox Softwear - refer to Status below.\r
21 \r
22 Last revision:  25-Nov-93 (Modified for the PCGPE 17-Apr-94)\r
23 \r
24 Figures:        1. M13ORG - memory organization in mode 13h\r
25                 2. MXORG - memory organization in unchained modes\r
26                 (Both files are appended to the end of this document)\r
27 \r
28                 The figures are available as 7-bit ASCII text (ASC) files.\r
29 \r
30 Status:         This article, its associated figures and source listings\r
31                 named above, are all donated to the public domain.\r
32                 Do with it whatever you like, but give credit where\r
33                 credit is due.\r
34 \r
35                 The standard disclaimer applies.\r
36 \r
37 Index:          0. ABSTRACT\r
38                 1. INTRODUCTION TO THE VGA AND ITS 256-COLOR MODE\r
39                 2. GETTING MORE PAGES AND PUTTING YOUR FIRST PIXEL\r
40                 3. THE ROAD FROM HERE\r
41                 4. BOOKS ON THE SUBJECT\r
42                 5. BYE - FOR NOW\r
43 \r
44 \r
45 0. ABSTRACT\r
46 \r
47 This text gives a fairly basic, yet technical, explanation to what, why\r
48 and how Mode X is.  It first tries to explain the layout of the VGA\r
49 memory and the shortcomings of the standard 320x200 256-color mode,\r
50 then gives instructions on how one can progress from mode 13h to a\r
51 multipage, planar 320x200 256-color mode, and from there to the\r
52 quasi-standard 320x240 mode, known as Mode X.\r
53 \r
54 A little experience in programming the standard VGA mode 13h\r
55 (320x200 in 256 colors) is assumed.  Likewise a good understanding of\r
56 hexadecimal notation and the concepts of segments and I/O ports is\r
57 assumed.  Keep a VGA reference handy, which at least should have\r
58 definitions of the VGA registers at bit level.\r
59 \r
60 Throughout the article, a simple graphics library for unchained (planar)\r
61 256-color modes is developed.  The library supports the 320x200 and\r
62 320x240 modes, active and visible pages, and writing and reading\r
63 individual pixels.\r
64 \r
65 \r
66 1. INTRODUCTION TO THE VGA AND ITS 256-COLOR MODE\r
67 \r
68 Since its first appearance on the motherboards of the IBM PS/2 50, 60\r
69 and 80 models in 1987, the Video Graphics Array has been the de facto\r
70 standard piece of graphics hardware for IBM and compatible personal\r
71 computers.  The abbreviation, VGA, was to most people synonymous with\r
72 acceptable resolution (640x480 pixels), and a stunning rainbow of colors\r
73 (256 from a palette of 262,144), at least compared to the rather gory\r
74 CGA and EGA cards.\r
75 \r
76 Sadly, to use 256 colors, the VGA BIOS limited the users to 320x200\r
77 pixels, i.e. the well-known mode 13h.  This mode has one good and one\r
78 bad asset.  The good one is that each one of the 64,000 pixels is easily\r
79 addressable in the 64 Kb video memory segment at 0A000h.  Simply calculate\r
80 the offset using this formula:\r
81 \r
82 offset = (y * 320) + x;\r
83 \r
84 Set the byte at this address (0A000h:offset) to the color you want, and\r
85 the pixel is there.  Reading a pixel is just as simple: just read the\r
86 corresponding byte.  This was heaven, compared to the havoc of planes and\r
87 masking registers needed in 16-color modes.  Suddenly, the distance from a\r
88 graphics algorithm on paper to an implemented graphics routine in assembly\r
89 was cut down to a fraction.  The results were impressively fast, too!\r
90 \r
91 The bad asset is that mode 13h is also limited to only one page, i.e.\r
92 the VGA can hold only one screenful at any one time (plus 1536 pixels, or\r
93 about four lines).  Most 16-color modes let the VGA hold more than one page,\r
94 and this enables you to show one of the pages to the user, while drawing on\r
95 another page in the meantime.  Page flipping is an important concept in making\r
96 flicker free animations.  Nice looking and smooth scrolling is also almost\r
97 impossible in mode 13h using plain VGA hardware.\r
98 \r
99 Now, the alert reader might say: "Hold on a minute!  If mode 13h enables\r
100 only one page, this means that there is memory for only one page.  But I\r
101 know for a fact that all VGAs have at least 256 Kb RAM, and one 320x200\r
102 256-color page should consume only 320*200=64000 bytes, which is less\r
103 than 64 Kb.  A standard VGA should room a little more than four 320x200\r
104 pages!"  Quite correct, and to see how the BIOS puts this limitation on\r
105 mode 13h, I'll elaborate a little on the memory organization of the VGA.\r
106 \r
107 The memory is separated into four bit planes.  The reason for this stems\r
108 from the EGA, where graphics modes were 16-color.  Using bit planes, the\r
109 designers chose to let each pixel on screen be addressable by a single\r
110 bit in a single byte in the video segment.  Assuming the palette has\r
111 not been modified from the default, each plane represent one of the EGA\r
112 primary colors: red, green, blue and intensity.  When modifying the bit\r
113 representing a pixel, the Write Plane Enable register is set to the\r
114 wanted color.  Reading is more complex and slower, since you can\r
115 only read from a single plane at a time, by setting the Read Plane\r
116 Select register.  Now, since each address in the video segment can\r
117 access 8 pixels, and there are 64 Kb addresses, 8 * 65,536 = 524,288\r
118 16-color pixels can be accessed.  In a 320x200 16-color mode, this makes\r
119 for about 8 (524,288/(320*200)) pages, in 640x480 you get nearly 2\r
120 (524,288/(640*480)) pages.\r
121 \r
122 In a 256-color mode, the picture changes subtly.  The designers decided\r
123 to fix the number of bit planes to 4, so extending the logic above to 8\r
124 planes and 256 colors does not work.  Instead, one of their goals was to\r
125 make the 256-color mode as easily accessible as possible.  Comparing the\r
126 8 pixels/address in 16-color modes to the 1-to-1 correspondence of\r
127 pixels and addresses of mode 13h, one can say that they have\r
128 succeeded, but at a certain cost.  For reasons I am not aware of, the\r
129 designers came up with the following effective, but memory-wasting\r
130 scheme:\r
131 \r
132 The address space of mode 13h is divided evenly across the four bit\r
133 planes.  When an 8-bit color value is written to a 16-bit address in the\r
134 VGA segment, a bit plane is automatically selected by the 2 least\r
135 significant bits of the address.  Then all 8 bits of the data is written\r
136 to the byte at the 16-bit address in the selected bitplane (have a look at\r
137 figure 1).  Reading works exactly the same way.  Since the bit planes are so\r
138 closely tied to the address, only every fourth byte in the video memory is\r
139 accessible, and 192 Kb of a 256 Kb VGA go to waste.  Eliminating the\r
140 need to bother about planes sure is convenient and beneficial, but to\r
141 most people the loss of 3/4 of the total VGA memory sounds just hilarious.\r
142 \r
143 To accomodate this new method of accessing video memory, the VGA\r
144 designers introduced a new configuration bit called Chain-4, which\r
145 resides as bit number 3 in index 4 of the Sequencer.  In 16-color modes,\r
146 the default state for this bit is off (zero), and the VGA operates as\r
147 described earlier.  In the VGA's standard 256-color mode, mode 13h, this\r
148 bit is turned on (set to one), and this turns the tieing of bit\r
149 planes and memory address on.\r
150 \r
151 In this state, the bit planes are said to be chained together, thus mode\r
152 13h is often called a _chained mode_.\r
153 \r
154 Note that Chain-4 in itself is not enough to set a 256-color mode -\r
155 there are other registers which deals with the other subtle changes in\r
156 nature from 16 to 256 colors.  But, as we now will base our work with\r
157 mode X on mode 13h, which already is 256-color, we won't bother about\r
158 these for now.\r
159 \r
160 \r
161 \r
162 2. GETTING MORE PAGES AND PUTTING YOUR FIRST PIXEL\r
163 \r
164 The observant reader might at this time suggest that clearing the\r
165 Chain-4 bit after setting mode 13h will give us access to all 256 Kb of\r
166 video memory, as the two least significant bits of the byte address\r
167 won't be `wasted' on selecting a bit plane.  This is correct.  You might\r
168 also start feeling a little uneasy, because something tells you that\r
169 you'll instantly loose the simple addressing scheme of mode 13h.  Sadly,\r
170 that is also correct.\r
171 \r
172 At the moment Chain-4 is cleared, each byte offset addresses *four*\r
173 sequential pixels, corresponding to the four planes addressed in 16-color\r
174 modes.  Every fourth pixel belong in the same plane.  Before writing to a byte\r
175 offset in the video segment, you should make sure that the 4-bit mask in the\r
176 Write Plane Enable register is set correctly, according to which of the four\r
177 addressable pixels you want to modify.  In essence, it works like a 16-color\r
178 mode with a twist.  See figure 2.\r
179 \r
180 So, is this mode X?  Not quite.  We need to elaborate to the VGA how to\r
181 fetch data for refreshing the monitor image.  Explaining the logic\r
182 behind this is beyond the scope of this getting-you-started text, and it\r
183 wouldn't be very interesting anyway.  Also, mode 13h has only 200 lines,\r
184 while I promised 240 lines.  I'll fix that later below.  Here is the minimum\r
185 snippet of code to initiate the 4 page variant of mode 13h (320x200), written\r
186 in plain C, using some DOS specific features (see header for a note about the\r
187 sources included):\r
188 \r
189 ----8<-------cut begin------\r
190 \r
191 /* width and height should specify the mode dimensions.  widthBytes\r
192    specify the width of a line in addressable bytes. */\r
193 \r
194 int width, height, widthBytes;\r
195 \r
196 /* actStart specifies the start of the page being accessed by\r
197    drawing operations.  visStart specifies the contents of the Screen\r
198    Start register, i.e. the start of the visible page */\r
199 \r
200 unsigned actStart, visStart;\r
201 \r
202 /*\r
203  * set320x200x256_X()\r
204  *      sets mode 13h, then turns it into an unchained (planar), 4-page\r
205  *      320x200x256 mode.\r
206  */\r
207 \r
208 set320x200x256_X()\r
209         {\r
210 \r
211         union REGS r;\r
212 \r
213         /* Set VGA BIOS mode 13h: */\r
214 \r
215         r.x.ax = 0x0013;\r
216         int86(0x10, &r, &r);\r
217 \r
218         /* Turn off the Chain-4 bit (bit 3 at index 4, port 0x3c4): */\r
219 \r
220         outport(SEQU_ADDR, 0x0604);\r
221 \r
222         /* Turn off word mode, by setting the Mode Control register\r
223            of the CRT Controller (index 0x17, port 0x3d4): */\r
224 \r
225         outport(CRTC_ADDR, 0xE317);\r
226 \r
227         /* Turn off doubleword mode, by setting the Underline Location\r
228            register (index 0x14, port 0x3d4): */\r
229 \r
230         outport(CRTC_ADDR, 0x0014);\r
231 \r
232         /* Clear entire video memory, by selecting all four planes, then\r
233            writing 0 to the entire segment. */\r
234 \r
235         outport(SEQU_ADDR, 0x0F02);\r
236         memset(vga+1, 0, 0xffff); /* stupid size_t exactly 1 too small */\r
237         vga[0] = 0;\r
238 \r
239         /* Update the global variables to reflect the dimensions of this\r
240            mode.  This is needed by most future drawing operations. */\r
241 \r
242         width   = 320;\r
243         height  = 200;\r
244 \r
245         /* Each byte addresses four pixels, so the width of a scan line\r
246            in *bytes* is one fourth of the number of pixels on a line. */\r
247 \r
248         widthBytes = width / 4;\r
249 \r
250         /* By default we want screen refreshing and drawing operations\r
251            to be based at offset 0 in the video segment. */\r
252 \r
253         actStart = visStart = 0;\r
254 \r
255         }\r
256 \r
257 ----8<-------cut end------\r
258 \r
259 As you can see, I've already provided some of the mechanics needed to\r
260 support multiple pages, by providing the actStart and visStart variables.\r
261 Selecting pages can be done in one of two contexts:\r
262 \r
263         1) selecting the visible page, i.e. which page is visible on\r
264            screen, and\r
265 \r
266         2) selecting the active page, i.e. which page is accessed by\r
267            drawing operations\r
268 \r
269 Selecting the active page is just a matter of offsetting our graphics\r
270 operations by the address of the start of the page, as demonstrated in\r
271 the put pixel routine below.  Selecting the visual page must be passed\r
272 in to the VGA, by setting the Screen Start register.  Sadly enough, the\r
273 resolution of this register is limited to one addressable byte, which\r
274 means four pixels in unchained 256-color modes.  Some further trickery is \r
275 needed for 1-pixel smooth, horizontal scrolling, but I'll make that a subject\r
276 for later.  The setXXXStart() functions provided here accept byte\r
277 offsets as parameters, so they'll work in any mode.  If widthBytes and\r
278 height are set correctly, so will the setXXXPage() functions.\r
279 \r
280 ----8<-------cut begin------\r
281 \r
282 /*\r
283  * setActiveStart() tells our graphics operations which address in video\r
284  * memory should be considered the top left corner.\r
285  */\r
286 \r
287 setActiveStart(unsigned offset)\r
288         {\r
289         actStart = offset;\r
290         }\r
291 \r
292 /*\r
293  * setVisibleStart() tells the VGA from which byte to fetch the first\r
294  * pixel when starting refresh at the top of the screen.  This version\r
295  * won't look very well in time critical situations (games for\r
296  * instance) as the register outputs are not synchronized with the\r
297  * screen refresh.  This refresh might start when the high byte is\r
298  * set, but before the low byte is set, which produces a bad flicker.\r
299  * I won't bother with this now.\r
300  */\r
301 \r
302 setVisibleStart(unsigned offset)\r
303         {\r
304         visStart = offset;\r
305         outport(CRTC_ADDR, 0x0C);               /* set high byte */\r
306         outport(CRTC_ADDR+1, visStart >> 8);\r
307         outport(CRTC_ADDR, 0x0D);               /* set low byte */\r
308         outport(CRTC_ADDR+1, visStart & 0xff);\r
309         }\r
310 \r
311 /*\r
312  * setXXXPage() sets the specified page by multiplying the page number\r
313  * with the size of one page at the current resolution, then handing the\r
314  * resulting offset value over to the corresponding setXXXStart()\r
315  * function.  The first page number is 0.\r
316  */\r
317 \r
318 setActivePage(int page)\r
319         {\r
320         setActiveStart(page * widthBytes * height);\r
321         }\r
322 \r
323 setVisiblePage(int page)\r
324         {\r
325         setVisibleStart(page * widthBytes * height);\r
326         }\r
327 \r
328 ----8<-------cut end------\r
329 \r
330 Due to the use of bit planes, the graphics routines tend to get more\r
331 complex than in mode 13h, and your first versions will generally tend to\r
332 be a little slower than mode 13h algorithms.  Here's a put pixel routine\r
333 for any unchained 256-color mode (it assumes that the 'width' variable\r
334 from the above code is set correctly).  Optimizing is left as an exercise\r
335 to you, the reader.  This will be the only drawing operation I'll cover\r
336 in this article, but all general primitives like lines and circles can be \r
337 based on this routine.  (You'll probably not want to do that though, due\r
338 to the inefficiency.)\r
339 \r
340 ----8<-------cut begin------\r
341 \r
342 putPixel_X(int x, int y, char color)\r
343         {\r
344 \r
345         /* Each address accesses four neighboring pixels, so set\r
346            Write Plane Enable according to which pixel we want\r
347            to modify.  The plane is determined by the two least\r
348            significant bits of the x-coordinate: */\r
349 \r
350         outportb(0x3c4, 0x02);\r
351         outportb(0x3c5, 0x01 << (x & 3));\r
352 \r
353         /* The offset of the pixel into the video segment is\r
354            offset = (width * y + x) / 4, and write the given\r
355            color to the plane we selected above.  Heed the active\r
356            page start selection. */\r
357 \r
358         vga[(unsigned)(widthBytes * y) + (x / 4) + actStart] = color;\r
359 \r
360         }\r
361 \r
362 char getPixel_X(int x, int y)\r
363         {\r
364 \r
365         /* Select the plane from which we must read the pixel color: */\r
366 \r
367         outport(GRAC_ADDR, 0x04);\r
368         outport(GRAC_ADDR+1, x & 3);\r
369 \r
370         return vga[(unsigned)(widthBytes * y) + (x / 4) + actStart];\r
371 \r
372         }\r
373 \r
374 ----8<-------cut end------\r
375 \r
376 \r
377 However, by now you should be aware of that the Write Plane Enable\r
378 register isn't limited to selecting just one bit plane, like the\r
379 Read Plane Select register is.  You can enable any combination of all\r
380 four to be written.  This ability to access 4 pixels with one\r
381 instruction helps quadrupling the speed in certain respects, especially when \r
382 drawing horizontal lines and filling polygons of a constant color.  Also, most \r
383 block algorithms can be optimized in various ways so that they need only\r
384 a constant number of OUTs (typically four) to the Write Plane Enable\r
385 register.  OUT is a relatively slow instruction.\r
386 \r
387 The gained ability to access the full 256 Kb of memory on a standard\r
388 VGA enables you to do paging and all the goodies following from that:\r
389 smooth scrolling over large maps, page flipping for flicker free\r
390 animation... and I'll leave something for your own imagination.\r
391 \r
392 In short, the stuff gained from unchaining mode 13h more than \r
393 upweighs the additional complexity of using a planar mode.  \r
394 \r
395 Now, the resolution of the mode is of little interest in this\r
396 context.  Nearly any 256-color resolution from (about) 80x8 to 400x300\r
397 is available for most VGAs.  I'll dwell particularly by 320x240, as this\r
398 is the mode that Michael Abrash introduced as 'Mode X' in his DDJ\r
399 articles.  It is also the resolution that most people refer to when\r
400 using that phrase.\r
401 \r
402 The good thing about the 320x240 mode is that the aspect ratio is\r
403 1:1, which means that each pixel is 'perfectly' square, i.e. not\r
404 rectangular like in 320x200.  An ellipse drawn with the same number of\r
405 pixels along both main axes will look like a perfect circle in 320x240,\r
406 but like a subtly tall ellipse in 320x200.\r
407 \r
408 Here's a function which sets the 320x240 mode.  You'll notice that\r
409 it depends on the first piece of code above:\r
410 \r
411 ----8<-------cut begin------\r
412 \r
413 set320x240x256_X()\r
414         {\r
415 \r
416         /* Set the unchained version of mode 13h: */\r
417 \r
418         set320x200x256_X();\r
419 \r
420         /* Modify the vertical sync polarity bits in the Misc. Output\r
421            Register to achieve square aspect ratio: */\r
422 \r
423         outportb(0x3C2, 0xE3);\r
424 \r
425         /* Modify the vertical timing registers to reflect the increased\r
426            vertical resolution, and to center the image as good as\r
427            possible: */\r
428 \r
429         outport(0x3D4, 0x2C11);         /* turn off write protect */\r
430         outport(0x3D4, 0x0D06);         /* vertical total */\r
431         outport(0x3D4, 0x3E07);         /* overflow register */\r
432         outport(0x3D4, 0xEA10);         /* vertical retrace start */\r
433         outport(0x3D4, 0xAC11);         /* vertical retrace end AND wr.prot */\r
434         outport(0x3D4, 0xDF12);         /* vertical display enable end */\r
435         outport(0x3D4, 0xE715);         /* start vertical blanking */\r
436         outport(0x3D4, 0x0616);         /* end vertical blanking */\r
437 \r
438         /* Update mode info, so future operations are aware of the\r
439            resolution: */\r
440 \r
441         height = 240;\r
442 \r
443         }\r
444 \r
445 ----8<-------cut end------\r
446 \r
447 \r
448 As you've figured out, this mode will be completely compatible with the\r
449 utility functions presented earlier, thanks to the global variable\r
450 'height'.  Boy, am I foreseeing or what!\r
451 \r
452 Other resolutions are achieved through giving other values to the sync\r
453 timing registers of the VGA, but this is quite a large and complex\r
454 subject, so I'll postpone this to later, if ever.\r
455 \r
456 Anyway, I hope I've helped getting you started using mode X.  As far as\r
457 I know, the two modes I've used above should work on *any* VGA and Super\r
458 VGA available, so this is pretty stable stuff.  Let me know of any \r
459 trouble, and -\r
460                         good luck!\r
461 \r
462 \r
463 \r
464 3. THE ROAD FROM HERE\r
465 \r
466 I'm providing information on various libraries and archives which relate\r
467 to what this article deals with.  If you want me to add anything to this\r
468 list (for future articles), let me know, although I can't promise anything.\r
469 I am assuming you have ftp access.\r
470 \r
471 \r
472 wuarchive.wustl.edu:/pub/MSDOS_UPLOADS/programming/xlib06.zip\r
473 \r
474 This is the current de facto C/assembler library for programming\r
475 unchained modes (do not confuse with a X Windows library).  All sources\r
476 are included, and the library is totally free.  It has functions for\r
477 pixels, lines, circles, bezier curves, mouse handling, sprites (bitmaps),\r
478 compiled bitmaps, and supports a number of resolutions.  The version number\r
479 ('06') is current as of November 1993.\r
480 \r
481 \r
482 graphprg.zip\r
483 \r
484 Michael Abrash' articles in Doctor Dobbs Journal is always mentioned\r
485 with awe.  In this 350 Kb archive, most of his interesting stuff has\r
486 been gathered.  Read about Mode X development and techniques from month\r
487 to month.  Included is also all the individual source code snippets from\r
488 each article, and also the full XSHARP library providing linedrawing,\r
489 polygons, bitmaps, solid 3D projection and speedy rendering, and even an\r
490 implementation of 2D texture mapping (can be used for quasi-3D texture\r
491 mapping), plus an article on assembly optimization on the i86 processor\r
492 family.  Definitely recommended.\r
493 \r
494 \r
495 oak.oakland.edu:/pub/msdos/vga/vgadoc2.zip\r
496 \r
497 This is a bare bones VGA register reference.  It also contains register\r
498 references for the CGA, EGA and Hercules cards, in addition to dozens of\r
499 SuperVGAs.  Check out the BOOKS section for some decent VGA references\r
500 though - you don't want to start tweaking without a real one.\r
501 \r
502 \r
503 wuarchive.wustl.edu:/pub/MSDOS_UPLOADS/programming/tweak15b.zip\r
504 \r
505 TWEAK might be of interest to the more adventurous reader.  TWEAK lets you\r
506 play around with the registers of the VGA in an interactive manner.\r
507 Various testing screens for viewing your newmade modes are applied at\r
508 the press of a key.  Version 1.5 adds a test screen which autodetects your \r
509 graphics mode and displays various information about resolutions etc.\r
510 Keep a VGA reference handy.  Don't try it if this is the first time you've \r
511 heard of 'registers' or 'mode X' or 'tweaking'.  I was planning a version\r
512 based on the Turbo Vision interface, but time has been short.  Maybe later!\r
513 \r
514 \r
515 \r
516 \r
517 4. BOOKS ON THE SUBJECT\r
518 \r
519 Extremely little has been published in written form about using\r
520 'Mode X'-style modes.  Below are some books which cover VGA programming\r
521 at varying degrees of technical level, but the only one to mention\r
522 unchained modes and Mode X, is Michael Abrash'.  I'd get one of the VGA\r
523 references first, though.\r
524 \r
525   o  George Sutty & Steve Blair : "Advanced Pogrammer's Guide to the\r
526      EGA/VGA" from Brady.  A bit old perhaps, but covers all *standard*\r
527      EGA/VGA registers, and discusses most BIOS functions and other\r
528      operations.  Contains disk with C/Pascal/assembler source code.\r
529      There's a sequel out for SuperVGAs, which I haven't seen.\r
530 \r
531   o  Michael Abrash : "Power Graphics Programming" from QUE/Programmer's\r
532      Journal.  Collections of (old) articles from Programmer's Journal on\r
533      EGA/VGA, read modes and write modes, animation, tweaking (320x400\r
534      and 360x480).  His newer ravings in DDJ covers fast 256-color\r
535      bitmaps, compiled bitmaps, polygons, 3D graphics, texture mapping\r
536      among other stuff.\r
537 \r
538   o  Richard F. Ferraro : "Programmer's Guide to the EGA and VGA video\r
539      cards including Super VGA".  I don't have this one, but heard it's\r
540      nice.  Detailed coverage of all EGA/VGA registers.  The Super VGA\r
541      reference makes it attractive.\r
542 \r
543   o  Richard Wilton : "Programmer's Guide to PC & PS/2 Video Systems"\r
544      Less technical, more application/algorithm oriented.  Nice enough,\r
545      even though it is a bit outdated, in that he discusses CGA and\r
546      Hercules cards just as much as EGA/VGA.\r
547 \r
548 \r
549 \r
550 \r
551 5. BYE - FOR NOW\r
552 \r
553 I am considering writing a text describing in more detail the process of\r
554 using TWEAK to achieve the VGA resolution you want or need.  However, I\r
555 thought I'd let this document go first, and see if I get any reactions.\r
556 If I don't, I'll stop.  Feel free to forward any suggestions,\r
557 criticisms, bombs and beers.\r
558 \r
559 I can be reached via:\r
560 \r
561   o  e-mail: robert@stud.unit.no\r
562 \r
563   o  land mail:\r
564 \r
565      Robert Schmidt\r
566      Stud.post 170\r
567      NTH\r
568      N-7034 Trondheim\r
569      NORWAY\r
570 \r
571 Nothing would encourage or please me more than a postcard from where you\r
572 live!\r
573 \r
574 ÚÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ\r
575 ³ M1ORG.ASC ³\r
576 ÀÄÄÄÄÄÄÄÄÄÄÄÙ\r
577 \r
578 Figure 1: Memory organization in mode 13h (ASCII version)\r
579           by Robert Schmidt\r
580           (C) 1993 Ztiff Zox Softwear\r
581 \r
582 a. Imagine that the top of the screen looks like this (pixel values are\r
583    represented by color digits 0-9 for simplicity - actual colors may\r
584    range from 0 to 255) - a screen width of 320 pixels is assumed:\r
585 \r
586     address:  0         10                310      319\r
587              ----------------------------------------\r
588              |0123456789012345    .....   0123456789|\r
589              |                                      |\r
590              |                                      |\r
591              |\r
592 \r
593 b. In VGA memory, the screen is represented as follows (question marks\r
594    represent unused bytes):\r
595 \r
596    Plane 0:\r
597 \r
598     address:  0         10                310      319\r
599              ----------------------------------------\r
600              |0???4???8???2???    .....   ??2???6???|\r
601              |                                      |\r
602              |                                      |\r
603 \r
604    Plane 1:\r
605 \r
606     address:  0         10                310      319\r
607              ----------------------------------------\r
608              |?1???5???9???3??    .....   ???3???7??|\r
609              |                                      |\r
610              |                                      |\r
611 \r
612    Plane 2:\r
613 \r
614     address:  0         10                310      319\r
615              ----------------------------------------\r
616              |??2???6???0???4?    .....   0???4???8?|\r
617              |                                      |\r
618              |                                      |\r
619 \r
620    Plane 3:\r
621 \r
622     address:  0         10                310      319\r
623              ----------------------------------------\r
624              |???3???7???1???5    .....   ?1???5???9|\r
625              |                                      |\r
626              |                                      |\r
627 \r
628    I.e. a plane is selected automatically by the two least significant\r
629    bits of the address of the byte being read from or written two.\r
630    This renders 3/4 of the video memory unavailable and useless, but\r
631    all visible pixels are easily accessed, as each address in the video\r
632    segment provides access to one and ONLY ONE pixel.\r
633 \r
634 ÚÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ\r
635 ³ MXORG.ASC ³\r
636 ÀÄÄÄÄÄÄÄÄÄÄÄÙ\r
637 \r
638 Figure 2: Memory organization in unchained 256-color modes (like\r
639           Mode X) (ASCII version)\r
640           by Robert Schmidt\r
641           (C) 1993 Ztiff Zox Softwear\r
642 \r
643 \r
644 Imagine that the screen looks the same as in figure 1a.  A screen width\r
645 of 320 pixels is still assumed.\r
646 \r
647 In VGA memory, the screen will be represented as follows:\r
648 \r
649    Plane 0:\r
650 \r
651     address:  0         10                70       79 (NOT 319!)\r
652              ----------------------------------------\r
653              |0482604826048260    .....   0482604826|\r
654              |                                      |\r
655              |                                      |\r
656 \r
657    Plane 1:\r
658 \r
659     address:  0         10                70       79\r
660              ----------------------------------------\r
661              |1593715937159371    .....   1593715937|\r
662              |                                      |\r
663              |                                      |\r
664 \r
665    Plane 2:\r
666 \r
667     address:  0         10                70       79\r
668              ----------------------------------------\r
669              |2604826048260482    .....   2604826048|\r
670              |                                      |\r
671              |                                      |\r
672 \r
673    Plane 3:\r
674 \r
675     address:  0         10                70       79\r
676              ----------------------------------------\r
677              |3715937159371593    .....   3715937159|\r
678              |                                      |\r
679              |                                      |\r
680 \r
681 Note that if pixel i is in plane p, pixel i+1 is in plane (p+1)%4.\r
682 When the planes are unchained, we need to set the Write Plane Enable\r
683 register to select which planes should receive the data when writing,\r
684 or the Read Plane Select register when reading.  As is evident, one \r
685 address in the video segment provides access to no less than FOUR\r
686 different pixels.\r
687 \r
688 ÚÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ\r
689 ³ Zox3D ³\r
690 ÀÄÄÄÄÄÄÄÙ\r
691 \r
692 Available via ftp :\r
693 ftp.wustl.edu:/pub/MSDOS_UPLOADS/games/programming/zox3d15.zip\r
694 wasp.eng.ufl.edu:/pub/msdos/demos/<somewhere>/zox3d15.zip\r
695 \r
696 zox3d15.zip contains a demo of my 3D graphics engine.\r
697 It resembles Wolf3D, but has a number of additional\r
698 features:\r
699 \r
700 - texture mapped floor and ceiling (sky, in this demo)\r
701 - real, recursive MIRRORS!\r
702 - partly TRANSPARENT walls\r
703 - input from keyboard, joystick and mouse (at the same\r
704   time, too, if you wish)\r
705 - controllable camera height - NOT fixed like Wolf3D\r
706 - quick resizable window\r
707 - online help and fps rating\r
708 - advanced collision detection and handling\r
709 - supports a variety of tweaked X modes, from 256x256 to 400x300.\r
710 \r
711 The sky and mirrors have to be seen to be beleived!\r
712 \r
713 Zox3D does NOT implement objects, like the guards in\r
714 Wolf3D, but that should be a breeze to add.\r
715 \r
716 The complete sources are available.  Read ZOX3D.DOC in\r
717 the demo archive for information.\r
718 \r
719 ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ\r
720 Robert Schmidt - robert@stud.unit.no - Buuud@IRC\r