]> git.proxmox.com Git - mirror_edk2.git/blob - OptionRomPkg/Library/FrameBufferBltLib/FrameBufferBltLib.c
5bb3cfbb28c0fa87ec88459e2150081b89d4bbac
[mirror_edk2.git] / OptionRomPkg / Library / FrameBufferBltLib / FrameBufferBltLib.c
1 /** @file
2 FrameBufferBltLib - Library to perform blt operations on a frame buffer.
3
4 Copyright (c) 2007 - 2011, Intel Corporation
5 All rights reserved. This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
9
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12
13 **/
14
15 #include "PiDxe.h"
16 #include <Library/BaseLib.h>
17 #include <Library/BaseMemoryLib.h>
18 #include <Library/BltLib.h>
19 #include <Library/DebugLib.h>
20
21 #if 0
22 #define VDEBUG DEBUG
23 #else
24 #define VDEBUG(x)
25 #endif
26
27 #define MAX_LINE_BUFFER_SIZE (SIZE_4KB * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL))
28
29 UINTN mBltLibColorDepth;
30 UINTN mBltLibWidthInBytes;
31 UINTN mBltLibBytesPerPixel;
32 UINTN mBltLibWidthInPixels;
33 UINTN mBltLibHeight;
34 UINT8 mBltLibLineBuffer[MAX_LINE_BUFFER_SIZE];
35 UINT8 *mBltLibFrameBuffer;
36 EFI_GRAPHICS_PIXEL_FORMAT mPixelFormat;
37 EFI_PIXEL_BITMASK mPixelBitMasks;
38 INTN mPixelShl[4]; // R-G-B-Rsvd
39 INTN mPixelShr[4]; // R-G-B-Rsvd
40
41
42 VOID
43 ConfigurePixelBitMaskFormat (
44 IN EFI_PIXEL_BITMASK *BitMask
45 )
46 {
47 UINTN Loop;
48 UINT32 *Masks;
49 UINT32 MergedMasks;
50
51 MergedMasks = 0;
52 Masks = (UINT32*) BitMask;
53 for (Loop = 0; Loop < 3; Loop++) {
54 ASSERT ((Loop == 3) || (Masks[Loop] != 0));
55 ASSERT ((MergedMasks & Masks[Loop]) == 0);
56 mPixelShl[Loop] = HighBitSet32 (Masks[Loop]) - 23 + (Loop * 8);
57 if (mPixelShl[Loop] < 0) {
58 mPixelShr[Loop] = -mPixelShl[Loop];
59 mPixelShl[Loop] = 0;
60 } else {
61 mPixelShr[Loop] = 0;
62 }
63 MergedMasks = (UINT32) (MergedMasks | Masks[Loop]);
64 DEBUG ((EFI_D_INFO, "%d: shl:%d shr:%d mask:%x\n", Loop, mPixelShl[Loop], mPixelShr[Loop], Masks[Loop]));
65 }
66 MergedMasks = (UINT32) (MergedMasks | Masks[3]);
67
68 mBltLibBytesPerPixel = HighBitSet32 (MergedMasks);
69 ASSERT (mBltLibBytesPerPixel >= 0);
70 mBltLibBytesPerPixel = (mBltLibBytesPerPixel + 7) / 8;
71
72 DEBUG ((EFI_D_INFO, "Bytes per pixel: %d\n", mBltLibBytesPerPixel));
73
74 CopyMem (&mPixelBitMasks, BitMask, sizeof (*BitMask));
75 }
76
77
78 /**
79 Configure the FrameBufferLib instance
80
81 @param[in] FrameBuffer Pointer to the start of the frame buffer
82 @param[in] FrameBufferInfo Describes the frame buffer characteristics
83
84 @retval EFI_INVALID_PARAMETER - Invalid parameter
85 @retval EFI_UNSUPPORTED - The BltLib does not support this configuration
86 @retval EFI_SUCCESS - Blt operation success
87
88 **/
89 EFI_STATUS
90 EFIAPI
91 BltLibConfigure (
92 IN VOID *FrameBuffer,
93 IN EFI_GRAPHICS_OUTPUT_MODE_INFORMATION *FrameBufferInfo
94 )
95 {
96 STATIC EFI_PIXEL_BITMASK RgbPixelMasks =
97 { 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 };
98 STATIC EFI_PIXEL_BITMASK BgrPixelMasks =
99 { 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 };
100
101 switch (FrameBufferInfo->PixelFormat) {
102 case PixelRedGreenBlueReserved8BitPerColor:
103 ConfigurePixelBitMaskFormat (&RgbPixelMasks);
104 break;
105 case PixelBlueGreenRedReserved8BitPerColor:
106 ConfigurePixelBitMaskFormat (&BgrPixelMasks);
107 break;
108 case PixelBitMask:
109 ConfigurePixelBitMaskFormat (&(FrameBufferInfo->PixelInformation));
110 break;
111 case PixelBltOnly:
112 ASSERT (FrameBufferInfo->PixelFormat != PixelBltOnly);
113 return EFI_UNSUPPORTED;
114 default:
115 ASSERT (FALSE);
116 return EFI_INVALID_PARAMETER;
117 }
118 mPixelFormat = FrameBufferInfo->PixelFormat;
119
120 mBltLibFrameBuffer = (UINT8*) FrameBuffer;
121 mBltLibWidthInPixels = (UINTN) FrameBufferInfo->HorizontalResolution;
122 mBltLibHeight = (UINTN) FrameBufferInfo->VerticalResolution;
123 mBltLibWidthInBytes = mBltLibWidthInPixels * mBltLibBytesPerPixel;
124
125 ASSERT (mBltLibWidthInBytes < sizeof (mBltLibLineBuffer));
126
127 return EFI_SUCCESS;
128 }
129
130
131 /**
132 Performs a UEFI Graphics Output Protocol Blt operation.
133
134 @param[in,out] BltBuffer - The data to transfer to screen
135 @param[in] BltOperation - The operation to perform
136 @param[in] SourceX - The X coordinate of the source for BltOperation
137 @param[in] SourceY - The Y coordinate of the source for BltOperation
138 @param[in] DestinationX - The X coordinate of the destination for BltOperation
139 @param[in] DestinationY - The Y coordinate of the destination for BltOperation
140 @param[in] Width - The width of a rectangle in the blt rectangle in pixels
141 @param[in] Height - The height of a rectangle in the blt rectangle in pixels
142 @param[in] Delta - Not used for EfiBltVideoFill and EfiBltVideoToVideo operation.
143 If a Delta of 0 is used, the entire BltBuffer will be operated on.
144 If a subrectangle of the BltBuffer is used, then Delta represents
145 the number of bytes in a row of the BltBuffer.
146
147 @retval EFI_DEVICE_ERROR - A hardware error occured
148 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
149 @retval EFI_SUCCESS - Blt operation success
150
151 **/
152 EFI_STATUS
153 EFIAPI
154 BltLibGopBlt (
155 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer, OPTIONAL
156 IN EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
157 IN UINTN SourceX,
158 IN UINTN SourceY,
159 IN UINTN DestinationX,
160 IN UINTN DestinationY,
161 IN UINTN Width,
162 IN UINTN Height,
163 IN UINTN Delta
164 )
165 {
166 switch (BltOperation) {
167 case EfiBltVideoToBltBuffer:
168 return BltLibVideoToBltBufferEx (
169 BltBuffer,
170 SourceX,
171 SourceY,
172 DestinationX,
173 DestinationY,
174 Width,
175 Height,
176 Delta
177 );
178
179 case EfiBltVideoToVideo:
180 return BltLibVideoToVideo (
181 SourceX,
182 SourceY,
183 DestinationX,
184 DestinationY,
185 Width,
186 Height
187 );
188
189 case EfiBltVideoFill:
190 return BltLibVideoFill (
191 BltBuffer,
192 DestinationX,
193 DestinationY,
194 Width,
195 Height
196 );
197
198 case EfiBltBufferToVideo:
199 return BltLibBufferToVideoEx (
200 BltBuffer,
201 SourceX,
202 SourceY,
203 DestinationX,
204 DestinationY,
205 Width,
206 Height,
207 Delta
208 );
209 default:
210 return EFI_INVALID_PARAMETER;
211 }
212 }
213
214
215 /**
216 Performs a UEFI Graphics Output Protocol Blt Video Fill.
217
218 @param[in] Color Color to fill the region with
219 @param[in] DestinationX X location to start fill operation
220 @param[in] DestinationY Y location to start fill operation
221 @param[in] Width Width (in pixels) to fill
222 @param[in] Height Height to fill
223
224 @retval EFI_DEVICE_ERROR - A hardware error occured
225 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
226 @retval EFI_SUCCESS - The sizes were returned
227
228 **/
229 EFI_STATUS
230 EFIAPI
231 BltLibVideoFill (
232 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Color,
233 IN UINTN DestinationX,
234 IN UINTN DestinationY,
235 IN UINTN Width,
236 IN UINTN Height
237 )
238 {
239 UINTN DstY;
240 VOID *BltMemSrc;
241 VOID *BltMemDst;
242 UINTN X;
243 UINT8 Uint8;
244 UINT32 Uint32;
245 UINT64 WideFill;
246 BOOLEAN UseWideFill;
247 BOOLEAN LineBufferReady;
248 UINTN Offset;
249 UINTN WidthInBytes;
250 UINTN SizeInBytes;
251
252 //
253 // BltBuffer to Video: Source is BltBuffer, destination is Video
254 //
255 if (DestinationY + Height > mBltLibHeight) {
256 DEBUG ((EFI_D_INFO, "VideoFill: Past screen (Y)\n"));
257 return EFI_INVALID_PARAMETER;
258 }
259
260 if (DestinationX + Width > mBltLibWidthInPixels) {
261 DEBUG ((EFI_D_INFO, "VideoFill: Past screen (X)\n"));
262 return EFI_INVALID_PARAMETER;
263 }
264
265 if (Width == 0 || Height == 0) {
266 DEBUG ((EFI_D_INFO, "VideoFill: Width or Height is 0\n"));
267 return EFI_INVALID_PARAMETER;
268 }
269
270 WidthInBytes = Width * mBltLibBytesPerPixel;
271
272 Uint32 = *(UINT32*) Color;
273 WideFill =
274 (UINT32) (
275 (((Uint32 << mPixelShl[0]) >> mPixelShr[0]) & mPixelBitMasks.RedMask) |
276 (((Uint32 << mPixelShl[1]) >> mPixelShr[1]) & mPixelBitMasks.GreenMask) |
277 (((Uint32 << mPixelShl[2]) >> mPixelShr[2]) & mPixelBitMasks.BlueMask)
278 );
279 VDEBUG ((EFI_D_INFO, "VideoFill: color=0x%x, wide-fill=0x%x\n", Uint32, WideFill));
280
281 //
282 // If the size of the pixel data evenly divides the sizeof
283 // WideFill, then a wide fill operation can be used
284 //
285 UseWideFill = TRUE;
286 if ((sizeof (WideFill) % mBltLibBytesPerPixel) == 0) {
287 for (X = mBltLibBytesPerPixel; X < sizeof (WideFill); X++) {
288 ((UINT8*)&WideFill)[X] = ((UINT8*)&WideFill)[X % mBltLibBytesPerPixel];
289 }
290 } else {
291 //
292 // If all the bytes in the pixel are the same value, then use
293 // a wide fill operation.
294 //
295 for (
296 X = 1, Uint8 = ((UINT8*)&WideFill)[0];
297 X < mBltLibBytesPerPixel;
298 X++) {
299 if (Uint8 != ((UINT8*)&WideFill)[X]) {
300 UseWideFill = FALSE;
301 break;
302 }
303 }
304 if (UseWideFill) {
305 SetMem ((VOID*) &WideFill, sizeof (WideFill), Uint8);
306 }
307 }
308
309 if (UseWideFill && (DestinationX == 0) && (Width == mBltLibWidthInPixels)) {
310 VDEBUG ((EFI_D_INFO, "VideoFill (wide, one-shot)\n"));
311 Offset = DestinationY * mBltLibWidthInPixels;
312 Offset = mBltLibBytesPerPixel * Offset;
313 BltMemDst = (VOID*) (mBltLibFrameBuffer + Offset);
314 SizeInBytes = WidthInBytes * Height;
315 if (SizeInBytes >= 8) {
316 SetMem32 (BltMemDst, SizeInBytes & ~3, (UINT32) WideFill);
317 SizeInBytes = SizeInBytes & 3;
318 }
319 if (SizeInBytes > 0) {
320 SetMem (BltMemDst, SizeInBytes, (UINT8)(UINTN) WideFill);
321 }
322 } else {
323 LineBufferReady = FALSE;
324 for (DstY = DestinationY; DstY < (Height + DestinationY); DstY++) {
325 Offset = (DstY * mBltLibWidthInPixels) + DestinationX;
326 Offset = mBltLibBytesPerPixel * Offset;
327 BltMemDst = (VOID*) (mBltLibFrameBuffer + Offset);
328
329 if (UseWideFill && (((UINTN) BltMemDst & 7) == 0)) {
330 VDEBUG ((EFI_D_INFO, "VideoFill (wide)\n"));
331 SizeInBytes = WidthInBytes;
332 if (SizeInBytes >= 8) {
333 SetMem64 (BltMemDst, SizeInBytes & ~7, WideFill);
334 SizeInBytes = SizeInBytes & 7;
335 }
336 if (SizeInBytes > 0) {
337 CopyMem (BltMemDst, (VOID*) &WideFill, SizeInBytes);
338 }
339 } else {
340 VDEBUG ((EFI_D_INFO, "VideoFill (not wide)\n"));
341 if (!LineBufferReady) {
342 CopyMem (mBltLibLineBuffer, &WideFill, mBltLibBytesPerPixel);
343 for (X = 1; X < Width; ) {
344 CopyMem(
345 (mBltLibLineBuffer + (X * mBltLibBytesPerPixel)),
346 mBltLibLineBuffer,
347 MIN (X, Width - X) * mBltLibBytesPerPixel
348 );
349 X = X + MIN (X, Width - X);
350 }
351 BltMemSrc = (VOID *) mBltLibLineBuffer;
352 LineBufferReady = TRUE;
353 }
354 CopyMem (BltMemDst, mBltLibLineBuffer, WidthInBytes);
355 }
356 }
357 }
358
359 return EFI_SUCCESS;
360 }
361
362
363 /**
364 Performs a UEFI Graphics Output Protocol Blt Video to Buffer operation.
365
366 @param[out] BltBuffer Output buffer for pixel color data
367 @param[in] SourceX X location within video
368 @param[in] SourceY Y location within video
369 @param[in] Width Width (in pixels)
370 @param[in] Height Height
371
372 @retval EFI_DEVICE_ERROR - A hardware error occured
373 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
374 @retval EFI_SUCCESS - The sizes were returned
375
376 **/
377 EFI_STATUS
378 EFIAPI
379 BltLibVideoToBltBuffer (
380 OUT EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer,
381 IN UINTN SourceX,
382 IN UINTN SourceY,
383 IN UINTN Width,
384 IN UINTN Height
385 )
386 {
387 return BltLibVideoToBltBufferEx (
388 BltBuffer,
389 SourceX,
390 SourceY,
391 0,
392 0,
393 Width,
394 Height,
395 0
396 );
397 }
398
399
400 /**
401 Performs a UEFI Graphics Output Protocol Blt Video to Buffer operation
402 with extended parameters.
403
404 @param[out] BltBuffer Output buffer for pixel color data
405 @param[in] SourceX X location within video
406 @param[in] SourceY Y location within video
407 @param[in] DestinationX X location within BltBuffer
408 @param[in] DestinationY Y location within BltBuffer
409 @param[in] Width Width (in pixels)
410 @param[in] Height Height
411 @param[in] Delta Number of bytes in a row of BltBuffer
412
413 @retval EFI_DEVICE_ERROR - A hardware error occured
414 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
415 @retval EFI_SUCCESS - The sizes were returned
416
417 **/
418 EFI_STATUS
419 EFIAPI
420 BltLibVideoToBltBufferEx (
421 OUT EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer,
422 IN UINTN SourceX,
423 IN UINTN SourceY,
424 IN UINTN DestinationX,
425 IN UINTN DestinationY,
426 IN UINTN Width,
427 IN UINTN Height,
428 IN UINTN Delta
429 )
430 {
431 UINTN DstY;
432 UINTN SrcY;
433 EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Blt;
434 VOID *BltMemSrc;
435 VOID *BltMemDst;
436 UINTN X;
437 UINT32 Uint32;
438 UINTN Offset;
439 UINTN WidthInBytes;
440
441 //
442 // Video to BltBuffer: Source is Video, destination is BltBuffer
443 //
444 if (SourceY + Height > mBltLibHeight) {
445 return EFI_INVALID_PARAMETER;
446 }
447
448 if (SourceX + Width > mBltLibWidthInPixels) {
449 return EFI_INVALID_PARAMETER;
450 }
451
452 if (Width == 0 || Height == 0) {
453 return EFI_INVALID_PARAMETER;
454 }
455
456 //
457 // If Delta is zero, then the entire BltBuffer is being used, so Delta
458 // is the number of bytes in each row of BltBuffer. Since BltBuffer is Width pixels size,
459 // the number of bytes in each row can be computed.
460 //
461 if (Delta == 0) {
462 Delta = Width * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
463 }
464
465 WidthInBytes = Width * mBltLibBytesPerPixel;
466
467 //
468 // Video to BltBuffer: Source is Video, destination is BltBuffer
469 //
470 for (SrcY = SourceY, DstY = DestinationY; DstY < (Height + DestinationY); SrcY++, DstY++) {
471
472 Offset = (SrcY * mBltLibWidthInPixels) + SourceX;
473 Offset = mBltLibBytesPerPixel * Offset;
474 BltMemSrc = (VOID *) (mBltLibFrameBuffer + Offset);
475
476 if (mPixelFormat == PixelBlueGreenRedReserved8BitPerColor) {
477 BltMemDst =
478 (VOID *) (
479 (UINT8 *) BltBuffer +
480 (DstY * Delta) +
481 (DestinationX * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL))
482 );
483 } else {
484 BltMemDst = (VOID *) mBltLibLineBuffer;
485 }
486
487 CopyMem (BltMemDst, BltMemSrc, WidthInBytes);
488
489 if (mPixelFormat != PixelBlueGreenRedReserved8BitPerColor) {
490 for (X = 0; X < Width; X++) {
491 Blt = (EFI_GRAPHICS_OUTPUT_BLT_PIXEL *) ((UINT8 *) BltBuffer + (DstY * Delta) + (DestinationX + X) * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL));
492 Uint32 = *(UINT32*) (mBltLibLineBuffer + (X * mBltLibBytesPerPixel));
493 *(UINT32*) Blt =
494 (UINT32) (
495 (((Uint32 & mPixelBitMasks.RedMask) >> mPixelShl[0]) << mPixelShr[0]) |
496 (((Uint32 & mPixelBitMasks.GreenMask) >> mPixelShl[1]) << mPixelShr[1]) |
497 (((Uint32 & mPixelBitMasks.BlueMask) >> mPixelShl[2]) << mPixelShr[2])
498 );
499 }
500 }
501 }
502
503 return EFI_SUCCESS;
504 }
505
506
507 /**
508 Performs a UEFI Graphics Output Protocol Blt Buffer to Video operation.
509
510 @param[in] BltBuffer Output buffer for pixel color data
511 @param[in] DestinationX X location within video
512 @param[in] DestinationY Y location within video
513 @param[in] Width Width (in pixels)
514 @param[in] Height Height
515
516 @retval EFI_DEVICE_ERROR - A hardware error occured
517 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
518 @retval EFI_SUCCESS - The sizes were returned
519
520 **/
521 EFI_STATUS
522 EFIAPI
523 BltLibBufferToVideo (
524 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer,
525 IN UINTN DestinationX,
526 IN UINTN DestinationY,
527 IN UINTN Width,
528 IN UINTN Height
529 )
530 {
531 return BltLibBufferToVideoEx (
532 BltBuffer,
533 0,
534 0,
535 DestinationX,
536 DestinationY,
537 Width,
538 Height,
539 0
540 );
541 }
542
543
544 /**
545 Performs a UEFI Graphics Output Protocol Blt Buffer to Video operation
546 with extended parameters.
547
548 @param[in] BltBuffer Output buffer for pixel color data
549 @param[in] SourceX X location within BltBuffer
550 @param[in] SourceY Y location within BltBuffer
551 @param[in] DestinationX X location within video
552 @param[in] DestinationY Y location within video
553 @param[in] Width Width (in pixels)
554 @param[in] Height Height
555 @param[in] Delta Number of bytes in a row of BltBuffer
556
557 @retval EFI_DEVICE_ERROR - A hardware error occured
558 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
559 @retval EFI_SUCCESS - The sizes were returned
560
561 **/
562 EFI_STATUS
563 EFIAPI
564 BltLibBufferToVideoEx (
565 IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BltBuffer,
566 IN UINTN SourceX,
567 IN UINTN SourceY,
568 IN UINTN DestinationX,
569 IN UINTN DestinationY,
570 IN UINTN Width,
571 IN UINTN Height,
572 IN UINTN Delta
573 )
574 {
575 UINTN DstY;
576 UINTN SrcY;
577 EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Blt;
578 VOID *BltMemSrc;
579 VOID *BltMemDst;
580 UINTN X;
581 UINT32 Uint32;
582 UINTN Offset;
583 UINTN WidthInBytes;
584
585 //
586 // BltBuffer to Video: Source is BltBuffer, destination is Video
587 //
588 if (DestinationY + Height > mBltLibHeight) {
589 return EFI_INVALID_PARAMETER;
590 }
591
592 if (DestinationX + Width > mBltLibWidthInPixels) {
593 return EFI_INVALID_PARAMETER;
594 }
595
596 if (Width == 0 || Height == 0) {
597 return EFI_INVALID_PARAMETER;
598 }
599
600 //
601 // If Delta is zero, then the entire BltBuffer is being used, so Delta
602 // is the number of bytes in each row of BltBuffer. Since BltBuffer is Width pixels size,
603 // the number of bytes in each row can be computed.
604 //
605 if (Delta == 0) {
606 Delta = Width * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
607 }
608
609 WidthInBytes = Width * mBltLibBytesPerPixel;
610
611 for (SrcY = SourceY, DstY = DestinationY; SrcY < (Height + SourceY); SrcY++, DstY++) {
612
613 Offset = (DstY * mBltLibWidthInPixels) + DestinationX;
614 Offset = mBltLibBytesPerPixel * Offset;
615 BltMemDst = (VOID*) (mBltLibFrameBuffer + Offset);
616
617 if (mPixelFormat == PixelBlueGreenRedReserved8BitPerColor) {
618 BltMemSrc = (VOID *) ((UINT8 *) BltBuffer + (SrcY * Delta));
619 } else {
620 for (X = 0; X < Width; X++) {
621 Blt =
622 (EFI_GRAPHICS_OUTPUT_BLT_PIXEL *) (
623 (UINT8 *) BltBuffer +
624 (SrcY * Delta) +
625 ((SourceX + X) * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL))
626 );
627 Uint32 = *(UINT32*) Blt;
628 *(UINT32*) (mBltLibLineBuffer + (X * mBltLibBytesPerPixel)) =
629 (UINT32) (
630 (((Uint32 << mPixelShl[0]) >> mPixelShr[0]) & mPixelBitMasks.RedMask) |
631 (((Uint32 << mPixelShl[1]) >> mPixelShr[1]) & mPixelBitMasks.GreenMask) |
632 (((Uint32 << mPixelShl[2]) >> mPixelShr[2]) & mPixelBitMasks.BlueMask)
633 );
634 }
635 BltMemSrc = (VOID *) mBltLibLineBuffer;
636 }
637
638 CopyMem (BltMemDst, BltMemSrc, WidthInBytes);
639 }
640
641 return EFI_SUCCESS;
642 }
643
644
645 /**
646 Performs a UEFI Graphics Output Protocol Blt Video to Video operation
647
648 @param[in] SourceX X location within video
649 @param[in] SourceY Y location within video
650 @param[in] DestinationX X location within video
651 @param[in] DestinationY Y location within video
652 @param[in] Width Width (in pixels)
653 @param[in] Height Height
654
655 @retval EFI_DEVICE_ERROR - A hardware error occured
656 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
657 @retval EFI_SUCCESS - The sizes were returned
658
659 **/
660 EFI_STATUS
661 EFIAPI
662 BltLibVideoToVideo (
663 IN UINTN SourceX,
664 IN UINTN SourceY,
665 IN UINTN DestinationX,
666 IN UINTN DestinationY,
667 IN UINTN Width,
668 IN UINTN Height
669 )
670 {
671 VOID *BltMemSrc;
672 VOID *BltMemDst;
673 UINTN Offset;
674 UINTN WidthInBytes;
675 INTN LineStride;
676
677 //
678 // Video to Video: Source is Video, destination is Video
679 //
680 if (SourceY + Height > mBltLibHeight) {
681 return EFI_INVALID_PARAMETER;
682 }
683
684 if (SourceX + Width > mBltLibWidthInPixels) {
685 return EFI_INVALID_PARAMETER;
686 }
687
688 if (DestinationY + Height > mBltLibHeight) {
689 return EFI_INVALID_PARAMETER;
690 }
691
692 if (DestinationX + Width > mBltLibWidthInPixels) {
693 return EFI_INVALID_PARAMETER;
694 }
695
696 if (Width == 0 || Height == 0) {
697 return EFI_INVALID_PARAMETER;
698 }
699
700 WidthInBytes = Width * mBltLibBytesPerPixel;
701
702 Offset = (SourceY * mBltLibWidthInPixels) + SourceX;
703 Offset = mBltLibBytesPerPixel * Offset;
704 BltMemSrc = (VOID *) (mBltLibFrameBuffer + Offset);
705
706 Offset = (DestinationY * mBltLibWidthInPixels) + DestinationX;
707 Offset = mBltLibBytesPerPixel * Offset;
708 BltMemDst = (VOID *) (mBltLibFrameBuffer + Offset);
709
710 LineStride = mBltLibWidthInBytes;
711 if ((UINTN) BltMemDst > (UINTN) BltMemSrc) {
712 LineStride = -LineStride;
713 }
714
715 while (Height > 0) {
716 CopyMem (BltMemDst, BltMemSrc, WidthInBytes);
717
718 BltMemSrc = (VOID*) ((UINT8*) BltMemSrc + LineStride);
719 BltMemDst = (VOID*) ((UINT8*) BltMemDst + LineStride);
720 Height--;
721 }
722
723 return EFI_SUCCESS;
724 }
725
726
727 /**
728 Returns the sizes related to the video device
729
730 @param[out] Width Width (in pixels)
731 @param[out] Height Height (in pixels)
732
733 @retval EFI_INVALID_PARAMETER - Invalid parameter passed in
734 @retval EFI_SUCCESS - The sizes were returned
735
736 **/
737 EFI_STATUS
738 EFIAPI
739 BltLibGetSizes (
740 OUT UINTN *Width, OPTIONAL
741 OUT UINTN *Height OPTIONAL
742 )
743 {
744 if (Width != NULL) {
745 *Width = mBltLibWidthInPixels;
746 }
747 if (Height != NULL) {
748 *Height = mBltLibHeight;
749 }
750
751 return EFI_SUCCESS;
752 }
753