]> git.proxmox.com Git - mirror_edk2.git/blame - IntelFrameworkModulePkg/Universal/Console/VgaClassDxe/VgaClass.c
Add in VgaClassDxe
[mirror_edk2.git] / IntelFrameworkModulePkg / Universal / Console / VgaClassDxe / VgaClass.c
CommitLineData
e081218d 1/*++\r
2\r
3Copyright (c) 2006, Intel Corporation. All rights reserved. <BR> \r
4This software and associated documentation (if any) is furnished\r
5under a license and may only be used or copied in accordance\r
6with the terms of the license. Except as permitted by such\r
7license, no part of this software or documentation may be\r
8reproduced, stored in a retrieval system, or transmitted in any\r
9form or by any means without the express written consent of\r
10Intel Corporation.\r
11\r
12\r
13Module Name:\r
14\r
15 VgaClass.c\r
16 \r
17Abstract: \r
18 This driver produces a VGA console.\r
19 \r
20--*/\r
21\r
22#include "VgaClass.h"\r
23\r
24//\r
25// EFI Driver Binding Protocol for the VGA Class Driver\r
26//\r
27EFI_DRIVER_BINDING_PROTOCOL gVgaClassDriverBinding = {\r
28 VgaClassDriverBindingSupported,\r
29 VgaClassDriverBindingStart,\r
30 VgaClassDriverBindingStop,\r
31 0xa,\r
32 NULL,\r
33 NULL\r
34};\r
35\r
36/**\r
37 The user Entry Point for module VgaClass. The user code starts with this function.\r
38\r
39 @param[in] ImageHandle The firmware allocated handle for the EFI image. \r
40 @param[in] SystemTable A pointer to the EFI System Table.\r
41 \r
42 @retval EFI_SUCCESS The entry point is executed successfully.\r
43 @retval other Some error occurs when executing this entry point.\r
44\r
45**/\r
46EFI_STATUS\r
47EFIAPI\r
48InitializeVgaClass(\r
49 IN EFI_HANDLE ImageHandle,\r
50 IN EFI_SYSTEM_TABLE *SystemTable\r
51 )\r
52{\r
53 EFI_STATUS Status;\r
54\r
55 //\r
56 // Install driver model protocol(s).\r
57 //\r
58 Status = EfiLibInstallAllDriverProtocols (\r
59 ImageHandle,\r
60 SystemTable,\r
61 &gVgaClassDriverBinding,\r
62 ImageHandle,\r
63 &gVgaClassComponentName,\r
64 NULL,\r
65 NULL\r
66 );\r
67 ASSERT_EFI_ERROR (Status);\r
68\r
69\r
70 return Status;\r
71}\r
72\r
73//\r
74// Local variables\r
75//\r
76static CHAR16 CrLfString[3] = { CHAR_CARRIAGE_RETURN, CHAR_LINEFEED, CHAR_NULL };\r
77\r
78typedef struct {\r
79 CHAR16 Unicode;\r
80 CHAR8 PcAnsi;\r
81 CHAR8 Ascii;\r
82} UNICODE_TO_CHAR;\r
83\r
84//\r
85// This list is used to define the valid extend chars.\r
86// It also provides a mapping from Unicode to PCANSI or\r
87// ASCII. The ASCII mapping we just made up.\r
88//\r
89//\r
90STATIC UNICODE_TO_CHAR UnicodeToPcAnsiOrAscii[] = {\r
91 {\r
92 BOXDRAW_HORIZONTAL,\r
93 0xc4,\r
94 L'-'\r
95 },\r
96 {\r
97 BOXDRAW_VERTICAL,\r
98 0xb3,\r
99 L'|'\r
100 },\r
101 {\r
102 BOXDRAW_DOWN_RIGHT,\r
103 0xda,\r
104 L'/'\r
105 },\r
106 {\r
107 BOXDRAW_DOWN_LEFT,\r
108 0xbf,\r
109 L'\\'\r
110 },\r
111 {\r
112 BOXDRAW_UP_RIGHT,\r
113 0xc0,\r
114 L'\\'\r
115 },\r
116 {\r
117 BOXDRAW_UP_LEFT,\r
118 0xd9,\r
119 L'/'\r
120 },\r
121 {\r
122 BOXDRAW_VERTICAL_RIGHT,\r
123 0xc3,\r
124 L'|'\r
125 },\r
126 {\r
127 BOXDRAW_VERTICAL_LEFT,\r
128 0xb4,\r
129 L'|'\r
130 },\r
131 {\r
132 BOXDRAW_DOWN_HORIZONTAL,\r
133 0xc2,\r
134 L'+'\r
135 },\r
136 {\r
137 BOXDRAW_UP_HORIZONTAL,\r
138 0xc1,\r
139 L'+'\r
140 },\r
141 {\r
142 BOXDRAW_VERTICAL_HORIZONTAL,\r
143 0xc5,\r
144 L'+'\r
145 },\r
146 {\r
147 BOXDRAW_DOUBLE_HORIZONTAL,\r
148 0xcd,\r
149 L'-'\r
150 },\r
151 {\r
152 BOXDRAW_DOUBLE_VERTICAL,\r
153 0xba,\r
154 L'|'\r
155 },\r
156 {\r
157 BOXDRAW_DOWN_RIGHT_DOUBLE,\r
158 0xd5,\r
159 L'/'\r
160 },\r
161 {\r
162 BOXDRAW_DOWN_DOUBLE_RIGHT,\r
163 0xd6,\r
164 L'/'\r
165 },\r
166 {\r
167 BOXDRAW_DOUBLE_DOWN_RIGHT,\r
168 0xc9,\r
169 L'/'\r
170 },\r
171 {\r
172 BOXDRAW_DOWN_LEFT_DOUBLE,\r
173 0xb8,\r
174 L'\\'\r
175 },\r
176 {\r
177 BOXDRAW_DOWN_DOUBLE_LEFT,\r
178 0xb7,\r
179 L'\\'\r
180 },\r
181 {\r
182 BOXDRAW_DOUBLE_DOWN_LEFT,\r
183 0xbb,\r
184 L'\\'\r
185 },\r
186 {\r
187 BOXDRAW_UP_RIGHT_DOUBLE,\r
188 0xd4,\r
189 L'\\'\r
190 },\r
191 {\r
192 BOXDRAW_UP_DOUBLE_RIGHT,\r
193 0xd3,\r
194 L'\\'\r
195 },\r
196 {\r
197 BOXDRAW_DOUBLE_UP_RIGHT,\r
198 0xc8,\r
199 L'\\'\r
200 },\r
201 {\r
202 BOXDRAW_UP_LEFT_DOUBLE,\r
203 0xbe,\r
204 L'/'\r
205 },\r
206 {\r
207 BOXDRAW_UP_DOUBLE_LEFT,\r
208 0xbd,\r
209 L'/'\r
210 },\r
211 {\r
212 BOXDRAW_DOUBLE_UP_LEFT,\r
213 0xbc,\r
214 L'/'\r
215 },\r
216 {\r
217 BOXDRAW_VERTICAL_RIGHT_DOUBLE,\r
218 0xc6,\r
219 L'|'\r
220 },\r
221 {\r
222 BOXDRAW_VERTICAL_DOUBLE_RIGHT,\r
223 0xc7,\r
224 L'|'\r
225 },\r
226 {\r
227 BOXDRAW_DOUBLE_VERTICAL_RIGHT,\r
228 0xcc,\r
229 L'|'\r
230 },\r
231 {\r
232 BOXDRAW_VERTICAL_LEFT_DOUBLE,\r
233 0xb5,\r
234 L'|'\r
235 },\r
236 {\r
237 BOXDRAW_VERTICAL_DOUBLE_LEFT,\r
238 0xb6,\r
239 L'|'\r
240 },\r
241 {\r
242 BOXDRAW_DOUBLE_VERTICAL_LEFT,\r
243 0xb9,\r
244 L'|'\r
245 },\r
246 {\r
247 BOXDRAW_DOWN_HORIZONTAL_DOUBLE,\r
248 0xd1,\r
249 L'+'\r
250 },\r
251 {\r
252 BOXDRAW_DOWN_DOUBLE_HORIZONTAL,\r
253 0xd2,\r
254 L'+'\r
255 },\r
256 {\r
257 BOXDRAW_DOUBLE_DOWN_HORIZONTAL,\r
258 0xcb,\r
259 L'+'\r
260 },\r
261 {\r
262 BOXDRAW_UP_HORIZONTAL_DOUBLE,\r
263 0xcf,\r
264 L'+'\r
265 },\r
266 {\r
267 BOXDRAW_UP_DOUBLE_HORIZONTAL,\r
268 0xd0,\r
269 L'+'\r
270 },\r
271 {\r
272 BOXDRAW_DOUBLE_UP_HORIZONTAL,\r
273 0xca,\r
274 L'+'\r
275 },\r
276 {\r
277 BOXDRAW_VERTICAL_HORIZONTAL_DOUBLE,\r
278 0xd8,\r
279 L'+'\r
280 },\r
281 {\r
282 BOXDRAW_VERTICAL_DOUBLE_HORIZONTAL,\r
283 0xd7,\r
284 L'+'\r
285 },\r
286 {\r
287 BOXDRAW_DOUBLE_VERTICAL_HORIZONTAL,\r
288 0xce,\r
289 L'+'\r
290 },\r
291\r
292 {\r
293 BLOCKELEMENT_FULL_BLOCK,\r
294 0xdb,\r
295 L'*'\r
296 },\r
297 {\r
298 BLOCKELEMENT_LIGHT_SHADE,\r
299 0xb0,\r
300 L'+'\r
301 },\r
302\r
303 {\r
304 GEOMETRICSHAPE_UP_TRIANGLE,\r
305 0x1e,\r
306 L'^'\r
307 },\r
308 {\r
309 GEOMETRICSHAPE_RIGHT_TRIANGLE,\r
310 0x10,\r
311 L'>'\r
312 },\r
313 {\r
314 GEOMETRICSHAPE_DOWN_TRIANGLE,\r
315 0x1f,\r
316 L'v'\r
317 },\r
318 {\r
319 GEOMETRICSHAPE_LEFT_TRIANGLE,\r
320 0x11,\r
321 L'<'\r
322 },\r
323\r
324 {\r
325 ARROW_LEFT,\r
326 0x3c,\r
327 L'<'\r
328 },\r
329\r
330 {\r
331 ARROW_UP,\r
332 0x18,\r
333 L'^'\r
334 },\r
335\r
336 {\r
337 ARROW_RIGHT,\r
338 0x3e,\r
339 L'>'\r
340 },\r
341\r
342 {\r
343 ARROW_DOWN,\r
344 0x19,\r
345 L'v'\r
346 },\r
347\r
348 {\r
349 0x0000,\r
350 0x00,\r
351 0x00\r
352 }\r
353};\r
354\r
355//\r
356// Private worker functions\r
357//\r
358STATIC\r
359VOID\r
360SetVideoCursorPosition (\r
361 IN VGA_CLASS_DEV *VgaClassDev,\r
362 IN UINTN Column,\r
363 IN UINTN Row,\r
364 IN UINTN MaxColumn\r
365 );\r
366\r
367STATIC\r
368VOID\r
369WriteCrtc (\r
370 IN VGA_CLASS_DEV *VgaClassDev,\r
371 IN UINT16 Address,\r
372 IN UINT8 Data\r
373 );\r
374\r
375STATIC\r
376BOOLEAN\r
377LibIsValidTextGraphics (\r
378 IN CHAR16 Graphic,\r
379 OUT CHAR8 *PcAnsi, OPTIONAL\r
380 OUT CHAR8 *Ascii OPTIONAL\r
381 );\r
382\r
383STATIC\r
384BOOLEAN\r
385IsValidAscii (\r
386 IN CHAR16 Ascii\r
387 );\r
388\r
389STATIC\r
390BOOLEAN\r
391IsValidEfiCntlChar (\r
392 IN CHAR16 c\r
393 );\r
394\r
395EFI_STATUS\r
396EFIAPI\r
397VgaClassDriverBindingSupported (\r
398 IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
399 IN EFI_HANDLE Controller,\r
400 IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath\r
401 )\r
402/*++\r
403 \r
404 Routine Description:\r
405 \r
406 Supported.\r
407 \r
408 Arguments:\r
409 \r
410 (Standard DriverBinding Protocol Supported() function)\r
411 \r
412 Returns:\r
413 \r
414 EFI_STATUS\r
415 \r
416--*/\r
417// GC_TODO: This - add argument and description to function comment\r
418// GC_TODO: Controller - add argument and description to function comment\r
419// GC_TODO: RemainingDevicePath - add argument and description to function comment\r
420{\r
421 EFI_STATUS Status;\r
422 EFI_VGA_MINI_PORT_PROTOCOL *VgaMiniPort;\r
423\r
424 //\r
425 // Open the IO Abstraction(s) needed to perform the supported test\r
426 //\r
427 Status = gBS->OpenProtocol (\r
428 Controller,\r
429 &gEfiVgaMiniPortProtocolGuid,\r
430 (VOID **) &VgaMiniPort,\r
431 This->DriverBindingHandle,\r
432 Controller,\r
433 EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
434 );\r
435 if (EFI_ERROR (Status)) {\r
436 return Status;\r
437 }\r
438 //\r
439 // Open the IO Abstraction(s) needed to perform the supported test\r
440 //\r
441 Status = gBS->OpenProtocol (\r
442 Controller,\r
443 &gEfiPciIoProtocolGuid,\r
444 NULL,\r
445 This->DriverBindingHandle,\r
446 Controller,\r
447 EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
448 );\r
449 if (EFI_ERROR (Status)) {\r
450 return Status;\r
451 }\r
452\r
453 return Status;\r
454}\r
455\r
456EFI_STATUS\r
457EFIAPI\r
458VgaClassDriverBindingStart (\r
459 IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
460 IN EFI_HANDLE Controller,\r
461 IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath\r
462 )\r
463/*++\r
464 \r
465 Routine Description:\r
466 \r
467 Layers the Simple Text Output Protocol on top of the \r
468 VGA Mini Port Protocol\r
469 \r
470 Arguments:\r
471 \r
472 (Standard DriverBinding Protocol Start() function)\r
473 \r
474 Returns:\r
475 \r
476 EFI_STATUS\r
477 \r
478--*/\r
479// GC_TODO: This - add argument and description to function comment\r
480// GC_TODO: Controller - add argument and description to function comment\r
481// GC_TODO: RemainingDevicePath - add argument and description to function comment\r
482// GC_TODO: EFI_OUT_OF_RESOURCES - add return value to function comment\r
483{\r
484 EFI_STATUS Status;\r
485 EFI_VGA_MINI_PORT_PROTOCOL *VgaMiniPort;\r
486 EFI_PCI_IO_PROTOCOL *PciIo;\r
487 VGA_CLASS_DEV *VgaClassPrivate;\r
488 EFI_DEVICE_PATH_PROTOCOL *DevicePath;\r
489\r
490 Status = gBS->HandleProtocol (\r
491 Controller,\r
492 &gEfiDevicePathProtocolGuid,\r
493 (VOID **) &DevicePath\r
494 );\r
495 if (EFI_ERROR (Status)) {\r
496 return Status;\r
497 }\r
498 //\r
499 // Report that VGA Class driver is being enabled\r
500 //\r
501 REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
502 EFI_PROGRESS_CODE,\r
503 EFI_PERIPHERAL_LOCAL_CONSOLE | EFI_P_PC_ENABLE,\r
504 DevicePath\r
505 );\r
506\r
507 //\r
508 // Open the IO Abstraction(s) needed\r
509 //\r
510 Status = gBS->OpenProtocol (\r
511 Controller,\r
512 &gEfiPciIoProtocolGuid,\r
513 (VOID **) &PciIo,\r
514 This->DriverBindingHandle,\r
515 Controller,\r
516 EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
517 );\r
518 if (EFI_ERROR (Status)) {\r
519 return Status;\r
520 }\r
521\r
522 Status = gBS->OpenProtocol (\r
523 Controller,\r
524 &gEfiVgaMiniPortProtocolGuid,\r
525 (VOID **) &VgaMiniPort,\r
526 This->DriverBindingHandle,\r
527 Controller,\r
528 EFI_OPEN_PROTOCOL_BY_DRIVER\r
529 );\r
530 if (EFI_ERROR (Status)) {\r
531 return Status;\r
532 }\r
533 //\r
534 // Allocate the private device structure\r
535 //\r
536 Status = gBS->AllocatePool (\r
537 EfiBootServicesData,\r
538 sizeof (VGA_CLASS_DEV),\r
539 (VOID **) &VgaClassPrivate\r
540 );\r
541 if (EFI_ERROR (Status)) {\r
542 gBS->CloseProtocol (\r
543 Controller,\r
544 &gEfiVgaMiniPortProtocolGuid,\r
545 This->DriverBindingHandle,\r
546 Controller\r
547 );\r
548 return EFI_OUT_OF_RESOURCES;\r
549 }\r
550\r
551 ZeroMem (VgaClassPrivate, sizeof (VGA_CLASS_DEV));\r
552\r
553 //\r
554 // Initialize the private device structure\r
555 //\r
556 VgaClassPrivate->Signature = VGA_CLASS_DEV_SIGNATURE;\r
557 VgaClassPrivate->Handle = Controller;\r
558 VgaClassPrivate->VgaMiniPort = VgaMiniPort;\r
559 VgaClassPrivate->PciIo = PciIo;\r
560\r
561 VgaClassPrivate->SimpleTextOut.Reset = VgaClassReset;\r
562 VgaClassPrivate->SimpleTextOut.OutputString = VgaClassOutputString;\r
563 VgaClassPrivate->SimpleTextOut.TestString = VgaClassTestString;\r
564 VgaClassPrivate->SimpleTextOut.ClearScreen = VgaClassClearScreen;\r
565 VgaClassPrivate->SimpleTextOut.SetAttribute = VgaClassSetAttribute;\r
566 VgaClassPrivate->SimpleTextOut.SetCursorPosition = VgaClassSetCursorPosition;\r
567 VgaClassPrivate->SimpleTextOut.EnableCursor = VgaClassEnableCursor;\r
568 VgaClassPrivate->SimpleTextOut.QueryMode = VgaClassQueryMode;\r
569 VgaClassPrivate->SimpleTextOut.SetMode = VgaClassSetMode;\r
570\r
571 VgaClassPrivate->SimpleTextOut.Mode = &VgaClassPrivate->SimpleTextOutputMode;\r
572 VgaClassPrivate->SimpleTextOutputMode.MaxMode = VgaMiniPort->MaxMode;\r
573 VgaClassPrivate->DevicePath = DevicePath;\r
574\r
575 Status = VgaClassPrivate->SimpleTextOut.SetAttribute (\r
576 &VgaClassPrivate->SimpleTextOut,\r
577 EFI_TEXT_ATTR (EFI_WHITE,\r
578 EFI_BLACK)\r
579 );\r
580 if (EFI_ERROR (Status)) {\r
581 goto ErrorExit;\r
582 }\r
583\r
584 Status = VgaClassPrivate->SimpleTextOut.Reset (\r
585 &VgaClassPrivate->SimpleTextOut,\r
586 FALSE\r
587 );\r
588 if (EFI_ERROR (Status)) {\r
589 goto ErrorExit;\r
590 }\r
591\r
592 Status = VgaClassPrivate->SimpleTextOut.EnableCursor (\r
593 &VgaClassPrivate->SimpleTextOut,\r
594 TRUE\r
595 );\r
596 if (EFI_ERROR (Status)) {\r
597 goto ErrorExit;\r
598 }\r
599\r
600 Status = gBS->InstallMultipleProtocolInterfaces (\r
601 &Controller,\r
602 &gEfiSimpleTextOutProtocolGuid,\r
603 &VgaClassPrivate->SimpleTextOut,\r
604 NULL\r
605 );\r
606\r
607 return Status;\r
608\r
609ErrorExit:\r
610 REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
611 EFI_ERROR_CODE | EFI_ERROR_MINOR,\r
612 EFI_PERIPHERAL_LOCAL_CONSOLE | EFI_P_EC_CONTROLLER_ERROR,\r
613 DevicePath\r
614 );\r
615\r
616 return Status;\r
617\r
618}\r
619\r
620EFI_STATUS\r
621EFIAPI\r
622VgaClassDriverBindingStop (\r
623 IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
624 IN EFI_HANDLE Controller,\r
625 IN UINTN NumberOfChildren,\r
626 IN EFI_HANDLE *ChildHandleBuffer\r
627 )\r
628/*++\r
629 \r
630 Routine Description:\r
631 \r
632 Stop.\r
633 \r
634 Arguments:\r
635 \r
636 (Standard DriverBinding Protocol Stop() function)\r
637 \r
638 Returns:\r
639 \r
640 EFI_STATUS\r
641 \r
642--*/\r
643// GC_TODO: This - add argument and description to function comment\r
644// GC_TODO: Controller - add argument and description to function comment\r
645// GC_TODO: NumberOfChildren - add argument and description to function comment\r
646// GC_TODO: ChildHandleBuffer - add argument and description to function comment\r
647// GC_TODO: EFI_SUCCESS - add return value to function comment\r
648{\r
649 EFI_STATUS Status;\r
650 EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *SimpleTextOut;\r
651 VGA_CLASS_DEV *VgaClassPrivate;\r
652\r
653 Status = gBS->OpenProtocol (\r
654 Controller,\r
655 &gEfiSimpleTextOutProtocolGuid,\r
656 (VOID **) &SimpleTextOut,\r
657 This->DriverBindingHandle,\r
658 Controller,\r
659 EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
660 );\r
661 if (EFI_ERROR (Status)) {\r
662 return Status;\r
663 }\r
664\r
665 VgaClassPrivate = VGA_CLASS_DEV_FROM_THIS (SimpleTextOut);\r
666\r
667 //\r
668 // Report that VGA Class driver is being disabled\r
669 //\r
670 REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
671 EFI_PROGRESS_CODE,\r
672 EFI_PERIPHERAL_LOCAL_CONSOLE | EFI_P_PC_DISABLE,\r
673 VgaClassPrivate->DevicePath\r
674 );\r
675\r
676 Status = gBS->UninstallProtocolInterface (\r
677 Controller,\r
678 &gEfiSimpleTextOutProtocolGuid,\r
679 &VgaClassPrivate->SimpleTextOut\r
680 );\r
681 if (EFI_ERROR (Status)) {\r
682 return Status;\r
683 }\r
684 //\r
685 // Release PCI I/O and VGA Mini Port Protocols on the controller handle.\r
686 //\r
687 gBS->CloseProtocol (\r
688 Controller,\r
689 &gEfiPciIoProtocolGuid,\r
690 This->DriverBindingHandle,\r
691 Controller\r
692 );\r
693\r
694 gBS->CloseProtocol (\r
695 Controller,\r
696 &gEfiVgaMiniPortProtocolGuid,\r
697 This->DriverBindingHandle,\r
698 Controller\r
699 );\r
700\r
701 gBS->FreePool (VgaClassPrivate);\r
702\r
703 return EFI_SUCCESS;\r
704}\r
705//\r
706// Simple Text Output Protocol Functions\r
707//\r
708EFI_STATUS\r
709EFIAPI\r
710VgaClassReset (\r
711 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
712 IN BOOLEAN ExtendedVerification\r
713 )\r
714/*++\r
715\r
716Routine Description:\r
717\r
718 GC_TODO: Add function description\r
719\r
720Arguments:\r
721\r
722 This - GC_TODO: add argument description\r
723 ExtendedVerification - GC_TODO: add argument description\r
724\r
725Returns:\r
726\r
727 GC_TODO: add return values\r
728\r
729--*/\r
730{\r
731 EFI_STATUS Status;\r
732 VGA_CLASS_DEV *VgaClassPrivate;\r
733\r
734 VgaClassPrivate = VGA_CLASS_DEV_FROM_THIS (This);\r
735\r
736 REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
737 EFI_PROGRESS_CODE,\r
738 EFI_PERIPHERAL_LOCAL_CONSOLE | EFI_P_PC_RESET,\r
739 VgaClassPrivate->DevicePath\r
740 );\r
741\r
742 This->SetAttribute (This, EFI_TEXT_ATTR (This->Mode->Attribute & 0x0F, EFI_BACKGROUND_BLACK));\r
743\r
744 Status = This->SetMode (This, 0);\r
745 if (EFI_ERROR (Status)) {\r
746 return Status;\r
747 }\r
748\r
749 return This->ClearScreen (This);\r
750}\r
751\r
752EFI_STATUS\r
753EFIAPI\r
754VgaClassOutputString (\r
755 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
756 IN CHAR16 *WString\r
757 )\r
758/*++\r
759\r
760Routine Description:\r
761\r
762 GC_TODO: Add function description\r
763\r
764Arguments:\r
765\r
766 This - GC_TODO: add argument description\r
767 WString - GC_TODO: add argument description\r
768\r
769Returns:\r
770\r
771 EFI_SUCCESS - GC_TODO: Add description for return value\r
772\r
773--*/\r
774{\r
775 EFI_STATUS Status;\r
776 VGA_CLASS_DEV *VgaClassDev;\r
777 EFI_SIMPLE_TEXT_OUTPUT_MODE *Mode;\r
778 UINTN MaxColumn;\r
779 UINTN MaxRow;\r
780 UINT32 VideoChar;\r
781 CHAR8 GraphicChar;\r
782\r
783 VgaClassDev = VGA_CLASS_DEV_FROM_THIS (This);\r
784\r
785 Mode = This->Mode;\r
786\r
787 Status = This->QueryMode (\r
788 This,\r
789 Mode->Mode,\r
790 &MaxColumn,\r
791 &MaxRow\r
792 );\r
793 if (EFI_ERROR (Status)) {\r
794 return Status;\r
795 }\r
796\r
797 for (; *WString != CHAR_NULL; WString++) {\r
798\r
799 switch (*WString) {\r
800 case CHAR_BACKSPACE:\r
801 if (Mode->CursorColumn > 0) {\r
802 Mode->CursorColumn--;\r
803 }\r
804 break;\r
805\r
806 case CHAR_LINEFEED:\r
807 if (Mode->CursorRow == (INT32) (MaxRow - 1)) {\r
808 //\r
809 // Scroll the screen by copying the contents\r
810 // of the VGA display up one line\r
811 //\r
812 VgaClassDev->PciIo->CopyMem (\r
813 VgaClassDev->PciIo,\r
814 EfiPciIoWidthUint32,\r
815 VgaClassDev->VgaMiniPort->VgaMemoryBar,\r
816 VgaClassDev->VgaMiniPort->VgaMemoryOffset,\r
817 VgaClassDev->VgaMiniPort->VgaMemoryBar,\r
818 VgaClassDev->VgaMiniPort->VgaMemoryOffset + MaxColumn * 2,\r
819 ((MaxRow - 1) * MaxColumn) >> 1\r
820 );\r
821\r
822 //\r
823 // Print Blank Line of spaces with the current color attributes\r
824 //\r
825 VideoChar = (Mode->Attribute << 8) | ' ';\r
826 VideoChar = (VideoChar << 16) | VideoChar;\r
827 VgaClassDev->PciIo->Mem.Write (\r
828 VgaClassDev->PciIo,\r
829 EfiPciIoWidthFillUint32,\r
830 VgaClassDev->VgaMiniPort->VgaMemoryBar,\r
831 VgaClassDev->VgaMiniPort->VgaMemoryOffset + (MaxRow - 1) * MaxColumn * 2,\r
832 MaxColumn >> 1,\r
833 &VideoChar\r
834 );\r
835 }\r
836\r
837 if (Mode->CursorRow < (INT32) (MaxRow - 1)) {\r
838 Mode->CursorRow++;\r
839 }\r
840 break;\r
841\r
842 case CHAR_CARRIAGE_RETURN:\r
843 Mode->CursorColumn = 0;\r
844 break;\r
845\r
846 default:\r
847 if (!LibIsValidTextGraphics (*WString, &GraphicChar, NULL)) {\r
848 //\r
849 // Just convert to ASCII\r
850 //\r
851 GraphicChar = (CHAR8) *WString;\r
852 if (!IsValidAscii (GraphicChar)) {\r
853 //\r
854 // Keep the API from supporting PCANSI Graphics chars\r
855 //\r
856 GraphicChar = '?';\r
857 }\r
858 }\r
859\r
860 VideoChar = (Mode->Attribute << 8) | GraphicChar;\r
861 VgaClassDev->PciIo->Mem.Write (\r
862 VgaClassDev->PciIo,\r
863 EfiPciIoWidthUint16,\r
864 VgaClassDev->VgaMiniPort->VgaMemoryBar,\r
865 VgaClassDev->VgaMiniPort->VgaMemoryOffset + ((Mode->CursorRow * MaxColumn + Mode->CursorColumn) * 2),\r
866 1,\r
867 &VideoChar\r
868 );\r
869\r
870 if (Mode->CursorColumn >= (INT32) (MaxColumn - 1)) {\r
871 This->OutputString (This, CrLfString);\r
872 } else {\r
873 Mode->CursorColumn++;\r
874 }\r
875 break;\r
876 }\r
877 }\r
878\r
879 SetVideoCursorPosition (\r
880 VgaClassDev,\r
881 (UINTN) Mode->CursorColumn,\r
882 (UINTN) Mode->CursorRow,\r
883 MaxColumn\r
884 );\r
885\r
886 return EFI_SUCCESS;\r
887}\r
888\r
889EFI_STATUS\r
890EFIAPI\r
891VgaClassTestString (\r
892 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
893 IN CHAR16 *WString\r
894 )\r
895/*++\r
896\r
897Routine Description:\r
898\r
899 GC_TODO: Add function description\r
900\r
901Arguments:\r
902\r
903 This - GC_TODO: add argument description\r
904 WString - GC_TODO: add argument description\r
905\r
906Returns:\r
907\r
908 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
909 EFI_SUCCESS - GC_TODO: Add description for return value\r
910\r
911--*/\r
912{\r
913 while (*WString != 0x0000) {\r
914 if (!(IsValidAscii (*WString) || IsValidEfiCntlChar (*WString) || LibIsValidTextGraphics (*WString, NULL, NULL))) {\r
915 return EFI_UNSUPPORTED;\r
916 }\r
917\r
918 WString++;\r
919 }\r
920\r
921 return EFI_SUCCESS;\r
922}\r
923\r
924EFI_STATUS\r
925EFIAPI\r
926VgaClassClearScreen (\r
927 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This\r
928 )\r
929/*++\r
930\r
931Routine Description:\r
932\r
933 GC_TODO: Add function description\r
934\r
935Arguments:\r
936\r
937 This - GC_TODO: add argument description\r
938\r
939Returns:\r
940\r
941 EFI_SUCCESS - GC_TODO: Add description for return value\r
942\r
943--*/\r
944{\r
945 EFI_STATUS Status;\r
946 VGA_CLASS_DEV *VgaClassDev;\r
947 UINTN MaxRow;\r
948 UINTN MaxColumn;\r
949 UINT32 VideoChar;\r
950\r
951 VgaClassDev = VGA_CLASS_DEV_FROM_THIS (This);\r
952\r
953 Status = This->QueryMode (\r
954 This,\r
955 This->Mode->Mode,\r
956 &MaxColumn,\r
957 &MaxRow\r
958 );\r
959 if (EFI_ERROR (Status)) {\r
960 return Status;\r
961 }\r
962\r
963 VideoChar = (This->Mode->Attribute << 8) | ' ';\r
964 VideoChar = (VideoChar << 16) | VideoChar;\r
965 VgaClassDev->PciIo->Mem.Write (\r
966 VgaClassDev->PciIo,\r
967 EfiPciIoWidthFillUint32,\r
968 VgaClassDev->VgaMiniPort->VgaMemoryBar,\r
969 VgaClassDev->VgaMiniPort->VgaMemoryOffset,\r
970 (MaxRow * MaxColumn) >> 1,\r
971 &VideoChar\r
972 );\r
973\r
974 This->SetCursorPosition (This, 0, 0);\r
975\r
976 return EFI_SUCCESS;\r
977}\r
978\r
979EFI_STATUS\r
980EFIAPI\r
981VgaClassSetAttribute (\r
982 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
983 IN UINTN Attribute\r
984 )\r
985/*++\r
986\r
987Routine Description:\r
988\r
989 GC_TODO: Add function description\r
990\r
991Arguments:\r
992\r
993 This - GC_TODO: add argument description\r
994 Attribute - GC_TODO: add argument description\r
995\r
996Returns:\r
997\r
998 EFI_SUCCESS - GC_TODO: Add description for return value\r
999 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
1000\r
1001--*/\r
1002{\r
1003 if (Attribute <= EFI_MAX_ATTRIBUTE) {\r
1004 This->Mode->Attribute = (INT32) Attribute;\r
1005 return EFI_SUCCESS;\r
1006 }\r
1007\r
1008 return EFI_UNSUPPORTED;\r
1009}\r
1010\r
1011EFI_STATUS\r
1012EFIAPI\r
1013VgaClassSetCursorPosition (\r
1014 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
1015 IN UINTN Column,\r
1016 IN UINTN Row\r
1017 )\r
1018/*++\r
1019\r
1020Routine Description:\r
1021\r
1022 GC_TODO: Add function description\r
1023\r
1024Arguments:\r
1025\r
1026 This - GC_TODO: add argument description\r
1027 Column - GC_TODO: add argument description\r
1028 Row - GC_TODO: add argument description\r
1029\r
1030Returns:\r
1031\r
1032 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
1033 EFI_SUCCESS - GC_TODO: Add description for return value\r
1034\r
1035--*/\r
1036{\r
1037 EFI_STATUS Status;\r
1038 VGA_CLASS_DEV *VgaClassDev;\r
1039 UINTN MaxColumn;\r
1040 UINTN MaxRow;\r
1041\r
1042 VgaClassDev = VGA_CLASS_DEV_FROM_THIS (This);\r
1043\r
1044 Status = This->QueryMode (\r
1045 This,\r
1046 This->Mode->Mode,\r
1047 &MaxColumn,\r
1048 &MaxRow\r
1049 );\r
1050 if (EFI_ERROR (Status)) {\r
1051 return Status;\r
1052 }\r
1053\r
1054 if (Column >= MaxColumn || Row >= MaxRow) {\r
1055 return EFI_UNSUPPORTED;\r
1056 }\r
1057\r
1058 SetVideoCursorPosition (VgaClassDev, Column, Row, MaxColumn);\r
1059\r
1060 This->Mode->CursorColumn = (INT32) Column;\r
1061 This->Mode->CursorRow = (INT32) Row;\r
1062\r
1063 return EFI_SUCCESS;\r
1064}\r
1065\r
1066EFI_STATUS\r
1067EFIAPI\r
1068VgaClassEnableCursor (\r
1069 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
1070 IN BOOLEAN Visible\r
1071 )\r
1072/*++\r
1073\r
1074Routine Description:\r
1075\r
1076 GC_TODO: Add function description\r
1077\r
1078Arguments:\r
1079\r
1080 This - GC_TODO: add argument description\r
1081 Visible - GC_TODO: add argument description\r
1082\r
1083Returns:\r
1084\r
1085 EFI_SUCCESS - GC_TODO: Add description for return value\r
1086\r
1087--*/\r
1088{\r
1089 VGA_CLASS_DEV *VgaClassDev;\r
1090\r
1091 VgaClassDev = VGA_CLASS_DEV_FROM_THIS (This);\r
1092 if (Visible) {\r
1093 switch (This->Mode->Mode) {\r
1094 case 1:\r
1095 WriteCrtc (VgaClassDev, CRTC_CURSOR_START, 0x06);\r
1096 WriteCrtc (VgaClassDev, CRTC_CURSOR_END, 0x07);\r
1097 break;\r
1098\r
1099 default:\r
1100 WriteCrtc (VgaClassDev, CRTC_CURSOR_START, 0x0e);\r
1101 WriteCrtc (VgaClassDev, CRTC_CURSOR_END, 0x0f);\r
1102 break;\r
1103 }\r
1104 } else {\r
1105 WriteCrtc (VgaClassDev, CRTC_CURSOR_START, 0x20);\r
1106 }\r
1107\r
1108 This->Mode->CursorVisible = Visible;\r
1109 return EFI_SUCCESS;\r
1110}\r
1111\r
1112EFI_STATUS\r
1113EFIAPI\r
1114VgaClassQueryMode (\r
1115 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
1116 IN UINTN ModeNumber,\r
1117 OUT UINTN *Columns,\r
1118 OUT UINTN *Rows\r
1119 )\r
1120/*++\r
1121\r
1122Routine Description:\r
1123\r
1124 GC_TODO: Add function description\r
1125\r
1126Arguments:\r
1127\r
1128 This - GC_TODO: add argument description\r
1129 ModeNumber - GC_TODO: add argument description\r
1130 Columns - GC_TODO: add argument description\r
1131 Rows - GC_TODO: add argument description\r
1132\r
1133Returns:\r
1134\r
1135 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
1136 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
1137 EFI_SUCCESS - GC_TODO: Add description for return value\r
1138\r
1139--*/\r
1140{\r
1141 if ((INT32) ModeNumber >= This->Mode->MaxMode) {\r
1142 *Columns = 0;\r
1143 *Rows = 0;\r
1144 return EFI_UNSUPPORTED;\r
1145 }\r
1146\r
1147 switch (ModeNumber) {\r
1148 case 0:\r
1149 *Columns = 80;\r
1150 *Rows = 25;\r
1151 break;\r
1152\r
1153 case 1:\r
1154 *Columns = 80;\r
1155 *Rows = 50;\r
1156 break;\r
1157\r
1158 default:\r
1159 *Columns = 0;\r
1160 *Rows = 0;\r
1161 return EFI_UNSUPPORTED;\r
1162 }\r
1163\r
1164 return EFI_SUCCESS;\r
1165}\r
1166\r
1167EFI_STATUS\r
1168EFIAPI\r
1169VgaClassSetMode (\r
1170 IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *This,\r
1171 IN UINTN ModeNumber\r
1172 )\r
1173/*++\r
1174\r
1175Routine Description:\r
1176\r
1177 GC_TODO: Add function description\r
1178\r
1179Arguments:\r
1180\r
1181 This - GC_TODO: add argument description\r
1182 ModeNumber - GC_TODO: add argument description\r
1183\r
1184Returns:\r
1185\r
1186 EFI_UNSUPPORTED - GC_TODO: Add description for return value\r
1187\r
1188--*/\r
1189{\r
1190 EFI_STATUS Status;\r
1191 VGA_CLASS_DEV *VgaClassDev;\r
1192\r
1193 VgaClassDev = VGA_CLASS_DEV_FROM_THIS (This);\r
1194\r
1195 if ((INT32) ModeNumber >= This->Mode->MaxMode) {\r
1196 return EFI_UNSUPPORTED;\r
1197 }\r
1198\r
1199 This->ClearScreen (This);\r
1200\r
1201 This->Mode->Mode = (INT32) ModeNumber;\r
1202\r
1203 Status = VgaClassDev->VgaMiniPort->SetMode (VgaClassDev->VgaMiniPort, ModeNumber);\r
1204\r
1205 return Status;\r
1206}\r
1207//\r
1208// Private Worker Functions\r
1209//\r
1210STATIC\r
1211VOID\r
1212SetVideoCursorPosition (\r
1213 IN VGA_CLASS_DEV *VgaClassDev,\r
1214 IN UINTN Column,\r
1215 IN UINTN Row,\r
1216 IN UINTN MaxColumn\r
1217 )\r
1218/*++\r
1219\r
1220Routine Description:\r
1221\r
1222 GC_TODO: Add function description\r
1223\r
1224Arguments:\r
1225\r
1226 VgaClassDev - GC_TODO: add argument description\r
1227 Column - GC_TODO: add argument description\r
1228 Row - GC_TODO: add argument description\r
1229 MaxColumn - GC_TODO: add argument description\r
1230\r
1231Returns:\r
1232\r
1233 GC_TODO: add return values\r
1234\r
1235--*/\r
1236{\r
1237 Column = Column & 0xff;\r
1238 Row = Row & 0xff;\r
1239 MaxColumn = MaxColumn & 0xff;\r
1240 WriteCrtc (\r
1241 VgaClassDev,\r
1242 CRTC_CURSOR_LOCATION_HIGH,\r
1243 (UINT8) ((Row * MaxColumn + Column) >> 8)\r
1244 );\r
1245 WriteCrtc (\r
1246 VgaClassDev,\r
1247 CRTC_CURSOR_LOCATION_LOW,\r
1248 (UINT8) ((Row * MaxColumn + Column) & 0xff)\r
1249 );\r
1250}\r
1251\r
1252STATIC\r
1253VOID\r
1254WriteCrtc (\r
1255 IN VGA_CLASS_DEV *VgaClassDev,\r
1256 IN UINT16 Address,\r
1257 IN UINT8 Data\r
1258 )\r
1259/*++\r
1260\r
1261Routine Description:\r
1262\r
1263 GC_TODO: Add function description\r
1264\r
1265Arguments:\r
1266\r
1267 VgaClassDev - GC_TODO: add argument description\r
1268 Address - GC_TODO: add argument description\r
1269 Data - GC_TODO: add argument description\r
1270\r
1271Returns:\r
1272\r
1273 GC_TODO: add return values\r
1274\r
1275--*/\r
1276{\r
1277 VgaClassDev->PciIo->Io.Write (\r
1278 VgaClassDev->PciIo,\r
1279 EfiPciIoWidthUint8,\r
1280 VgaClassDev->VgaMiniPort->CrtcAddressRegisterBar,\r
1281 VgaClassDev->VgaMiniPort->CrtcAddressRegisterOffset,\r
1282 1,\r
1283 &Address\r
1284 );\r
1285\r
1286 VgaClassDev->PciIo->Io.Write (\r
1287 VgaClassDev->PciIo,\r
1288 EfiPciIoWidthUint8,\r
1289 VgaClassDev->VgaMiniPort->CrtcDataRegisterBar,\r
1290 VgaClassDev->VgaMiniPort->CrtcDataRegisterOffset,\r
1291 1,\r
1292 &Data\r
1293 );\r
1294}\r
1295\r
1296STATIC\r
1297BOOLEAN\r
1298LibIsValidTextGraphics (\r
1299 IN CHAR16 Graphic,\r
1300 OUT CHAR8 *PcAnsi, OPTIONAL\r
1301 OUT CHAR8 *Ascii OPTIONAL\r
1302 )\r
1303/*++\r
1304\r
1305Routine Description:\r
1306\r
1307 Detects if a Unicode char is for Box Drawing text graphics.\r
1308\r
1309Arguments:\r
1310\r
1311 Grphic - Unicode char to test.\r
1312\r
1313 PcAnsi - Optional pointer to return PCANSI equivalent of Graphic.\r
1314\r
1315 Asci - Optional pointer to return Ascii equivalent of Graphic.\r
1316\r
1317Returns:\r
1318\r
1319 TRUE if Gpaphic is a supported Unicode Box Drawing character.\r
1320\r
1321--*/\r
1322// GC_TODO: Graphic - add argument and description to function comment\r
1323{\r
1324 UNICODE_TO_CHAR *Table;\r
1325\r
1326 if ((((Graphic & 0xff00) != 0x2500) && ((Graphic & 0xff00) != 0x2100))) {\r
1327 //\r
1328 // Unicode drawing code charts are all in the 0x25xx range,\r
1329 // arrows are 0x21xx\r
1330 //\r
1331 return FALSE;\r
1332 }\r
1333\r
1334 for (Table = UnicodeToPcAnsiOrAscii; Table->Unicode != 0x0000; Table++) {\r
1335 if (Graphic == Table->Unicode) {\r
1336 if (PcAnsi) {\r
1337 *PcAnsi = Table->PcAnsi;\r
1338 }\r
1339\r
1340 if (Ascii) {\r
1341 *Ascii = Table->Ascii;\r
1342 }\r
1343\r
1344 return TRUE;\r
1345 }\r
1346 }\r
1347\r
1348 return FALSE;\r
1349}\r
1350\r
1351STATIC\r
1352BOOLEAN\r
1353IsValidAscii (\r
1354 IN CHAR16 Ascii\r
1355 )\r
1356/*++\r
1357\r
1358Routine Description:\r
1359\r
1360 GC_TODO: Add function description\r
1361\r
1362Arguments:\r
1363\r
1364 Ascii - GC_TODO: add argument description\r
1365\r
1366Returns:\r
1367\r
1368 GC_TODO: add return values\r
1369\r
1370--*/\r
1371{\r
1372 if ((Ascii >= 0x20) && (Ascii <= 0x7f)) {\r
1373 return TRUE;\r
1374 }\r
1375\r
1376 return FALSE;\r
1377}\r
1378\r
1379STATIC\r
1380BOOLEAN\r
1381IsValidEfiCntlChar (\r
1382 IN CHAR16 c\r
1383 )\r
1384/*++\r
1385\r
1386Routine Description:\r
1387\r
1388 GC_TODO: Add function description\r
1389\r
1390Arguments:\r
1391\r
1392 c - GC_TODO: add argument description\r
1393\r
1394Returns:\r
1395\r
1396 GC_TODO: add return values\r
1397\r
1398--*/\r
1399{\r
1400 if (c == CHAR_NULL || c == CHAR_BACKSPACE || c == CHAR_LINEFEED || c == CHAR_CARRIAGE_RETURN) {\r
1401 return TRUE;\r
1402 }\r
1403\r
1404 return FALSE;\r
1405}\r