3 Copyright (c) 2004 - 2010, Intel Corporation. All rights reserved.<BR>
4 This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 Basic Ascii AvSPrintf() function named VSPrint(). VSPrint() enables very
19 simple implemenation of SPrint() and Print() to support debug.
21 You can not Print more than EFI_DRIVER_LIB_MAX_PRINT_BUFFER characters at a
22 time. This makes the implementation very simple.
24 VSPrint, Print, SPrint format specification has the follwoing form
32 ',' - Place commas in numberss
33 '0' - Prefix for width with zeros
38 '*' - Get width from a UINTN argumnet from the argument list
39 Decimal number that represents width of print
42 'X' - argument is a UINTN hex number, prefix '0'
43 'x' - argument is a hex number
44 'd' - argument is a decimal number
45 'a' - argument is an ascii string
46 'S','s' - argument is an Unicode string
47 'g' - argument is a pointer to an EFI_GUID
48 't' - argument is a pointer to an EFI_TIME structure
49 'c' - argument is an ascii character
50 'r' - argument is EFI_STATUS
56 #include "EfiDriverLib.h"
57 #include "TianoCommon.h"
58 #include "EfiCommonLib.h"
59 #include "PrintWidth.h"
60 #include "EfiPrintLib.h"
62 #if (EFI_SPECIFICATION_VERSION >= 0x0002000A)
63 #include EFI_PROTOCOL_DEFINITION (HiiFont)
65 #include EFI_PROTOCOL_DEFINITION (Hii)
68 static EFI_GRAPHICS_OUTPUT_BLT_PIXEL mEfiColors
[16] = {
69 {0x00, 0x00, 0x00, 0x00},
70 {0x98, 0x00, 0x00, 0x00},
71 {0x00, 0x98, 0x00, 0x00},
72 {0x98, 0x98, 0x00, 0x00},
73 {0x00, 0x00, 0x98, 0x00},
74 {0x98, 0x00, 0x98, 0x00},
75 {0x00, 0x98, 0x98, 0x00},
76 {0x98, 0x98, 0x98, 0x00},
77 {0x10, 0x10, 0x10, 0x00},
78 {0xff, 0x10, 0x10, 0x00},
79 {0x10, 0xff, 0x10, 0x00},
80 {0xff, 0xff, 0x10, 0x00},
81 {0x10, 0x10, 0xff, 0x00},
82 {0xf0, 0x10, 0xff, 0x00},
83 {0x10, 0xff, 0xff, 0x00},
84 {0xff, 0xff, 0xff, 0x00},
90 IN EFI_GRAPHICS_OUTPUT_PROTOCOL
*GraphicsOutput
,
91 IN EFI_UGA_DRAW_PROTOCOL
*UgaDraw
,
92 IN EFI_SIMPLE_TEXT_OUT_PROTOCOL
*Sto
,
95 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL
*Foreground
,
96 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL
*Background
,
104 Display string worker for: Print, PrintAt, IPrint, IPrintAt
108 GraphicsOutput - Graphics output protocol interface
110 UgaDraw - UGA draw protocol interface
112 Sto - Simple text out protocol interface
114 X - X coordinate to start printing
116 Y - Y coordinate to start printing
118 Foreground - Foreground color
120 Background - Background color
124 args - Print arguments
128 Length of string printed to the console
135 CHAR16
*UnicodeWeight
;
136 UINT32 HorizontalResolution
;
137 UINT32 VerticalResolution
;
142 #if (EFI_SPECIFICATION_VERSION >= 0x0002000A)
143 EFI_HII_FONT_PROTOCOL
*HiiFont
;
144 EFI_IMAGE_OUTPUT
*Blt
;
145 EFI_FONT_DISPLAY_INFO
*FontInfo
;
147 EFI_HII_PROTOCOL
*Hii
;
151 EFI_NARROW_GLYPH
*Glyph
;
152 EFI_GRAPHICS_OUTPUT_BLT_PIXEL
*LineBuffer
;
156 // For now, allocate an arbitrarily long buffer
158 Buffer
= EfiLibAllocateZeroPool (0x10000);
159 if (Buffer
== NULL
) {
163 if (GraphicsOutput
!= NULL
) {
164 HorizontalResolution
= GraphicsOutput
->Mode
->Info
->HorizontalResolution
;
165 VerticalResolution
= GraphicsOutput
->Mode
->Info
->VerticalResolution
;
167 UgaDraw
->GetMode (UgaDraw
, &HorizontalResolution
, &VerticalResolution
, &ColorDepth
, &RefreshRate
);
169 ASSERT ((HorizontalResolution
!= 0) && (VerticalResolution
!=0));
171 #if (EFI_SPECIFICATION_VERSION >= 0x0002000A)
174 ASSERT (GraphicsOutput
!= NULL
);
175 Status
= gBS
->LocateProtocol (&gEfiHiiFontProtocolGuid
, NULL
, (VOID
**) &HiiFont
);
176 if (EFI_ERROR (Status
)) {
181 Status
= gBS
->LocateProtocol (&gEfiHiiProtocolGuid
, NULL
, (VOID
**)&Hii
);
182 if (EFI_ERROR (Status
)) {
185 LineBufferLen
= sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
) * HorizontalResolution
* GLYPH_HEIGHT
;
186 LineBuffer
= EfiLibAllocatePool (LineBufferLen
);
187 if (LineBuffer
== NULL
) {
188 Status
= EFI_OUT_OF_RESOURCES
;
193 VSPrint (Buffer
, 0x10000, fmt
, args
);
195 UnicodeWeight
= (CHAR16
*) Buffer
;
197 for (Index
= 0; UnicodeWeight
[Index
] != 0; Index
++) {
198 if (UnicodeWeight
[Index
] == CHAR_BACKSPACE
||
199 UnicodeWeight
[Index
] == CHAR_LINEFEED
||
200 UnicodeWeight
[Index
] == CHAR_CARRIAGE_RETURN
) {
201 UnicodeWeight
[Index
] = 0;
205 BufferLen
= EfiStrLen (Buffer
);
207 #if (EFI_SPECIFICATION_VERSION >= 0x0002000A)
208 LineBufferLen
= sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
) * HorizontalResolution
* EFI_GLYPH_HEIGHT
;
209 if (EFI_GLYPH_WIDTH
* EFI_GLYPH_HEIGHT
* sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL
) * BufferLen
> LineBufferLen
) {
210 Status
= EFI_INVALID_PARAMETER
;
214 Blt
= (EFI_IMAGE_OUTPUT
*) EfiLibAllocateZeroPool (sizeof (EFI_IMAGE_OUTPUT
));
216 Status
= EFI_OUT_OF_RESOURCES
;
220 Blt
->Width
= (UINT16
) (HorizontalResolution
);
221 Blt
->Height
= (UINT16
) (VerticalResolution
);
222 Blt
->Image
.Screen
= GraphicsOutput
;
224 FontInfo
= (EFI_FONT_DISPLAY_INFO
*) EfiLibAllocateZeroPool (sizeof (EFI_FONT_DISPLAY_INFO
));
225 if (FontInfo
== NULL
) {
226 Status
= EFI_OUT_OF_RESOURCES
;
229 if (Foreground
!= NULL
) {
230 EfiCopyMem (&FontInfo
->ForegroundColor
, Foreground
, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
));
233 &FontInfo
->ForegroundColor
,
234 &mEfiColors
[Sto
->Mode
->Attribute
& 0x0f],
235 sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
)
238 if (Background
!= NULL
) {
239 EfiCopyMem (&FontInfo
->BackgroundColor
, Background
, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
));
242 &FontInfo
->BackgroundColor
,
243 &mEfiColors
[Sto
->Mode
->Attribute
>> 4],
244 sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
)
248 Status
= HiiFont
->StringToImage (
250 EFI_HII_IGNORE_IF_NO_GLYPH
| EFI_HII_DIRECT_TO_SCREEN
,
264 if (GLYPH_WIDTH
* GLYPH_HEIGHT
* sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL
) * BufferLen
> LineBufferLen
) {
265 Status
= EFI_INVALID_PARAMETER
;
269 for (Index
= 0; Index
< BufferLen
; Index
++) {
270 StringIndex
= (UINT16
) Index
;
271 Status
= Hii
->GetGlyph (Hii
, UnicodeWeight
, &StringIndex
, (UINT8
**) &Glyph
, &GlyphWidth
, &GlyphStatus
);
272 if (EFI_ERROR (Status
)) {
276 if (Foreground
== NULL
|| Background
== NULL
) {
277 Status
= Hii
->GlyphToBlt (
280 mEfiColors
[Sto
->Mode
->Attribute
& 0x0f],
281 mEfiColors
[Sto
->Mode
->Attribute
>> 4],
285 &LineBuffer
[Index
* GLYPH_WIDTH
]
288 Status
= Hii
->GlyphToBlt (
296 &LineBuffer
[Index
* GLYPH_WIDTH
]
302 // Blt a character to the screen
304 if (GraphicsOutput
!= NULL
) {
305 Status
= GraphicsOutput
->Blt (
313 GLYPH_WIDTH
* BufferLen
,
315 GLYPH_WIDTH
* BufferLen
* sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL
)
318 Status
= UgaDraw
->Blt (
320 (EFI_UGA_PIXEL
*) LineBuffer
,
321 EfiUgaBltBufferToVideo
,
326 GLYPH_WIDTH
* BufferLen
,
328 GLYPH_WIDTH
* BufferLen
* sizeof (EFI_UGA_PIXEL
)
335 #if (EFI_SPECIFICATION_VERSION >= 0x0002000A)
336 EfiLibSafeFreePool (Blt
);
337 EfiLibSafeFreePool (FontInfo
);
339 EfiLibSafeFreePool (LineBuffer
);
341 gBS
->FreePool (Buffer
);
343 if (EFI_ERROR (Status
)) {
355 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL
*ForeGround
, OPTIONAL
356 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL
*BackGround
, OPTIONAL
364 Prints a formatted unicode string to the default console
368 X - X coordinate to start printing
370 Y - Y coordinate to start printing
372 ForeGround - Foreground color
374 BackGround - Background color
378 ... - Print arguments
382 Length of string printed to the console
387 EFI_GRAPHICS_OUTPUT_PROTOCOL
*GraphicsOutput
;
388 EFI_UGA_DRAW_PROTOCOL
*UgaDraw
;
389 EFI_SIMPLE_TEXT_OUT_PROTOCOL
*Sto
;
393 VA_START (Args
, Fmt
);
395 Handle
= gST
->ConsoleOutHandle
;
397 Status
= gBS
->HandleProtocol (
399 &gEfiGraphicsOutputProtocolGuid
,
400 (VOID
**) &GraphicsOutput
404 if (EFI_ERROR (Status
)) {
405 GraphicsOutput
= NULL
;
407 Status
= gBS
->HandleProtocol (
409 &gEfiUgaDrawProtocolGuid
,
413 if (EFI_ERROR (Status
) || (UgaDraw
!= NULL
)) {
419 Status
= gBS
->HandleProtocol (
421 &gEfiSimpleTextOutProtocolGuid
,
425 if (EFI_ERROR (Status
) || (Sto
!= NULL
)) {
429 return _IPrint (GraphicsOutput
, UgaDraw
, Sto
, X
, Y
, ForeGround
, BackGround
, Fmt
, Args
);
437 IN CONST CHAR_W
*Format
,
444 SPrint function to process format and place the results in Buffer.
448 Buffer - Wide char buffer to print the results of the parsing of Format into.
450 BufferSize - Maximum number of characters to put into buffer. Zero means no
453 Format - Format string see file header for more details.
455 ... - Vararg list consumed by processing Format.
459 Number of characters printed.
466 VA_START (Marker
, Format
);
467 Return
= VSPrint (Buffer
, BufferSize
, Format
, Marker
);
476 OUT CHAR_W
*StartOfBuffer
,
478 IN CONST CHAR_W
*FormatString
,
485 VSPrint function to process format and place the results in Buffer. Since a
486 VA_LIST is used this rountine allows the nesting of Vararg routines. Thus
487 this is the main print working routine
491 StartOfBuffer - Unicode buffer to print the results of the parsing of Format into.
493 BufferSize - Maximum number of characters to put into buffer. Zero means
496 FormatString - Unicode format string see file header for more details.
498 Marker - Vararg list consumed by processing Format.
502 Number of characters printed.
507 EFI_PRINT_PROTOCOL
*PrintProtocol
;
509 Status
= gBS
->LocateProtocol (
510 &gEfiPrintProtocolGuid
,
512 (VOID
**) &PrintProtocol
514 if (EFI_ERROR (Status
)) {
517 return PrintProtocol
->VSPrint (