1 /* 2 * PROJECT: ReactOS VGA Miniport Driver 3 * LICENSE: Microsoft NT4 DDK Sample Code License 4 * FILE: win32ss/drivers/miniport/vga_new/modeset.c 5 * PURPOSE: Handles switching to Standard VGA Modes for compatible cards 6 * PROGRAMMERS: Copyright (c) 1992 Microsoft Corporation 7 * ReactOS Portable Systems Group 8 */ 9 10 #include "vga.h" 11 12 VP_STATUS 13 NTAPI 14 VgaInterpretCmdStream( 15 PHW_DEVICE_EXTENSION HwDeviceExtension, 16 PUSHORT pusCmdStream 17 ); 18 19 VP_STATUS 20 NTAPI 21 VgaSetMode( 22 PHW_DEVICE_EXTENSION HwDeviceExtension, 23 PVIDEO_MODE Mode, 24 ULONG ModeSize, 25 // eVb: 2.1 [SET MODE] - Add new output parameter for framebuffer update functionality 26 PULONG PhysPtrChange 27 // eVb: 2.1 [END] 28 ); 29 30 VP_STATUS 31 NTAPI 32 VgaQueryAvailableModes( 33 PHW_DEVICE_EXTENSION HwDeviceExtension, 34 PVIDEO_MODE_INFORMATION ModeInformation, 35 ULONG ModeInformationSize, 36 PULONG_PTR OutputSize 37 ); 38 39 VP_STATUS 40 NTAPI 41 VgaQueryNumberOfAvailableModes( 42 PHW_DEVICE_EXTENSION HwDeviceExtension, 43 PVIDEO_NUM_MODES NumModes, 44 ULONG NumModesSize, 45 PULONG_PTR OutputSize 46 ); 47 48 VP_STATUS 49 NTAPI 50 VgaQueryCurrentMode( 51 PHW_DEVICE_EXTENSION HwDeviceExtension, 52 PVIDEO_MODE_INFORMATION ModeInformation, 53 ULONG ModeInformationSize, 54 PULONG_PTR OutputSize 55 ); 56 57 VOID 58 NTAPI 59 VgaZeroVideoMemory( 60 PHW_DEVICE_EXTENSION HwDeviceExtension 61 ); 62 63 #if defined(ALLOC_PRAGMA) 64 #pragma alloc_text(PAGE,VgaInterpretCmdStream) 65 #pragma alloc_text(PAGE,VgaSetMode) 66 #pragma alloc_text(PAGE,VgaQueryAvailableModes) 67 #pragma alloc_text(PAGE,VgaQueryNumberOfAvailableModes) 68 #pragma alloc_text(PAGE,VgaZeroVideoMemory) 69 #endif 70 71 //--------------------------------------------------------------------------- 72 VP_STATUS 73 NTAPI 74 VgaInterpretCmdStream( 75 PHW_DEVICE_EXTENSION HwDeviceExtension, 76 PUSHORT pusCmdStream 77 ) 78 79 /*++ 80 81 Routine Description: 82 83 Interprets the appropriate command array to set up VGA registers for the 84 requested mode. Typically used to set the VGA into a particular mode by 85 programming all of the registers 86 87 Arguments: 88 89 HwDeviceExtension - Pointer to the miniport driver's device extension. 90 91 pusCmdStream - array of commands to be interpreted. 92 93 Return Value: 94 95 The status of the operation (can only fail on a bad command); TRUE for 96 success, FALSE for failure. 97 98 --*/ 99 100 { 101 ULONG ulCmd; 102 ULONG_PTR ulPort; 103 UCHAR jValue; 104 USHORT usValue; 105 ULONG culCount; 106 ULONG ulIndex; 107 ULONG_PTR ulBase; 108 109 if (pusCmdStream == NULL) { 110 111 VideoDebugPrint((1, "VgaInterpretCmdStream - Invalid pusCmdStream\n")); 112 return TRUE; 113 } 114 115 ulBase = (ULONG_PTR)HwDeviceExtension->IOAddress; 116 117 // 118 // Now set the adapter to the desired mode. 119 // 120 121 while ((ulCmd = *pusCmdStream++) != EOD) { 122 123 // 124 // Determine major command type 125 // 126 127 switch (ulCmd & 0xF0) { 128 129 // 130 // Basic input/output command 131 // 132 133 case INOUT: 134 135 // 136 // Determine type of inout instruction 137 // 138 139 if (!(ulCmd & IO)) { 140 141 // 142 // Out instruction. Single or multiple outs? 143 // 144 145 if (!(ulCmd & MULTI)) { 146 147 // 148 // Single out. Byte or word out? 149 // 150 151 if (!(ulCmd & BW)) { 152 153 // 154 // Single byte out 155 // 156 157 ulPort = *pusCmdStream++; 158 jValue = (UCHAR) *pusCmdStream++; 159 VideoPortWritePortUchar((PUCHAR)(ulBase+ulPort), 160 jValue); 161 162 } else { 163 164 // 165 // Single word out 166 // 167 168 ulPort = *pusCmdStream++; 169 usValue = *pusCmdStream++; 170 VideoPortWritePortUshort((PUSHORT)(ulBase+ulPort), 171 usValue); 172 173 } 174 175 } else { 176 177 // 178 // Output a string of values 179 // Byte or word outs? 180 // 181 182 if (!(ulCmd & BW)) { 183 184 // 185 // String byte outs. Do in a loop; can't use 186 // VideoPortWritePortBufferUchar because the data 187 // is in USHORT form 188 // 189 190 ulPort = ulBase + *pusCmdStream++; 191 culCount = *pusCmdStream++; 192 193 while (culCount--) { 194 jValue = (UCHAR) *pusCmdStream++; 195 VideoPortWritePortUchar((PUCHAR)ulPort, 196 jValue); 197 198 } 199 200 } else { 201 202 // 203 // String word outs 204 // 205 206 ulPort = *pusCmdStream++; 207 culCount = *pusCmdStream++; 208 VideoPortWritePortBufferUshort((PUSHORT) 209 (ulBase + ulPort), pusCmdStream, culCount); 210 pusCmdStream += culCount; 211 212 } 213 } 214 215 } else { 216 217 // In instruction 218 // 219 // Currently, string in instructions aren't supported; all 220 // in instructions are handled as single-byte ins 221 // 222 // Byte or word in? 223 // 224 225 if (!(ulCmd & BW)) { 226 // 227 // Single byte in 228 // 229 230 ulPort = *pusCmdStream++; 231 jValue = VideoPortReadPortUchar((PUCHAR)ulBase+ulPort); 232 233 } else { 234 235 // 236 // Single word in 237 // 238 239 ulPort = *pusCmdStream++; 240 usValue = VideoPortReadPortUshort((PUSHORT) 241 (ulBase+ulPort)); 242 243 } 244 245 } 246 247 break; 248 249 // 250 // Higher-level input/output commands 251 // 252 253 case METAOUT: 254 255 // 256 // Determine type of metaout command, based on minor 257 // command field 258 // 259 switch (ulCmd & 0x0F) { 260 261 // 262 // Indexed outs 263 // 264 265 case INDXOUT: 266 267 ulPort = ulBase + *pusCmdStream++; 268 culCount = *pusCmdStream++; 269 ulIndex = *pusCmdStream++; 270 271 while (culCount--) { 272 273 usValue = (USHORT) (ulIndex + 274 (((ULONG)(*pusCmdStream++)) << 8)); 275 VideoPortWritePortUshort((PUSHORT)ulPort, usValue); 276 277 ulIndex++; 278 279 } 280 281 break; 282 283 // 284 // Masked out (read, AND, XOR, write) 285 // 286 287 case MASKOUT: 288 289 ulPort = *pusCmdStream++; 290 jValue = VideoPortReadPortUchar((PUCHAR)ulBase+ulPort); 291 jValue &= *pusCmdStream++; 292 jValue ^= *pusCmdStream++; 293 VideoPortWritePortUchar((PUCHAR)ulBase + ulPort, 294 jValue); 295 break; 296 297 // 298 // Attribute Controller out 299 // 300 301 case ATCOUT: 302 303 ulPort = ulBase + *pusCmdStream++; 304 culCount = *pusCmdStream++; 305 ulIndex = *pusCmdStream++; 306 307 while (culCount--) { 308 309 // Write Attribute Controller index 310 VideoPortWritePortUchar((PUCHAR)ulPort, 311 (UCHAR)ulIndex); 312 313 // Write Attribute Controller data 314 jValue = (UCHAR) *pusCmdStream++; 315 VideoPortWritePortUchar((PUCHAR)ulPort, jValue); 316 317 ulIndex++; 318 319 } 320 321 break; 322 323 // 324 // None of the above; error 325 // 326 default: 327 328 return FALSE; 329 330 } 331 332 333 break; 334 335 // 336 // NOP 337 // 338 339 case NCMD: 340 341 break; 342 343 // 344 // Unknown command; error 345 // 346 347 default: 348 349 return FALSE; 350 351 } 352 353 } 354 355 return TRUE; 356 357 } // end VgaInterpretCmdStream() 358 359 VP_STATUS 360 NTAPI 361 VgaSetMode( 362 PHW_DEVICE_EXTENSION HwDeviceExtension, 363 PVIDEO_MODE Mode, 364 ULONG ModeSize, 365 // eVb: 2.2 [SET MODE] - Add new output parameter for framebuffer update functionality 366 PULONG PhysPtrChange 367 // eVb: 2.2 [END] 368 ) 369 370 /*++ 371 372 Routine Description: 373 374 This routine sets the vga into the requested mode. 375 376 Arguments: 377 378 HwDeviceExtension - Pointer to the miniport driver's device extension. 379 380 Mode - Pointer to the structure containing the information about the 381 font to be set. 382 383 ModeSize - Length of the input buffer supplied by the user. 384 385 Return Value: 386 387 ERROR_INSUFFICIENT_BUFFER if the input buffer was not large enough 388 for the input data. 389 390 ERROR_INVALID_PARAMETER if the mode number is invalid. 391 392 NO_ERROR if the operation completed successfully. 393 394 --*/ 395 396 { 397 PVIDEOMODE pRequestedMode; 398 VP_STATUS status; 399 ULONG RequestedModeNum; 400 // eVb: 2.3 [SET MODE] - Add new output parameter for framebuffer update functionality 401 *PhysPtrChange = FALSE; 402 // eVb: 2.3 [END] 403 // 404 // Check if the size of the data in the input buffer is large enough. 405 // 406 407 if (ModeSize < sizeof(VIDEO_MODE)) 408 { 409 return ERROR_INSUFFICIENT_BUFFER; 410 } 411 412 // 413 // Extract the clear memory, and map linear bits. 414 // 415 416 RequestedModeNum = Mode->RequestedMode & 417 ~(VIDEO_MODE_NO_ZERO_MEMORY | VIDEO_MODE_MAP_MEM_LINEAR); 418 419 420 if (!(Mode->RequestedMode & VIDEO_MODE_NO_ZERO_MEMORY)) 421 { 422 #if defined(_X86_) 423 VgaZeroVideoMemory(HwDeviceExtension); 424 #endif 425 } 426 427 // 428 // Check to see if we are requesting a valid mode 429 // 430 // eVb: 2.4 [CIRRUS] - Remove Cirrus-specific check for valid mode 431 if ( (RequestedModeNum >= NumVideoModes) ) 432 // eVb: 2.4 [END] 433 { 434 VideoDebugPrint((0, "Invalide Mode Number = %d!\n", RequestedModeNum)); 435 436 return ERROR_INVALID_PARAMETER; 437 } 438 439 VideoDebugPrint((2, "Attempting to set mode %d\n", 440 RequestedModeNum)); 441 // eVb: 2.5 [VBE] - Use dynamic VBE mode list instead of hard-coded VGA list 442 pRequestedMode = &VgaModeList[RequestedModeNum]; 443 // eVb: 2.5 [END] 444 VideoDebugPrint((2, "Info on Requested Mode:\n" 445 "\tResolution: %dx%d\n", 446 pRequestedMode->hres, 447 pRequestedMode->vres )); 448 449 // 450 // VESA BIOS mode switch 451 // 452 // eVb: 2.6 [VBE] - VBE Mode Switch Support 453 status = VbeSetMode(HwDeviceExtension, pRequestedMode, PhysPtrChange); 454 if (status == ERROR_INVALID_FUNCTION) 455 { 456 // 457 // VGA mode switch 458 // 459 460 if (!pRequestedMode->CmdStream) return ERROR_INVALID_FUNCTION; 461 if (!VgaInterpretCmdStream(HwDeviceExtension, pRequestedMode->CmdStream)) return ERROR_INVALID_FUNCTION; 462 goto Cleanup; 463 } 464 else if (status != NO_ERROR) return status; 465 // eVb: 2.6 [END] 466 // eVb: 2.7 [MODE-X] - Windows VGA Miniport Supports Mode-X, we should too 467 // 468 // ModeX check 469 // 470 471 if (pRequestedMode->hres == 320) 472 { 473 VideoDebugPrint((0, "ModeX not support!!!\n")); 474 return ERROR_INVALID_PARAMETER; 475 } 476 // eVb: 2.7 [END] 477 // 478 // Text mode check 479 // 480 481 if (!(pRequestedMode->fbType & VIDEO_MODE_GRAPHICS)) 482 { 483 // eVb: 2.8 [TODO] - This code path is not implemented yet 484 VideoDebugPrint((0, "Text-mode not support!!!\n")); 485 return ERROR_INVALID_PARAMETER; 486 // eVb: 2.8 [END] 487 } 488 489 Cleanup: 490 // 491 // Update the location of the physical frame buffer within video memory. 492 // 493 // eVb: 2.9 [VBE] - Linear and banked support is unified in VGA, unlike Cirrus 494 HwDeviceExtension->PhysicalVideoMemoryBase.LowPart = pRequestedMode->PhysBase; 495 HwDeviceExtension->PhysicalVideoMemoryLength = pRequestedMode->PhysSize; 496 497 HwDeviceExtension->PhysicalFrameLength = 498 pRequestedMode->FrameBufferSize; 499 500 HwDeviceExtension->PhysicalFrameOffset.LowPart = 501 pRequestedMode->FrameBufferBase; 502 // eVb: 2.9 [END] 503 504 // 505 // Store the new mode value. 506 // 507 508 HwDeviceExtension->CurrentMode = pRequestedMode; 509 HwDeviceExtension->ModeIndex = Mode->RequestedMode; 510 511 return NO_ERROR; 512 513 } //end VgaSetMode() 514 515 VP_STATUS 516 NTAPI 517 VgaQueryAvailableModes( 518 PHW_DEVICE_EXTENSION HwDeviceExtension, 519 PVIDEO_MODE_INFORMATION ModeInformation, 520 ULONG ModeInformationSize, 521 PULONG_PTR OutputSize 522 ) 523 524 /*++ 525 526 Routine Description: 527 528 This routine returns the list of all available available modes on the 529 card. 530 531 Arguments: 532 533 HwDeviceExtension - Pointer to the miniport driver's device extension. 534 535 ModeInformation - Pointer to the output buffer supplied by the user. 536 This is where the list of all valid modes is stored. 537 538 ModeInformationSize - Length of the output buffer supplied by the user. 539 540 OutputSize - Pointer to a buffer in which to return the actual size of 541 the data in the buffer. If the buffer was not large enough, this 542 contains the minimum required buffer size. 543 544 Return Value: 545 546 ERROR_INSUFFICIENT_BUFFER if the output buffer was not large enough 547 for the data being returned. 548 549 NO_ERROR if the operation completed successfully. 550 551 --*/ 552 553 { 554 PVIDEO_MODE_INFORMATION videoModes = ModeInformation; 555 ULONG i; 556 557 // 558 // Find out the size of the data to be put in the buffer and return 559 // that in the status information (whether or not the information is 560 // there). If the buffer passed in is not large enough return an 561 // appropriate error code. 562 // 563 564 if (ModeInformationSize < (*OutputSize = 565 // eVb: 2.10 [VBE] - We store VBE/VGA mode count in this global, not in DevExt like Cirrus 566 NumVideoModes * 567 // eVb: 2.10 [END] 568 sizeof(VIDEO_MODE_INFORMATION)) ) { 569 570 return ERROR_INSUFFICIENT_BUFFER; 571 572 } 573 574 // 575 // For each mode supported by the card, store the mode characteristics 576 // in the output buffer. 577 // 578 579 for (i = 0; i < NumVideoModes; i++) 580 { 581 videoModes->Length = sizeof(VIDEO_MODE_INFORMATION); 582 videoModes->ModeIndex = i; 583 // eVb: 2.11 [VBE] - Use dynamic VBE mode list instead of hard-coded VGA list 584 videoModes->VisScreenWidth = VgaModeList[i].hres; 585 videoModes->ScreenStride = VgaModeList[i].wbytes; 586 videoModes->VisScreenHeight = VgaModeList[i].vres; 587 videoModes->NumberOfPlanes = VgaModeList[i].numPlanes; 588 videoModes->BitsPerPlane = VgaModeList[i].bitsPerPlane; 589 videoModes->Frequency = VgaModeList[i].Frequency; 590 videoModes->XMillimeter = 320; // temporary hardcoded constant 591 videoModes->YMillimeter = 240; // temporary hardcoded constant 592 videoModes->AttributeFlags = VgaModeList[i].fbType; 593 // eVb: 2.11 [END] 594 595 if ((VgaModeList[i].bitsPerPlane == 32) || 596 (VgaModeList[i].bitsPerPlane == 24)) 597 { 598 599 videoModes->NumberRedBits = 8; 600 videoModes->NumberGreenBits = 8; 601 videoModes->NumberBlueBits = 8; 602 videoModes->RedMask = 0xff0000; 603 videoModes->GreenMask = 0x00ff00; 604 videoModes->BlueMask = 0x0000ff; 605 606 } 607 else if (VgaModeList[i].bitsPerPlane == 16) 608 { 609 610 videoModes->NumberRedBits = 6; 611 videoModes->NumberGreenBits = 6; 612 videoModes->NumberBlueBits = 6; 613 videoModes->RedMask = 0x1F << 11; 614 videoModes->GreenMask = 0x3F << 5; 615 videoModes->BlueMask = 0x1F; 616 617 } 618 // eVb: 2.12 [VGA] - Add support for 15bpp modes, which Cirrus doesn't support 619 else if (VgaModeList[i].bitsPerPlane == 15) 620 { 621 622 videoModes->NumberRedBits = 6; 623 videoModes->NumberGreenBits = 6; 624 videoModes->NumberBlueBits = 6; 625 videoModes->RedMask = 0x3E << 9; 626 videoModes->GreenMask = 0x1F << 5; 627 videoModes->BlueMask = 0x1F; 628 } 629 // eVb: 2.12 [END] 630 else 631 { 632 633 videoModes->NumberRedBits = 6; 634 videoModes->NumberGreenBits = 6; 635 videoModes->NumberBlueBits = 6; 636 videoModes->RedMask = 0; 637 videoModes->GreenMask = 0; 638 videoModes->BlueMask = 0; 639 } 640 641 // eVb: 2.13 [VGA] - All modes are palette managed/driven, unlike Cirrus 642 videoModes->AttributeFlags |= VIDEO_MODE_PALETTE_DRIVEN | 643 VIDEO_MODE_MANAGED_PALETTE; 644 // eVb: 2.13 [END] 645 videoModes++; 646 647 } 648 649 return NO_ERROR; 650 651 } // end VgaGetAvailableModes() 652 653 VP_STATUS 654 NTAPI 655 VgaQueryNumberOfAvailableModes( 656 PHW_DEVICE_EXTENSION HwDeviceExtension, 657 PVIDEO_NUM_MODES NumModes, 658 ULONG NumModesSize, 659 PULONG_PTR OutputSize 660 ) 661 662 /*++ 663 664 Routine Description: 665 666 This routine returns the number of available modes for this particular 667 video card. 668 669 Arguments: 670 671 HwDeviceExtension - Pointer to the miniport driver's device extension. 672 673 NumModes - Pointer to the output buffer supplied by the user. This is 674 where the number of modes is stored. 675 676 NumModesSize - Length of the output buffer supplied by the user. 677 678 OutputSize - Pointer to a buffer in which to return the actual size of 679 the data in the buffer. 680 681 Return Value: 682 683 ERROR_INSUFFICIENT_BUFFER if the output buffer was not large enough 684 for the data being returned. 685 686 NO_ERROR if the operation completed successfully. 687 688 --*/ 689 690 { 691 // 692 // Find out the size of the data to be put in the the buffer and return 693 // that in the status information (whether or not the information is 694 // there). If the buffer passed in is not large enough return an 695 // appropriate error code. 696 // 697 698 if (NumModesSize < (*OutputSize = sizeof(VIDEO_NUM_MODES)) ) { 699 700 return ERROR_INSUFFICIENT_BUFFER; 701 702 } 703 704 // 705 // Store the number of modes into the buffer. 706 // 707 708 // eVb: 2.14 [VBE] - We store VBE/VGA mode count in this global, not in DevExt like Cirrus 709 NumModes->NumModes = NumVideoModes; 710 // eVb: 2.14 [END] 711 NumModes->ModeInformationLength = sizeof(VIDEO_MODE_INFORMATION); 712 713 return NO_ERROR; 714 715 } // end VgaGetNumberOfAvailableModes() 716 717 VP_STATUS 718 NTAPI 719 VgaQueryCurrentMode( 720 PHW_DEVICE_EXTENSION HwDeviceExtension, 721 PVIDEO_MODE_INFORMATION ModeInformation, 722 ULONG ModeInformationSize, 723 PULONG_PTR OutputSize 724 ) 725 726 /*++ 727 728 Routine Description: 729 730 This routine returns a description of the current video mode. 731 732 Arguments: 733 734 HwDeviceExtension - Pointer to the miniport driver's device extension. 735 736 ModeInformation - Pointer to the output buffer supplied by the user. 737 This is where the current mode information is stored. 738 739 ModeInformationSize - Length of the output buffer supplied by the user. 740 741 OutputSize - Pointer to a buffer in which to return the actual size of 742 the data in the buffer. If the buffer was not large enough, this 743 contains the minimum required buffer size. 744 745 Return Value: 746 747 ERROR_INSUFFICIENT_BUFFER if the output buffer was not large enough 748 for the data being returned. 749 750 NO_ERROR if the operation completed successfully. 751 752 --*/ 753 754 { 755 // 756 // check if a mode has been set 757 // 758 759 if (HwDeviceExtension->CurrentMode == NULL ) { 760 761 return ERROR_INVALID_FUNCTION; 762 763 } 764 765 // 766 // Find out the size of the data to be put in the the buffer and return 767 // that in the status information (whether or not the information is 768 // there). If the buffer passed in is not large enough return an 769 // appropriate error code. 770 // 771 772 if (ModeInformationSize < (*OutputSize = sizeof(VIDEO_MODE_INFORMATION))) { 773 774 return ERROR_INSUFFICIENT_BUFFER; 775 776 } 777 778 // 779 // Store the characteristics of the current mode into the buffer. 780 // 781 782 ModeInformation->Length = sizeof(VIDEO_MODE_INFORMATION); 783 ModeInformation->ModeIndex = HwDeviceExtension->ModeIndex; 784 ModeInformation->VisScreenWidth = HwDeviceExtension->CurrentMode->hres; 785 ModeInformation->ScreenStride = HwDeviceExtension->CurrentMode->wbytes; 786 ModeInformation->VisScreenHeight = HwDeviceExtension->CurrentMode->vres; 787 ModeInformation->NumberOfPlanes = HwDeviceExtension->CurrentMode->numPlanes; 788 ModeInformation->BitsPerPlane = HwDeviceExtension->CurrentMode->bitsPerPlane; 789 ModeInformation->Frequency = HwDeviceExtension->CurrentMode->Frequency; 790 ModeInformation->XMillimeter = 320; // temporary hardcoded constant 791 ModeInformation->YMillimeter = 240; // temporary hardcoded constant 792 793 ModeInformation->AttributeFlags = HwDeviceExtension->CurrentMode->fbType; 794 795 if ((ModeInformation->BitsPerPlane == 32) || 796 (ModeInformation->BitsPerPlane == 24)) 797 { 798 799 ModeInformation->NumberRedBits = 8; 800 ModeInformation->NumberGreenBits = 8; 801 ModeInformation->NumberBlueBits = 8; 802 ModeInformation->RedMask = 0xff0000; 803 ModeInformation->GreenMask = 0x00ff00; 804 ModeInformation->BlueMask = 0x0000ff; 805 806 } 807 else if (ModeInformation->BitsPerPlane == 16) 808 { 809 810 ModeInformation->NumberRedBits = 6; 811 ModeInformation->NumberGreenBits = 6; 812 ModeInformation->NumberBlueBits = 6; 813 ModeInformation->RedMask = 0x1F << 11; 814 ModeInformation->GreenMask = 0x3F << 5; 815 ModeInformation->BlueMask = 0x1F; 816 817 } 818 // eVb: 2.12 [VGA] - Add support for 15bpp modes, which Cirrus doesn't support 819 else if (ModeInformation->BitsPerPlane == 15) 820 { 821 822 ModeInformation->NumberRedBits = 6; 823 ModeInformation->NumberGreenBits = 6; 824 ModeInformation->NumberBlueBits = 6; 825 ModeInformation->RedMask = 0x3E << 9; 826 ModeInformation->GreenMask = 0x1F << 5; 827 ModeInformation->BlueMask = 0x1F; 828 } 829 // eVb: 2.12 [END] 830 else 831 { 832 833 ModeInformation->NumberRedBits = 6; 834 ModeInformation->NumberGreenBits = 6; 835 ModeInformation->NumberBlueBits = 6; 836 ModeInformation->RedMask = 0; 837 ModeInformation->GreenMask = 0; 838 ModeInformation->BlueMask = 0; 839 } 840 841 // eVb: 2.13 [VGA] - All modes are palette managed/driven, unlike Cirrus 842 ModeInformation->AttributeFlags |= VIDEO_MODE_PALETTE_DRIVEN | 843 VIDEO_MODE_MANAGED_PALETTE; 844 // eVb: 2.13 [END] 845 846 return NO_ERROR; 847 848 } // end VgaQueryCurrentMode() 849 850 VOID 851 NTAPI 852 VgaZeroVideoMemory( 853 PHW_DEVICE_EXTENSION HwDeviceExtension 854 ) 855 856 /*++ 857 858 Routine Description: 859 860 This routine zeros the first 256K on the VGA. 861 862 Arguments: 863 864 HwDeviceExtension - Pointer to the miniport driver's device extension. 865 866 867 Return Value: 868 869 None. 870 871 --*/ 872 { 873 UCHAR temp; 874 875 // 876 // Map font buffer at A0000 877 // 878 879 VgaInterpretCmdStream(HwDeviceExtension, EnableA000Data); 880 881 // 882 // Enable all planes. 883 // 884 885 VideoPortWritePortUchar(HwDeviceExtension->IOAddress + SEQ_ADDRESS_PORT, 886 IND_MAP_MASK); 887 888 temp = VideoPortReadPortUchar(HwDeviceExtension->IOAddress + 889 SEQ_DATA_PORT) | (UCHAR)0x0F; 890 891 VideoPortWritePortUchar(HwDeviceExtension->IOAddress + SEQ_DATA_PORT, 892 temp); 893 894 VideoPortZeroDeviceMemory(HwDeviceExtension->VideoMemoryAddress, 0xFFFF); 895 896 VgaInterpretCmdStream(HwDeviceExtension, DisableA000Color); 897 898 } 899