xref: /reactos/boot/environ/lib/io/display/efi/guicons.c (revision 40462c92)
1 /*
2  * COPYRIGHT:       See COPYING.ARM in the top level directory
3  * PROJECT:         ReactOS UEFI Boot Library
4  * FILE:            boot/environ/lib/io/display/efi/guicons.c
5  * PURPOSE:         Boot Library EFI GUI Console Routines
6  * PROGRAMMER:      Alex Ionescu (alex.ionescu@reactos.org)
7  */
8 
9 /* INCLUDES ******************************************************************/
10 
11 #include "bl.h"
12 
13 /* DATA VARIABLES ************************************************************/
14 
15 /* FUNCTIONS *****************************************************************/
16 
17 VOID
18 ConsoleFirmwareGraphicalClose (
19     _In_ PBL_GRAPHICS_CONSOLE GraphicsConsole
20     )
21 {
22     /* Call the correct close routine based on the console mode */
23     if (GraphicsConsole->Type == BlUgaConsole)
24     {
25         ConsoleEfiUgaClose(GraphicsConsole);
26     }
27     else
28     {
29         ConsoleEfiGopClose(GraphicsConsole);
30     }
31 }
32 
33 NTSTATUS
34 ConsoleEfiGraphicalOpenProtocol (
35     _In_ PBL_GRAPHICS_CONSOLE GraphicsConsole,
36     _In_ BL_GRAPHICS_CONSOLE_TYPE Type
37     )
38 {
39     ULONG HandleIndex, HandleCount;
40     EFI_HANDLE* HandleArray;
41     EFI_HANDLE Handle;
42     NTSTATUS Status;
43     PVOID Interface;
44 
45     /* Find a device handle that implements either GOP or UGA */
46     HandleCount = 0;
47     HandleArray = NULL;
48     Status = EfiLocateHandleBuffer(ByProtocol,
49                                    (Type == BlGopConsole) ?
50                                    &EfiGraphicsOutputProtocol :
51                                    &EfiUgaDrawProtocol,
52                                    &HandleCount,
53                                    &HandleArray);
54     if (!NT_SUCCESS(Status))
55     {
56         /* Nothing supports this (no video card?) */
57         EfiPrintf(L"Status: %lx Count: %d\r\n", Status, HandleCount);
58         return STATUS_UNSUCCESSFUL;
59     }
60 
61     /* Scan through the handles we received */
62     for (HandleIndex = 0; HandleIndex < HandleCount; HandleIndex++)
63     {
64         /* Try to open each one */
65         GraphicsConsole->Handle = HandleArray[HandleIndex];
66         Handle = HandleArray[HandleIndex];
67         Status = EfiOpenProtocol(Handle, &EfiDevicePathProtocol, &Interface);
68         if (NT_SUCCESS(Status))
69         {
70             /* Test worked, close the protocol */
71             EfiCloseProtocol(Handle, &EfiDevicePathProtocol);
72 
73             /* Now open the real protocol we want, either UGA or GOP */
74             Status = Type ? ConsoleEfiUgaOpen(GraphicsConsole) :
75                             ConsoleEfiGopOpen(GraphicsConsole);
76             if (NT_SUCCESS(Status))
77             {
78                 /* It worked -- store the type of console this is */
79                 GraphicsConsole->Type = Type;
80                 return STATUS_SUCCESS;
81             }
82         }
83     }
84 
85     /* We failed to find a working GOP/UGA protocol provider */
86     return STATUS_UNSUCCESSFUL;
87 }
88 
89 NTSTATUS
90 ConsoleFirmwareGraphicalClear (
91     _In_ PBL_GRAPHICS_CONSOLE Console,
92     _In_ ULONG Color
93     )
94 {
95     NTSTATUS Status;
96     UCHAR Pixel[4] = { 0 };
97 
98     /* Convert the standard color to a firmware pixel color */
99     Status = ConsolepConvertColorToPixel(Color, Pixel);
100     if (!NT_SUCCESS(Status))
101     {
102         return Status;
103     }
104 
105     /* Check if this is GOP or UGA */
106     if (Console->Type == BlUgaConsole)
107     {
108         EfiPrintf(L"Uga not supported\r\n");
109         Status = STATUS_NOT_IMPLEMENTED;
110     }
111     else
112     {
113         /* For GOP, just fill the screen */
114         ConsolepClearBuffer(Console->FrameBuffer,
115                             Console->DisplayMode.HRes,
116                             Pixel,
117                             Console->DisplayMode.VRes,
118                             Console->PixelsPerScanLine,
119                             Console->PixelDepth);
120         Status = STATUS_SUCCESS;
121     }
122 
123     /* All clear */
124     return Status;
125 }
126 
127 NTSTATUS
128 ConsoleFirmwareGraphicalEnable (
129     _In_ PBL_GRAPHICS_CONSOLE GraphicsConsole
130     )
131 {
132     NTSTATUS Status;
133 
134     /* Check what type of console this is */
135     if (GraphicsConsole->Type == BlUgaConsole)
136     {
137         /* Handle UGA */
138         Status = ConsoleEfiUgaSetResolution(GraphicsConsole,
139                                             &GraphicsConsole->DisplayMode,
140                                             1);
141     }
142     else
143     {
144         /* Handle GOP */
145         Status = ConsoleEfiGopEnable(GraphicsConsole);
146     }
147 
148     /* Return back to caller */
149     return Status;
150 }
151 
152 VOID
153 ConsoleFirmwareGraphicalDisable (
154     _In_ PBL_GRAPHICS_CONSOLE GraphicsConsole
155     )
156 {
157     /* Is this a GOP console? */
158     if (GraphicsConsole->Type == BlGopConsole)
159     {
160         /* Did we map a framebuffer? */
161         if (GraphicsConsole->FrameBuffer)
162         {
163             /* Unmap it */
164             BlMmUnmapVirtualAddressEx(GraphicsConsole->FrameBuffer,
165                                       GraphicsConsole->FrameBufferSize);
166         }
167     }
168 }
169