|
|
1.1 root 1: /*++
2:
3: Copyright (c) 1990-1992 Microsoft Corporation
4:
5: Module Name:
6:
7: xga.c
8:
9: Abstract:
10:
11: This module contains the code that implements the XGA miniport driver.
12:
13: Environment:
14:
15: Kernel mode
16:
17: Revision History:
18:
19: --*/
20:
21: #include "dderror.h"
22: #include "devioctl.h"
23: #include "miniport.h"
24:
25: #include "ntddvdeo.h"
26: #include "video.h"
27: #include "xga.h"
28: #include "xgaioctl.h"
29:
30: #include "xgaloger.h"
31:
32:
33: //
34: // Function Prototypes
35: //
36: // Functions that start with 'Xga' are entry points for the OS port driver.
37: //
38:
39: VP_STATUS
40: XgaFindAdapter(
41: PVOID HwDeviceExtension,
42: PVOID HwContext,
43: PWSTR ArgumentString,
44: PVIDEO_PORT_CONFIG_INFO ConfigInfo,
45: PUCHAR Again
46: );
47:
48: BOOLEAN
49: XgaInitialize(
50: PVOID HwDeviceExtension
51: );
52:
53: BOOLEAN
54: XgaStartIO(
55: PVOID HwDeviceExtension,
56: PVIDEO_REQUEST_PACKET RequestPacket
57: );
58:
59: //
60: // Define device driver procedure prototypes.
61: //
62:
63: VP_STATUS
64: XgaGetPosData(
65: PVOID HwDeviceExtension,
66: PVOID Context,
67: VIDEO_DEVICE_DATA_TYPE DeviceDataType,
68: PVOID Identifier,
69: ULONG IdentifierLength,
70: PVOID ConfigurationData,
71: ULONG ConfigurationDataLength,
72: PVOID ComponentInformation,
73: ULONG ComponentInformationLength
74: );
75:
76: ULONG
77: XgaFindXga(
78: PHW_DEVICE_EXTENSION HwDeviceExtension,
79: PCM_MCA_POS_DATA PosData
80: );
81:
82: VP_STATUS
83: XgaSetMode(
84: PHW_DEVICE_EXTENSION HwDeviceExtension,
85: ULONG ModeNum
86: );
87:
88: VP_STATUS
89: XgaGetRegistryParamaterCallback(
90: PVOID HwDeviceExtension,
91: PVOID Context,
92: PWSTR ValueName,
93: PVOID ValueData,
94: ULONG ValueLength
95: );
96:
97: //
98: // Last slot at which an adapter was found.
99: //
100:
101: ULONG XgaSlot;
102: LONG BusNumber = -1;
103:
104:
105: ULONG
106: DriverEntry (
107: PVOID Context1,
108: PVOID Context2
109: )
110:
111: /*++
112:
113: Routine Description:
114:
115: Installable driver initialization entry point.
116: This entry point is called directly by the I/O system.
117:
118: Arguments:
119:
120: Context1 - First context value passed by the operating system. This is
121: the value with which the miniport driver calls VideoPortInitialize().
122:
123: Context2 - Second context value passed by the operating system. This is
124: the value with which the miniport driver calls VideoPortInitialize().
125:
126: Return Value:
127:
128: Status from VideoPortInitialize()
129:
130: --*/
131:
132: {
133:
134: VIDEO_HW_INITIALIZATION_DATA hwInitData;
135:
136: //
137: // Zero out structure.
138: //
139:
140: VideoPortZeroMemory(&hwInitData, sizeof(VIDEO_HW_INITIALIZATION_DATA)) ;
141:
142: //
143: // Specify sizes of structure and extension.
144: //
145:
146: hwInitData.HwInitDataSize = sizeof(VIDEO_HW_INITIALIZATION_DATA);
147:
148: //
149: // Set entry points.
150: //
151:
152: hwInitData.HwFindAdapter = XgaFindAdapter;
153: hwInitData.HwInitialize = XgaInitialize;
154: hwInitData.HwInterrupt = NULL;
155: hwInitData.HwStartIO = XgaStartIO;
156:
157: //
158: // Determine the size we require for the device extension.
159: //
160:
161: hwInitData.HwDeviceExtensionSize = sizeof(HW_DEVICE_EXTENSION);
162:
163: //
164: // Always start with parameters for device0 in this case.
165: //
166:
167: // hwInitData.StartingDeviceNumber = 0;
168:
169: //
170: // This device only supports the internal bus type. So return the status
171: // value directly to the operating system.
172: //
173:
174: hwInitData.AdapterInterfaceType = MicroChannel;
175:
176: return VideoPortInitialize(Context1,
177: Context2,
178: &hwInitData,
179: NULL);
180:
181: } // end DriverEntry()
182:
183: VP_STATUS
184: XgaFindAdapter(
185: PVOID HwDeviceExtension,
186: PVOID HwContext,
187: PWSTR ArgumentString,
188: PVIDEO_PORT_CONFIG_INFO ConfigInfo,
189: PUCHAR Again
190: )
191:
192: /*++
193:
194: Routine Description:
195:
196: This routine is called to determine if the adapter for this driver
197: is present in the system.
198: If it is present, the function fills out some information describing
199: the adapter.
200:
201: Arguments:
202:
203: HwDeviceExtension - Supplies the miniport driver's adapter storage. This
204: storage is initialized to zero before this call.
205:
206: HwContext - Supplies the context value which was passed to
207: VideoPortInitialize().
208:
209: ArgumentString - Suuplies a NULL terminated ASCII string. This string
210: originates from the user.
211:
212: ConfigInfo - Returns the configuration information structure which is
213: filled by the miniport driver. This structure is initialized with
214: any knwon configuration information (such as SystemIoBusNumber) by
215: the port driver. Where possible, drivers should have one set of
216: defaults which do not require any supplied configuration information.
217:
218: Again - Indicates if the miniport driver wants the port driver to call
219: its VIDEO_HW_FIND_ADAPTER function again with a new device extension
220: and the same config info. This is used by the miniport drivers which
221: can search for several adapters on a bus.
222:
223: Return Value:
224:
225: This routine must return:
226:
227: NO_ERROR - Indicates a host adapter was found and the
228: configuration information was successfully determined.
229:
230: ERROR_INVALID_PARAMETER - Indicates an adapter was found but there was an
231: error obtaining the configuration information. If possible an error
232: should be logged.
233:
234: ERROR_DEV_NOT_EXIST - Indicates no host adapter was found for the
235: supplied configuration information.
236:
237: --*/
238:
239: {
240:
241: //
242: // Number of entries in the access range structure passed to the port driver.
243: //
244:
245: #define NUM_XGA_ACCESS_RANGES 6
246:
247: PHW_DEVICE_EXTENSION hwDeviceExtension = HwDeviceExtension;
248: CM_MCA_POS_DATA posData;
249: ULONG ioAddress;
250: VP_STATUS status;
251: VIDEO_ACCESS_RANGE accessRange[NUM_XGA_ACCESS_RANGES];
252: PHYSICAL_ADDRESS A0000PhysicalAddress;
253: PHYSICAL_ADDRESS passThroughPort;
254:
255: A0000PhysicalAddress.LowPart = 0x000A0000;
256: A0000PhysicalAddress.HighPart = 0x00000000;
257:
258: passThroughPort.LowPart = 0x000003C3;
259: passThroughPort.HighPart = 0x00000000;
260:
261: //
262: // Indicate we do not wish to be called over
263: //
264:
265: *Again = 0;
266:
267: //
268: // Make sure the size of the structure is at least as large as what we
269: // are expecting (check version of the config info structure).
270: //
271:
272: if (ConfigInfo->Length < sizeof(VIDEO_PORT_CONFIG_INFO)) {
273:
274: return ERROR_INVALID_PARAMETER;
275:
276: }
277:
278: //
279: // Reset the Slot number being examined to zero if we are processing
280: // a new bus number.
281: //
282:
283: if (BusNumber != (LONG)ConfigInfo->SystemIoBusNumber) {
284:
285: BusNumber = ConfigInfo->SystemIoBusNumber;
286: XgaSlot = 0;
287:
288: }
289:
290: //
291: // This picks up the POS registers.
292: //
293:
294: if (NO_ERROR != VideoPortGetDeviceData(hwDeviceExtension,
295: VpBusData,
296: XgaGetPosData,
297: &posData)) {
298:
299: VideoDebugPrint((2, "Xga: GetDeviceData returned error - probably no XGAs\n"));
300:
301: return ERROR_DEV_NOT_EXIST;
302: }
303:
304: //
305: // Since we got the data properly, make sure we get called again to find
306: // the next XGA adapter.
307: //
308:
309: *Again = 1;
310:
311: //
312: // Determine the XGA registers by munging the POS register data.
313: //
314:
315: ioAddress = (posData.PosData1 &0x0E) >> 1;
316:
317: hwDeviceExtension->PhysicalRomBaseAddress.LowPart =
318: (((posData.PosData1 & 0xF0) >> 4) * 0x2000) + 0xC0000 ;
319: hwDeviceExtension->PhysicalRomBaseAddress.HighPart = 0x00000000 ;
320:
321: hwDeviceExtension->PhysicalIoRegBaseAddress.LowPart = 0x2100 +
322: (ioAddress << 4) ;
323: hwDeviceExtension->PhysicalIoRegBaseAddress.HighPart = 0x00000000;
324:
325: //
326: // Choose a size of 1 MEG for video memory as a default
327: //
328:
329: hwDeviceExtension->PhysicalVideoMemoryLength = 0x00100000;
330:
331: //
332: // Find the virtual address of the frame buffer. Get the 4Meg aperture
333: // if it is available, otherwise take the 1MEG.
334: //
335:
336: if (posData.PosData3 & 0x01) {
337:
338: VideoDebugPrint((1, "Xga: using the 4 MEG Aperture\n"));
339:
340: hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart =
341: ((posData.PosData3 &0xFE) << 24) | (ioAddress << 22) ;
342: hwDeviceExtension->PhysicalVideoMemoryAddress.HighPart =
343: 0x00000000 ;
344:
345: } else {
346:
347: VideoDebugPrint((1, "Xga: trying the 1 MEG aperture\n"));
348:
349: hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart =
350: (posData.PosData4 &0x0F) << 20 ;
351: hwDeviceExtension->PhysicalVideoMemoryAddress.HighPart = 0x00000000 ;
352:
353: }
354:
355: //
356: // If none of these apertures are open, (64K aperture) then fail.
357: // 1 MEG aperture is disabled if the base is 0
358: //
359:
360: if (!hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart) {
361:
362: VideoDebugPrint((1, "Xga: 64K aperture\n"));
363:
364: VideoPortLogError(hwDeviceExtension,
365: NULL,
366: XGA_WRONG_APERTURE,
367: __LINE__);
368:
369: return ERROR_INVALID_PARAMETER;
370:
371: }
372:
373: //
374: // Get the address of the Co processor registers.
375: //
376:
377: hwDeviceExtension->PhysicalCoProcessorAddress.LowPart = 0x80 * ioAddress
378: + 0x1C00 + hwDeviceExtension->PhysicalRomBaseAddress.LowPart;
379: hwDeviceExtension->PhysicalCoProcessorAddress.HighPart = 0x00000000 ;
380:
381: //
382: // Save the data for access ranges
383: //
384:
385: //
386: // Io Ports
387: //
388:
389: accessRange[0].RangeStart = hwDeviceExtension->PhysicalIoRegBaseAddress;
390: accessRange[0].RangeLength = XGA_IO_REGS_SIZE;
391: accessRange[0].RangeInIoSpace = TRUE;
392: accessRange[0].RangeVisible = TRUE;
393: accessRange[0].RangeShareable = FALSE;
394:
395: //
396: // Video Memory
397: //
398:
399: accessRange[1].RangeStart = hwDeviceExtension->PhysicalVideoMemoryAddress;
400: accessRange[1].RangeLength = hwDeviceExtension->PhysicalVideoMemoryLength;
401: accessRange[1].RangeInIoSpace = FALSE;
402: accessRange[1].RangeVisible = TRUE;
403: accessRange[1].RangeShareable = FALSE;
404:
405: //
406: // ROM Location
407: //
408:
409: accessRange[2].RangeStart = hwDeviceExtension->PhysicalRomBaseAddress;
410: accessRange[2].RangeLength = XGA_ROM_SIZE;
411: accessRange[2].RangeInIoSpace = FALSE;
412: accessRange[2].RangeVisible = TRUE;
413: accessRange[2].RangeShareable = FALSE;
414:
415: //
416: // Co-Processor Location
417: //
418:
419: accessRange[3].RangeStart = hwDeviceExtension->PhysicalCoProcessorAddress;
420: accessRange[3].RangeLength = XGA_CO_PROCESSOR_REGS_SIZE;
421: accessRange[3].RangeInIoSpace = FALSE;
422: accessRange[3].RangeVisible = TRUE;
423: accessRange[3].RangeShareable = FALSE;
424:
425: //
426: // Resources shared with the VGA
427: //
428:
429: //
430: // Io Ports
431: //
432:
433: accessRange[4].RangeStart = passThroughPort;
434: accessRange[4].RangeLength = 0x00000001;
435: accessRange[4].RangeInIoSpace = TRUE;
436: accessRange[4].RangeVisible = FALSE;
437: accessRange[4].RangeShareable = TRUE;
438:
439: //
440: // Video Memory
441: //
442:
443: accessRange[5].RangeStart = A0000PhysicalAddress;
444: accessRange[5].RangeLength = 0x00010000;
445: accessRange[5].RangeInIoSpace = FALSE;
446: accessRange[5].RangeVisible = FALSE;
447: accessRange[5].RangeShareable = TRUE;
448:
449: //
450: // Check to see if there is a hardware resource conflict.
451: //
452:
453: status = VideoPortVerifyAccessRanges(HwDeviceExtension,
454: NUM_XGA_ACCESS_RANGES,
455: accessRange);
456:
457: if (status != NO_ERROR) {
458:
459: return status;
460:
461: }
462:
463: //
464: // Clear out the Emulator entries and the state size since this driver
465: // does not support them.
466: //
467:
468: ConfigInfo->NumEmulatorAccessEntries = 0;
469: ConfigInfo->EmulatorAccessEntries = NULL;
470: ConfigInfo->EmulatorAccessEntriesContext = 0;
471:
472: ConfigInfo->VdmPhysicalVideoMemoryAddress.LowPart = 0x00000000;
473: ConfigInfo->VdmPhysicalVideoMemoryAddress.HighPart = 0x00000000;
474: ConfigInfo->VdmPhysicalVideoMemoryLength = 0x00000000;
475:
476: ConfigInfo->HardwareStateSize = 0;
477:
478: //
479: // Map the video memory into the system virtual address space so we can
480: // clear it out.
481: //
482:
483: if ( (hwDeviceExtension->FrameAddress =
484: VideoPortGetDeviceBase(hwDeviceExtension,
485: hwDeviceExtension->PhysicalVideoMemoryAddress,
486: hwDeviceExtension->PhysicalVideoMemoryLength,
487: FALSE)) == NULL) {
488:
489: return ERROR_INVALID_PARAMETER;
490:
491: }
492:
493: //
494: // Map in the memory at A0000 so we can test the card for the amount of
495: // memory afterwards.
496: //
497:
498: if ( ( hwDeviceExtension->A0000MemoryAddress =
499: VideoPortGetDeviceBase(hwDeviceExtension,
500: A0000PhysicalAddress,
501: 0x00010000,
502: FALSE)) == NULL) {
503:
504: VideoDebugPrint((2, "XgaFindAdapter - Fail to get A0000 aperture address\n"));
505:
506: return ERROR_INVALID_PARAMETER;
507:
508: }
509:
510: //
511: // Map in the IO registers so we can access them.
512: //
513:
514: if ( ( hwDeviceExtension->IoRegBaseAddress = (ULONG)
515: VideoPortGetDeviceBase(hwDeviceExtension,
516: hwDeviceExtension->PhysicalIoRegBaseAddress,
517: XGA_IO_REGS_SIZE,
518: TRUE)) == 0) {
519:
520: VideoDebugPrint((2, "XgaFindAdapter - Fail to get io register addresses\n"));
521:
522: return ERROR_INVALID_PARAMETER;
523:
524: }
525:
526: //
527: // Map in the pass-throught port.
528: //
529:
530: if ( ( hwDeviceExtension->PassThroughPort =
531: VideoPortGetDeviceBase(hwDeviceExtension,
532: passThroughPort,
533: 1,
534: TRUE)) == 0) {
535:
536: VideoDebugPrint((2, "XgaFindAdapter - Fail to get io register addresses\n"));
537:
538: return ERROR_INVALID_PARAMETER;
539:
540: }
541:
542: //
543: // Indicate a successful completion status.
544: //
545:
546: return NO_ERROR;
547:
548: } // end XgaFindAdapter()
549:
550:
551: VP_STATUS
552: XgaGetPosData(
553: PVOID HwDeviceExtension,
554: PVOID Context,
555: VIDEO_DEVICE_DATA_TYPE DeviceDataType,
556: PVOID Identifier,
557: ULONG IdentifierLength,
558: PVOID ConfigurationData,
559: ULONG ConfigurationDataLength,
560: PVOID ComponentInformation,
561: ULONG ComponentInformationLength
562: )
563:
564: /*++
565:
566: Routine Description:
567:
568: Callback for the GetDeviceData function.
569: This routine will scan for an XGA adapter, and if it finds one, will
570: save the POS information in the device extension so it can be further
571: processed in the FindAdapter() routine.
572:
573: Arguments:
574:
575: HwDeviceExtension - Pointer to the miniport drivers device extension.
576:
577: Context - Context value passed to the VideoPortGetDeviceData function.
578:
579: DeviceDataType - The type of data that was requested in
580: VideoPortGetDeviceData.
581:
582: Identifier - Pointer to a string that contains the name of the device,
583: as setup by the ROM or ntdetect.
584:
585: IdentifierLength - Length of the Identifier string.
586:
587: ConfigurationData - Pointer to the configuration data for the device or
588: BUS.
589:
590: ConfigurationDataLength - Length of the data in the configurationData
591: field.
592:
593: ComponentInformation - Undefined.
594:
595: ComponentInformationLength - Undefined.
596:
597: Return Value:
598:
599: Returns NO_ERROR if the function completed properly.
600: Returns ERROR_DEV_NOT_EXIST if we did not find the device.
601: Returns ERROR_INVALID_PARAMETER otherwise.
602:
603: --*/
604:
605: {
606: PHW_DEVICE_EXTENSION hwDeviceExtension = HwDeviceExtension;
607: USHORT adapterId;
608: BOOLEAN found = FALSE;
609: PCM_MCA_POS_DATA posData = Context;
610:
611: //
612: // Find the XGA.
613: // Loop through all the POS data in the PosData array
614: //
615:
616: while ((XgaSlot + 1) * sizeof(CM_MCA_POS_DATA) <= ConfigurationDataLength) {
617:
618: adapterId = *((PUSHORT)((PCM_MCA_POS_DATA)ConfigurationData + XgaSlot));
619:
620: VideoDebugPrint((3, "PosAdapterId for slot %d is %x \n", XgaSlot,
621: adapterId));
622:
623: switch ( adapterId ) {
624:
625: case 0x8FDB:
626:
627: hwDeviceExtension->BoardType = XGA_TYPE_1;
628:
629: found = TRUE;
630: break;
631:
632: case 0x8FDA:
633:
634: hwDeviceExtension->BoardType = XGA_TYPE_2;
635:
636: found = TRUE;
637: break;
638:
639: default:
640: break;
641:
642: }
643:
644: //
645: // Go to the next slot.
646: //
647:
648: XgaSlot++;
649:
650: //
651: // We have found an XGA adapter. Save the data in the device extension
652: // so we can process it further.
653: //
654:
655: if (found) {
656:
657: *posData = *((PCM_MCA_POS_DATA)ConfigurationData + XgaSlot - 1);
658:
659: return NO_ERROR;
660: }
661: }
662:
663: return ERROR_DEV_NOT_EXIST;
664:
665: }
666:
667: BOOLEAN
668: XgaInitialize(
669: PVOID HwDeviceExtension
670: )
671:
672: /*++
673:
674: Routine Description:
675:
676: This routine does one time initialization of the device.
677:
678: Arguments:
679:
680: HwDeviceExtension - Supplies a pointer to the miniport's device extension.
681:
682: Return Value:
683:
684:
685: Always returns TRUE since this routine can never fail.
686:
687: --*/
688:
689: {
690: PHW_DEVICE_EXTENSION hwDeviceExtension = HwDeviceExtension;
691: volatile PUCHAR videoMemory;
692: UCHAR testValue = 0xA5;
693: ULONG i;
694: ULONG color;
695:
696: videoMemory = hwDeviceExtension->A0000MemoryAddress;
697:
698: //
699: // Disable interrupts on the card since they will not be used
700: //
701:
702: VideoPortWritePortUchar(
703: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | INT_ENABLE_REG), 0x00);
704:
705: //
706: // Blank the palette so we get a black screen.
707: //
708:
709: VideoPortWritePortUchar(
710: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | INDEX_REG), 0x64);
711:
712: VideoPortWritePortUchar(
713: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | DATA_IN_REG), 0x00);
714:
715: //
716: // Put the adapter in a temporary Extended Graphics Mode, set up video
717: // memory at A0000, put the aperture at 768 K higher and try to access
718: // it to determine how much memory is present.
719: //
720:
721: VideoPortWritePortUchar(
722: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | OP_MODE_REG), 0x04);
723:
724: VideoPortWritePortUchar(
725: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | APP_CTL_REG), 0x01);
726:
727: VideoPortWritePortUchar(
728: (PUCHAR) (hwDeviceExtension->IoRegBaseAddress | APP_INDEX_REG), 0x0C);
729:
730: //
731: // To test if memory is present, use a test value (make sure the same
732: // value is not currently stored in video memory, otherwise change it),
733: // store it in video memory, and read it back. If the value is identical
734: // to the value we stored then there must be memory present at that
735: // location (which, in this case, means we have 1 MEG of Video RAM).
736: //
737:
738: if (*videoMemory == testValue) {
739:
740: testValue >>= 1;
741:
742: }
743:
744: *videoMemory = testValue;
745:
746: if (*videoMemory == testValue) {
747:
748: hwDeviceExtension->PhysicalVideoMemoryLength = 0x00100000;
749:
750: } else {
751:
752: hwDeviceExtension->PhysicalVideoMemoryLength = 0x00080000;
753:
754: }
755:
756: VideoDebugPrint((2, "XgaInitialize\n The amount of memory on the card is %d K\n",
757: hwDeviceExtension->PhysicalVideoMemoryLength >> 10));
758:
759: //
760: // For now, we only support color devices
761: //
762:
763: hwDeviceExtension->Color = TRUE;
764:
765: //
766: // Now compute the number of available modes based on the infromation
767: // we found out.
768: //
769:
770: hwDeviceExtension->NumAvailableModes = 0;
771:
772: for (i = 0; i < XGA_NUM_MODES; i++) {
773:
774: //
775: // If the right amount of memory and the right board type is present ...
776: //
777:
778: if (XgaModes[i].minimumRequiredMemory <=
779: hwDeviceExtension->PhysicalVideoMemoryLength) {
780:
781: //
782: // Check we have the right type of board.
783: //
784:
785: if ( (XgaModes[i].Xga1Mode &&
786: (hwDeviceExtension->BoardType & XGA_TYPE_1)) ||
787: (XgaModes[i].Xga2Mode &&
788: (hwDeviceExtension->BoardType & XGA_TYPE_2)) ) {
789:
790: color = XgaModes[i].modeInformation.AttributeFlags &
791: VIDEO_MODE_COLOR;
792:
793: //
794: // check that both the mode and what we support is the same
795: // in terms of color.
796: //
797:
798: if ( (color && (ULONG)hwDeviceExtension->Color) || // color
799: (color == (ULONG)hwDeviceExtension->Color) ) { // monochrome
800:
801: hwDeviceExtension->Valid[i] = TRUE;
802: hwDeviceExtension->NumAvailableModes++;
803:
804: }
805: }
806: }
807: }
808:
809: VideoPortGetRegistryParameters(hwDeviceExtension,
810: L"Monitor",
811: TRUE,
812: XgaGetRegistryParamaterCallback,
813: NULL);
814:
815: return TRUE;
816:
817: } // end XgaInitialize()
818:
819:
820: VP_STATUS
821: XgaGetRegistryParamaterCallback(
822: PVOID HwDeviceExtension,
823: PVOID Context,
824: PWSTR ValueName,
825: PVOID ValueData,
826: ULONG ValueLength
827: )
828:
829: /*++
830:
831: Routine Description:
832:
833: Callback routine to process the information coming back from the registry.
834:
835: Arguments:
836:
837: HwDeviceExtension - Pointer to the miniport driver's device extension.
838:
839: Context - Context parameter passed to the callback routine.
840:
841: ValueName - Pointer to the name of the requested data field.
842:
843: ValueData - Pointer to a buffer containing the information.
844:
845: ValueLength - Size of the data.
846:
847: Return Value:
848:
849:
850: Environment:
851:
852: Can only be called During initialization.
853:
854: --*/
855:
856: {
857:
858: VideoDebugPrint((3, "In the GetRegistryParameters callback routine\n"));
859:
860: return NO_ERROR;
861:
862: }
863:
864:
865: BOOLEAN
866: XgaStartIO(
867: PVOID HwDeviceExtension,
868: PVIDEO_REQUEST_PACKET RequestPacket
869: )
870:
871: /*++
872:
873: Routine Description:
874:
875: This routine is the main execution routine for the miniport driver. It
876: acceptss a Video Request Packet, performs the request, and then returns
877: with the appropriate status.
878:
879: Arguments:
880:
881: HwDeviceExtension - Supplies a pointer to the miniport's device extension.
882:
883: RequestPacket - Pointer to the video request packet. This structure
884: contains all the parameters passed to the VideoIoControl function.
885:
886: Return Value:
887:
888:
889: --*/
890:
891: {
892: VP_STATUS status;
893: PHW_DEVICE_EXTENSION hwDeviceExtension = HwDeviceExtension;
894:
895: PVIDEO_MEMORY_INFORMATION memoryInformation;
896: PVIDEO_MODE_INFORMATION modeInformation;
897: ULONG inIoSpace;
898:
899: PVIDEO_CLUT clutBuffer;
900: PVIDEO_CLUTDATA pClutData;
901:
902: USHORT i;
903: ULONG length;
904: PHYSICAL_ADDRESS physicalAddress;
905: ULONG offset;
906:
907:
908: //
909: // Switch on the IoContolCode in the RequestPacket. It indicates which
910: // function must be performed by the driver.
911: //
912:
913: switch (RequestPacket->IoControlCode) {
914:
915:
916: case IOCTL_VIDEO_MAP_VIDEO_MEMORY:
917:
918: VideoDebugPrint((2, "XgaStartIO - MapVideoMemory\n"));
919:
920: if ( (RequestPacket->OutputBufferLength <
921: (RequestPacket->StatusBlock->Information =
922: sizeof(VIDEO_MEMORY_INFORMATION))) ||
923: (RequestPacket->InputBufferLength < sizeof(VIDEO_MEMORY)) ) {
924:
925: status = ERROR_INSUFFICIENT_BUFFER;
926: }
927:
928: memoryInformation = RequestPacket->OutputBuffer;
929:
930: memoryInformation->VideoRamBase = ((PVIDEO_MEMORY)
931: (RequestPacket->InputBuffer))->RequestedVirtualAddress;
932:
933: memoryInformation->VideoRamLength =
934: hwDeviceExtension->PhysicalVideoMemoryLength;
935:
936: inIoSpace = 0;
937:
938: status = VideoPortMapMemory(hwDeviceExtension,
939: hwDeviceExtension->PhysicalVideoMemoryAddress,
940: &(memoryInformation->VideoRamLength),
941: &inIoSpace,
942: &(memoryInformation->VideoRamBase));
943:
944: //
945: // The frame buffer and virtual memory and equivalent in this
946: // case.
947: //
948:
949: memoryInformation->FrameBufferBase =
950: memoryInformation->VideoRamBase;
951:
952: memoryInformation->FrameBufferLength =
953: XgaModes[hwDeviceExtension->CurrentMode].modeInformation.VisScreenHeight *
954: XgaModes[hwDeviceExtension->CurrentMode].modeInformation.ScreenStride;
955:
956: VideoDebugPrint((3, "Xga IOCLT_MAP_MEMORY\n physical = %x\n \
957: virtual = %x\n length = %x\n framebase = %x\n frameLength = %x\n",
958: hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart,
959: memoryInformation->VideoRamBase,
960: memoryInformation->VideoRamLength,
961: memoryInformation->FrameBufferBase,
962: memoryInformation->FrameBufferLength));
963:
964: break;
965:
966:
967: case IOCTL_VIDEO_UNMAP_VIDEO_MEMORY:
968:
969: VideoDebugPrint((2, "XgaStartIO - UnMapVideoMemory\n"));
970:
971: if (RequestPacket->InputBufferLength < sizeof(VIDEO_MEMORY)) {
972:
973: status = ERROR_INSUFFICIENT_BUFFER;
974: }
975:
976: status = VideoPortUnmapMemory(hwDeviceExtension,
977: ((PVIDEO_MEMORY)
978: (RequestPacket->InputBuffer))->
979: RequestedVirtualAddress,
980: 0);
981: break;
982:
983:
984: case IOCTL_VIDEO_QUERY_NUM_AVAIL_MODES:
985:
986: VideoDebugPrint((2, "XgaStartIO - QueryNumberAvaialbleModes\n"));
987:
988: if (RequestPacket->OutputBufferLength <
989: (RequestPacket->StatusBlock->Information =
990: sizeof(VIDEO_NUM_MODES)) ) {
991:
992: status = ERROR_INSUFFICIENT_BUFFER;
993:
994: } else {
995:
996: ((PVIDEO_NUM_MODES)RequestPacket->OutputBuffer)->NumModes =
997: hwDeviceExtension->NumAvailableModes;
998: ((PVIDEO_NUM_MODES)RequestPacket->OutputBuffer)->ModeInformationLength =
999: sizeof(VIDEO_MODE_INFORMATION);
1000:
1001: status = NO_ERROR;
1002: }
1003:
1004: break;
1005:
1006:
1007: case IOCTL_VIDEO_QUERY_AVAIL_MODES:
1008:
1009: VideoDebugPrint((2, "XgaStartIO - QueryAvailableModes\n"));
1010:
1011: if (RequestPacket->OutputBufferLength <
1012: (RequestPacket->StatusBlock->Information =
1013: hwDeviceExtension->NumAvailableModes *
1014: sizeof(VIDEO_MODE_INFORMATION)) ) {
1015:
1016: status = ERROR_INSUFFICIENT_BUFFER;
1017:
1018: } else {
1019:
1020: modeInformation = RequestPacket->OutputBuffer;
1021:
1022: for (i = 0; i < XGA_NUM_MODES; i++) {
1023:
1024: if (hwDeviceExtension->Valid[i]) {
1025:
1026: *modeInformation = XgaModes[i].modeInformation;
1027: modeInformation++;
1028:
1029: }
1030: }
1031:
1032: status = NO_ERROR;
1033: }
1034:
1035: break;
1036:
1037:
1038: case IOCTL_VIDEO_QUERY_CURRENT_MODE:
1039:
1040: VideoDebugPrint((2, "XgaStartIO - QueryCurrentMode\n"));
1041:
1042: if (RequestPacket->OutputBufferLength <
1043: (RequestPacket->StatusBlock->Information =
1044: sizeof(VIDEO_MODE_INFORMATION)) ) {
1045:
1046: status = ERROR_INSUFFICIENT_BUFFER;
1047:
1048: } else {
1049:
1050: *((PVIDEO_MODE_INFORMATION)RequestPacket->OutputBuffer) =
1051: XgaModes[hwDeviceExtension->CurrentMode].modeInformation;
1052:
1053: status = NO_ERROR;
1054:
1055: }
1056:
1057: break;
1058:
1059:
1060:
1061:
1062:
1063:
1064: case IOCTL_VIDEO_SET_CURRENT_MODE:
1065:
1066: VideoDebugPrint((2, "XgaStartIO - SetCurrentMode\n"));
1067:
1068: if (RequestPacket->InputBufferLength < sizeof(VIDEO_MODE)) {
1069:
1070: status = ERROR_INSUFFICIENT_BUFFER;
1071:
1072: } else {
1073:
1074: status = XgaSetMode(hwDeviceExtension,
1075: ((PVIDEO_MODE)RequestPacket->InputBuffer)->
1076: RequestedMode);
1077:
1078: }
1079:
1080: break;
1081:
1082:
1083: case IOCTL_VIDEO_SET_COLOR_REGISTERS:
1084:
1085: VideoDebugPrint((2, "XgaStartIO - SetColorRegs\n"));
1086:
1087: clutBuffer = RequestPacket->InputBuffer;
1088:
1089: /* Load simple 16 entry palette */
1090:
1091: XGAIDXOUT(INDEX_REG, 0x66, 0x0) ;
1092:
1093: /* Start at beginning of palette */
1094:
1095: XGAIDXOUT(INDEX_REG, 0x60, clutBuffer->FirstEntry) ;
1096: XGAIDXOUT(INDEX_REG, 0x61, 0x0) ;
1097:
1098:
1099: for ( i = 0 ; i < clutBuffer->NumEntries; i++ ) {
1100:
1101: pClutData = &clutBuffer->LookupTable[i].RgbArray ;
1102:
1103: XGAOUT(INDEX_REG, 0x65) ;
1104: XGAOUT(0x0B, pClutData->Red) ;
1105:
1106: XGAOUT(INDEX_REG, 0x65) ;
1107: XGAOUT(0x0B, pClutData->Green) ;
1108:
1109: XGAOUT(INDEX_REG, 0x65) ;
1110: XGAOUT(0x0B, pClutData->Blue) ;
1111: }
1112:
1113: status = NO_ERROR;
1114:
1115: break;
1116:
1117: case IOCTL_VIDEO_XGA_MAP_COPROCESSOR:
1118:
1119: if (RequestPacket->OutputBufferLength <
1120: (RequestPacket->StatusBlock->Information =
1121: sizeof(VIDEO_XGA_COPROCESSOR_INFORMATION)) ) {
1122:
1123: status = ERROR_INSUFFICIENT_BUFFER;
1124: break;
1125:
1126: }
1127:
1128: length = XGA_CO_PROCESSOR_REGS_SIZE;
1129:
1130: // Map in at the page ganularity, then add in the page offset
1131: // to the linear address.
1132:
1133: offset = hwDeviceExtension->PhysicalCoProcessorAddress.LowPart & 0x00000FFF ;
1134:
1135: physicalAddress.LowPart =
1136: hwDeviceExtension->PhysicalCoProcessorAddress.LowPart & 0xFFFFF000 ;
1137:
1138: physicalAddress.HighPart = 0x00000000;
1139:
1140: ((PVIDEO_XGA_COPROCESSOR_INFORMATION)RequestPacket->OutputBuffer)->
1141: CoProcessorVirtualAddress = 0;
1142:
1143: inIoSpace = 0;
1144:
1145: status = VideoPortMapMemory(hwDeviceExtension,
1146: physicalAddress,
1147: &length,
1148: &inIoSpace,
1149: &((PVIDEO_XGA_COPROCESSOR_INFORMATION)RequestPacket->
1150: OutputBuffer)->CoProcessorVirtualAddress);
1151:
1152: (PCHAR) ((PVIDEO_XGA_COPROCESSOR_INFORMATION)
1153: RequestPacket->OutputBuffer)->CoProcessorVirtualAddress += offset;
1154:
1155: //
1156: // Also return the physical address of the video memory so the
1157: // co-processor can access it.
1158: //
1159:
1160:
1161: (ULONG) ((PVIDEO_XGA_COPROCESSOR_INFORMATION)
1162: RequestPacket->OutputBuffer)->PhysicalVideoMemoryAddress =
1163: hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart;
1164:
1165: //
1166: // Also return the XGA IO Register Base Address.
1167: //
1168:
1169: (ULONG) ((PVIDEO_XGA_COPROCESSOR_INFORMATION)
1170: RequestPacket->OutputBuffer)->XgaIoRegisterBaseAddress =
1171: hwDeviceExtension->PhysicalIoRegBaseAddress.LowPart;
1172:
1173:
1174: VideoDebugPrint((3, "Xga IOCLT_MAP_CO_PROCESSOR\n physicalco = %x\n virtualco = %x\n physicalmem = %x\n",
1175: hwDeviceExtension->PhysicalCoProcessorAddress.LowPart,
1176: ((PVIDEO_XGA_COPROCESSOR_INFORMATION)
1177: RequestPacket->OutputBuffer)->CoProcessorVirtualAddress,
1178: hwDeviceExtension->PhysicalVideoMemoryAddress.LowPart));
1179:
1180: break ;
1181:
1182:
1183: case IOCTL_VIDEO_RESET_DEVICE:
1184:
1185: XGAOUT(APP_CTL_REG, 0x00) ;
1186:
1187: XGAOUT(INT_ENABLE_REG, 0x00) ;
1188:
1189: XGAOUT(INT_STATUS_REG, 0xff) ;
1190:
1191: // Now init all the index registers.
1192:
1193: for (i = 0 ; XgaResetToVga[i].PortIndex != 0xff ; i++) {
1194:
1195: XGAIDXOUT(0x0A,
1196: XgaResetToVga[i].PortIndex,
1197: XgaResetToVga[i].Data) ;
1198: }
1199:
1200: XGAOUT(OP_MODE_REG, 0x1) ;
1201:
1202: VideoPortWritePortUchar(hwDeviceExtension->PassThroughPort, 0x01);
1203:
1204: status = NO_ERROR;
1205:
1206: break ;
1207:
1208: //
1209: // if we get here, an invalid IoControlCode was specified.
1210: //
1211:
1212: default:
1213:
1214: VideoDebugPrint((1, "Fell through Xga startIO routine - invalid command\n"));
1215:
1216: status = ERROR_INVALID_FUNCTION ;
1217:
1218: break;
1219:
1220: }
1221:
1222: RequestPacket->StatusBlock->Status = status;
1223:
1224: return TRUE;
1225:
1226: } // end XgaStartIO()
1227:
1228:
1229: VP_STATUS
1230: XgaSetMode(
1231: PHW_DEVICE_EXTENSION HwDeviceExtension,
1232: ULONG ModeNum
1233: )
1234:
1235: /*++
1236:
1237: Routine Description:
1238:
1239: This routine is the main execution routine for the miniport driver. It
1240: acceptss a Video Request Packet, performs the request, and then returns
1241: with the appropriate status.
1242:
1243: Arguments:
1244:
1245: HwDeviceExtension - Supplies a pointer to the miniport's device extension.
1246:
1247: ModeNum - Index of the mode in which the adapter must be programmed.
1248:
1249: Return Value:
1250:
1251: NO_ERROR if the function completed successfully
1252: ERROR_INVALID_PARAMETER if the requested mode is invalid for the device.
1253:
1254: --*/
1255:
1256: {
1257: PHW_DEVICE_EXTENSION hwDeviceExtension = HwDeviceExtension;
1258: PUCHAR indexRegister = (PUCHAR) (hwDeviceExtension->IoRegBaseAddress + INDEX_REG);
1259: PMODE_REGISTER_DATA_TABLE modeTable;
1260: UCHAR input;
1261:
1262: VideoDebugPrint((1, "XgaSetMode: the mode being set is %d\n", ModeNum));
1263:
1264: //
1265: // Get the right mode table
1266: //
1267:
1268: if (hwDeviceExtension->BoardType & XGA_TYPE_1) {
1269:
1270: modeTable = XgaModes[ModeNum].Xga1Mode;
1271:
1272: } else {
1273:
1274: if (hwDeviceExtension->BoardType & XGA_TYPE_2) {
1275:
1276: modeTable = XgaModes[ModeNum].Xga2Mode;
1277:
1278: } else {
1279:
1280: VideoDebugPrint((0, "XGA: Internal mode flags are invalid"));
1281: return ERROR_INVALID_PARAMETER;
1282:
1283: }
1284: }
1285:
1286: //
1287: // Program the registers.
1288: //
1289:
1290: while (modeTable->Port != END_OF_SWITCH) {
1291:
1292: switch (modeTable->Port) {
1293:
1294: case INDEX_REG:
1295:
1296: VideoPortWritePortUchar(indexRegister,
1297: modeTable->IndexPort);
1298:
1299: VideoPortWritePortUchar(indexRegister + 1,
1300: modeTable->Data);
1301:
1302: break;
1303:
1304: case INDEX_OR_REG:
1305:
1306: VideoPortWritePortUchar(indexRegister,
1307: modeTable->IndexPort);
1308:
1309: input = VideoPortReadPortUchar((PUCHAR) hwDeviceExtension->IoRegBaseAddress +
1310: DATA_IN_REG);
1311:
1312: input |= modeTable->Data;
1313:
1314: VideoPortWritePortUchar(indexRegister + 1, input);
1315:
1316: break;
1317:
1318: default:
1319:
1320: VideoPortWritePortUchar((PUCHAR) hwDeviceExtension->IoRegBaseAddress +
1321: modeTable->Port,
1322: modeTable->Data);
1323:
1324: }
1325:
1326: modeTable++;
1327:
1328: }
1329:
1330: //
1331: // Save the current mode for future reference.
1332: //
1333:
1334: hwDeviceExtension->CurrentMode = (UCHAR) ModeNum;
1335:
1336: return NO_ERROR;
1337:
1338: } // end XgaSetMode();
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.