1 /************************************************************************** 2 * 3 * Copyright 2009-2010 Vmware, Inc. 4 * All Rights Reserved. 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the 8 * "Software"), to deal in the Software without restriction, including 9 * without limitation the rights to use, copy, modify, merge, publish, 10 * distribute, sub license, and/or sell copies of the Software, and to 11 * permit persons to whom the Software is furnished to do so, subject to 12 * the following conditions: 13 * 14 * The above copyright notice and this permission notice (including the 15 * next paragraph) shall be included in all copies or substantial portions 16 * of the Software. 17 * 18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 21 * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR 22 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25 * 26 **************************************************************************/ 27 28 29 #ifndef U_FORMAT_H 30 #define U_FORMAT_H 31 32 33 #include "pipe/p_format.h" 34 #include "util/u_debug.h" 35 36 #ifdef __cplusplus 37 extern "C" { 38 #endif 39 40 41 /** 42 * Describe how to pack/unpack pixels into/from the prescribed format. 43 * 44 * XXX: This could be renamed to something like util_format_pack, or broke down 45 * in flags inside util_format_block that said exactly what we want. 46 */ 47 enum util_format_layout { 48 /** 49 * Formats with util_format_block::width == util_format_block::height == 1 50 * that can be described as an ordinary data structure. 51 */ 52 UTIL_FORMAT_LAYOUT_PLAIN = 0, 53 54 /** 55 * Formats with sub-sampled channels. 56 * 57 * This is for formats like YVYU where there is less than one sample per 58 * pixel. 59 */ 60 UTIL_FORMAT_LAYOUT_SUBSAMPLED = 3, 61 62 /** 63 * S3 Texture Compression formats. 64 */ 65 UTIL_FORMAT_LAYOUT_S3TC = 4, 66 67 /** 68 * Red-Green Texture Compression formats. 69 */ 70 UTIL_FORMAT_LAYOUT_RGTC = 5, 71 72 /** 73 * Ericsson Texture Compression 74 */ 75 UTIL_FORMAT_LAYOUT_ETC = 6, 76 77 /** 78 * Everything else that doesn't fit in any of the above layouts. 79 */ 80 UTIL_FORMAT_LAYOUT_OTHER = 7 81 }; 82 83 84 struct util_format_block 85 { 86 /** Block width in pixels */ 87 unsigned width; 88 89 /** Block height in pixels */ 90 unsigned height; 91 92 /** Block size in bits */ 93 unsigned bits; 94 }; 95 96 97 enum util_format_type { 98 UTIL_FORMAT_TYPE_VOID = 0, 99 UTIL_FORMAT_TYPE_UNSIGNED = 1, 100 UTIL_FORMAT_TYPE_SIGNED = 2, 101 UTIL_FORMAT_TYPE_FIXED = 3, 102 UTIL_FORMAT_TYPE_FLOAT = 4 103 }; 104 105 106 enum util_format_swizzle { 107 UTIL_FORMAT_SWIZZLE_X = 0, 108 UTIL_FORMAT_SWIZZLE_Y = 1, 109 UTIL_FORMAT_SWIZZLE_Z = 2, 110 UTIL_FORMAT_SWIZZLE_W = 3, 111 UTIL_FORMAT_SWIZZLE_0 = 4, 112 UTIL_FORMAT_SWIZZLE_1 = 5, 113 UTIL_FORMAT_SWIZZLE_NONE = 6, 114 UTIL_FORMAT_SWIZZLE_MAX = 7 /**< Number of enums counter (must be last) */ 115 }; 116 117 118 enum util_format_colorspace { 119 UTIL_FORMAT_COLORSPACE_RGB = 0, 120 UTIL_FORMAT_COLORSPACE_SRGB = 1, 121 UTIL_FORMAT_COLORSPACE_YUV = 2, 122 UTIL_FORMAT_COLORSPACE_ZS = 3 123 }; 124 125 126 struct util_format_channel_description 127 { 128 unsigned type:5; /**< UTIL_FORMAT_TYPE_x */ 129 unsigned normalized:1; 130 unsigned pure_integer:1; 131 unsigned size:9; /**< bits per channel */ 132 }; 133 134 135 struct util_format_description 136 { 137 enum pipe_format format; 138 139 const char *name; 140 141 /** 142 * Short name, striped of the prefix, lower case. 143 */ 144 const char *short_name; 145 146 /** 147 * Pixel block dimensions. 148 */ 149 struct util_format_block block; 150 151 enum util_format_layout layout; 152 153 /** 154 * The number of channels. 155 */ 156 unsigned nr_channels:3; 157 158 /** 159 * Whether all channels have the same number of (whole) bytes. 160 */ 161 unsigned is_array:1; 162 163 /** 164 * Whether the pixel format can be described as a bitfield structure. 165 * 166 * In particular: 167 * - pixel depth must be 8, 16, or 32 bits; 168 * - all channels must be unsigned, signed, or void 169 */ 170 unsigned is_bitmask:1; 171 172 /** 173 * Whether channels have mixed types (ignoring UTIL_FORMAT_TYPE_VOID). 174 */ 175 unsigned is_mixed:1; 176 177 /** 178 * Input channel description. 179 * 180 * Only valid for UTIL_FORMAT_LAYOUT_PLAIN formats. 181 */ 182 struct util_format_channel_description channel[4]; 183 184 /** 185 * Output channel swizzle. 186 * 187 * The order is either: 188 * - RGBA 189 * - YUV(A) 190 * - ZS 191 * depending on the colorspace. 192 */ 193 unsigned char swizzle[4]; 194 195 /** 196 * Colorspace transformation. 197 */ 198 enum util_format_colorspace colorspace; 199 200 /** 201 * Unpack pixel blocks to R8G8B8A8_UNORM. 202 * Note: strides are in bytes. 203 * 204 * Only defined for non-depth-stencil formats. 205 */ 206 void 207 (*unpack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, 208 const uint8_t *src, unsigned src_stride, 209 unsigned width, unsigned height); 210 211 /** 212 * Pack pixel blocks from R8G8B8A8_UNORM. 213 * Note: strides are in bytes. 214 * 215 * Only defined for non-depth-stencil formats. 216 */ 217 void 218 (*pack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, 219 const uint8_t *src, unsigned src_stride, 220 unsigned width, unsigned height); 221 222 /** 223 * Fetch a single pixel (i, j) from a block. 224 * 225 * XXX: Only defined for a very few select formats. 226 */ 227 void 228 (*fetch_rgba_8unorm)(uint8_t *dst, 229 const uint8_t *src, 230 unsigned i, unsigned j); 231 232 /** 233 * Unpack pixel blocks to R32G32B32A32_FLOAT. 234 * Note: strides are in bytes. 235 * 236 * Only defined for non-depth-stencil formats. 237 */ 238 void 239 (*unpack_rgba_float)(float *dst, unsigned dst_stride, 240 const uint8_t *src, unsigned src_stride, 241 unsigned width, unsigned height); 242 243 /** 244 * Pack pixel blocks from R32G32B32A32_FLOAT. 245 * Note: strides are in bytes. 246 * 247 * Only defined for non-depth-stencil formats. 248 */ 249 void 250 (*pack_rgba_float)(uint8_t *dst, unsigned dst_stride, 251 const float *src, unsigned src_stride, 252 unsigned width, unsigned height); 253 254 /** 255 * Fetch a single pixel (i, j) from a block. 256 * 257 * Only defined for non-depth-stencil and non-integer formats. 258 */ 259 void 260 (*fetch_rgba_float)(float *dst, 261 const uint8_t *src, 262 unsigned i, unsigned j); 263 264 /** 265 * Unpack pixels to Z32_UNORM. 266 * Note: strides are in bytes. 267 * 268 * Only defined for depth formats. 269 */ 270 void 271 (*unpack_z_32unorm)(uint32_t *dst, unsigned dst_stride, 272 const uint8_t *src, unsigned src_stride, 273 unsigned width, unsigned height); 274 275 /** 276 * Pack pixels from Z32_FLOAT. 277 * Note: strides are in bytes. 278 * 279 * Only defined for depth formats. 280 */ 281 void 282 (*pack_z_32unorm)(uint8_t *dst, unsigned dst_stride, 283 const uint32_t *src, unsigned src_stride, 284 unsigned width, unsigned height); 285 286 /** 287 * Unpack pixels to Z32_FLOAT. 288 * Note: strides are in bytes. 289 * 290 * Only defined for depth formats. 291 */ 292 void 293 (*unpack_z_float)(float *dst, unsigned dst_stride, 294 const uint8_t *src, unsigned src_stride, 295 unsigned width, unsigned height); 296 297 /** 298 * Pack pixels from Z32_FLOAT. 299 * Note: strides are in bytes. 300 * 301 * Only defined for depth formats. 302 */ 303 void 304 (*pack_z_float)(uint8_t *dst, unsigned dst_stride, 305 const float *src, unsigned src_stride, 306 unsigned width, unsigned height); 307 308 /** 309 * Unpack pixels to S8_UINT. 310 * Note: strides are in bytes. 311 * 312 * Only defined for stencil formats. 313 */ 314 void 315 (*unpack_s_8uint)(uint8_t *dst, unsigned dst_stride, 316 const uint8_t *src, unsigned src_stride, 317 unsigned width, unsigned height); 318 319 /** 320 * Pack pixels from S8_UINT. 321 * Note: strides are in bytes. 322 * 323 * Only defined for stencil formats. 324 */ 325 void 326 (*pack_s_8uint)(uint8_t *dst, unsigned dst_stride, 327 const uint8_t *src, unsigned src_stride, 328 unsigned width, unsigned height); 329 330 /** 331 * Unpack pixel blocks to R32G32B32A32_UINT. 332 * Note: strides are in bytes. 333 * 334 * Only defined for INT formats. 335 */ 336 void 337 (*unpack_rgba_uint)(unsigned *dst, unsigned dst_stride, 338 const uint8_t *src, unsigned src_stride, 339 unsigned width, unsigned height); 340 341 void 342 (*pack_rgba_uint)(uint8_t *dst, unsigned dst_stride, 343 const unsigned *src, unsigned src_stride, 344 unsigned width, unsigned height); 345 346 /** 347 * Unpack pixel blocks to R32G32B32A32_SINT. 348 * Note: strides are in bytes. 349 * 350 * Only defined for INT formats. 351 */ 352 void 353 (*unpack_rgba_sint)(signed *dst, unsigned dst_stride, 354 const uint8_t *src, unsigned src_stride, 355 unsigned width, unsigned height); 356 357 void 358 (*pack_rgba_sint)(uint8_t *dst, unsigned dst_stride, 359 const int *src, unsigned src_stride, 360 unsigned width, unsigned height); 361 362 /** 363 * Fetch a single pixel (i, j) from a block. 364 * 365 * Only defined for unsigned (pure) integer formats. 366 */ 367 void 368 (*fetch_rgba_uint)(uint32_t *dst, 369 const uint8_t *src, 370 unsigned i, unsigned j); 371 372 /** 373 * Fetch a single pixel (i, j) from a block. 374 * 375 * Only defined for signed (pure) integer formats. 376 */ 377 void 378 (*fetch_rgba_sint)(int32_t *dst, 379 const uint8_t *src, 380 unsigned i, unsigned j); 381 }; 382 383 384 extern const struct util_format_description 385 util_format_description_table[]; 386 387 388 const struct util_format_description * 389 util_format_description(enum pipe_format format); 390 391 392 /* 393 * Format query functions. 394 */ 395 396 static INLINE const char * 397 util_format_name(enum pipe_format format) 398 { 399 const struct util_format_description *desc = util_format_description(format); 400 401 assert(desc); 402 if (!desc) { 403 return "PIPE_FORMAT_???"; 404 } 405 406 return desc->name; 407 } 408 409 static INLINE const char * 410 util_format_short_name(enum pipe_format format) 411 { 412 const struct util_format_description *desc = util_format_description(format); 413 414 assert(desc); 415 if (!desc) { 416 return "???"; 417 } 418 419 return desc->short_name; 420 } 421 422 /** 423 * Whether this format is plain, see UTIL_FORMAT_LAYOUT_PLAIN for more info. 424 */ 425 static INLINE boolean 426 util_format_is_plain(enum pipe_format format) 427 { 428 const struct util_format_description *desc = util_format_description(format); 429 430 if (!format) { 431 return FALSE; 432 } 433 434 return desc->layout == UTIL_FORMAT_LAYOUT_PLAIN ? TRUE : FALSE; 435 } 436 437 static INLINE boolean 438 util_format_is_compressed(enum pipe_format format) 439 { 440 const struct util_format_description *desc = util_format_description(format); 441 442 assert(desc); 443 if (!desc) { 444 return FALSE; 445 } 446 447 switch (desc->layout) { 448 case UTIL_FORMAT_LAYOUT_S3TC: 449 case UTIL_FORMAT_LAYOUT_RGTC: 450 /* XXX add other formats in the future */ 451 return TRUE; 452 default: 453 return FALSE; 454 } 455 } 456 457 static INLINE boolean 458 util_format_is_s3tc(enum pipe_format format) 459 { 460 const struct util_format_description *desc = util_format_description(format); 461 462 assert(desc); 463 if (!desc) { 464 return FALSE; 465 } 466 467 return desc->layout == UTIL_FORMAT_LAYOUT_S3TC ? TRUE : FALSE; 468 } 469 470 static INLINE boolean 471 util_format_is_srgb(enum pipe_format format) 472 { 473 const struct util_format_description *desc = util_format_description(format); 474 return desc->colorspace == UTIL_FORMAT_COLORSPACE_SRGB; 475 } 476 477 static INLINE boolean 478 util_format_has_depth(const struct util_format_description *desc) 479 { 480 return desc->colorspace == UTIL_FORMAT_COLORSPACE_ZS && 481 desc->swizzle[0] != UTIL_FORMAT_SWIZZLE_NONE; 482 } 483 484 static INLINE boolean 485 util_format_has_stencil(const struct util_format_description *desc) 486 { 487 return desc->colorspace == UTIL_FORMAT_COLORSPACE_ZS && 488 desc->swizzle[1] != UTIL_FORMAT_SWIZZLE_NONE; 489 } 490 491 static INLINE boolean 492 util_format_is_depth_or_stencil(enum pipe_format format) 493 { 494 const struct util_format_description *desc = util_format_description(format); 495 496 assert(desc); 497 if (!desc) { 498 return FALSE; 499 } 500 501 return util_format_has_depth(desc) || 502 util_format_has_stencil(desc); 503 } 504 505 static INLINE boolean 506 util_format_is_depth_and_stencil(enum pipe_format format) 507 { 508 const struct util_format_description *desc = util_format_description(format); 509 510 assert(desc); 511 if (!desc) { 512 return FALSE; 513 } 514 515 return util_format_has_depth(desc) && 516 util_format_has_stencil(desc); 517 } 518 519 520 /** 521 * Give the RGBA colormask of the channels that can be represented in this 522 * format. 523 * 524 * That is, the channels whose values are preserved. 525 */ 526 static INLINE unsigned 527 util_format_colormask(const struct util_format_description *desc) 528 { 529 unsigned colormask; 530 unsigned chan; 531 532 switch (desc->colorspace) { 533 case UTIL_FORMAT_COLORSPACE_RGB: 534 case UTIL_FORMAT_COLORSPACE_SRGB: 535 case UTIL_FORMAT_COLORSPACE_YUV: 536 colormask = 0; 537 for (chan = 0; chan < 4; ++chan) { 538 if (desc->swizzle[chan] < 4) { 539 colormask |= (1 << chan); 540 } 541 } 542 return colormask; 543 case UTIL_FORMAT_COLORSPACE_ZS: 544 return 0; 545 default: 546 assert(0); 547 return 0; 548 } 549 } 550 551 552 /** 553 * Checks if color mask covers every channel for the specified format 554 * 555 * @param desc a format description to check colormask with 556 * @param colormask a bit mask for channels, matches format of PIPE_MASK_RGBA 557 */ 558 static INLINE boolean 559 util_format_colormask_full(const struct util_format_description *desc, unsigned colormask) 560 { 561 return (~colormask & util_format_colormask(desc)) == 0; 562 } 563 564 565 boolean 566 util_format_is_float(enum pipe_format format); 567 568 569 boolean 570 util_format_is_rgb_no_alpha(enum pipe_format format); 571 572 573 boolean 574 util_format_is_luminance(enum pipe_format format); 575 576 577 boolean 578 util_format_is_luminance_alpha(enum pipe_format format); 579 580 581 boolean 582 util_format_is_intensity(enum pipe_format format); 583 584 boolean 585 util_format_is_pure_integer(enum pipe_format format); 586 587 boolean 588 util_format_is_pure_sint(enum pipe_format format); 589 590 boolean 591 util_format_is_pure_uint(enum pipe_format format); 592 593 /** 594 * Whether the format is a simple array format where all channels 595 * are of the same type and can be loaded from memory as a vector 596 */ 597 boolean 598 util_format_is_array(const struct util_format_description *desc); 599 600 /** 601 * Check if the src format can be blitted to the destination format with 602 * a simple memcpy. For example, blitting from RGBA to RGBx is OK, but not 603 * the reverse. 604 */ 605 boolean 606 util_is_format_compatible(const struct util_format_description *src_desc, 607 const struct util_format_description *dst_desc); 608 609 /** 610 * Whether the format is supported by Gallium for the given bindings. 611 * This covers S3TC textures and floating-point render targets. 612 */ 613 boolean 614 util_format_is_supported(enum pipe_format format, unsigned bind); 615 616 /** 617 * Whether this format is a rgab8 variant. 618 * 619 * That is, any format that matches the 620 * 621 * PIPE_FORMAT_?8?8?8?8_UNORM 622 */ 623 static INLINE boolean 624 util_format_is_rgba8_variant(const struct util_format_description *desc) 625 { 626 unsigned chan; 627 628 if(desc->block.width != 1 || 629 desc->block.height != 1 || 630 desc->block.bits != 32) 631 return FALSE; 632 633 for(chan = 0; chan < 4; ++chan) { 634 if(desc->channel[chan].type != UTIL_FORMAT_TYPE_UNSIGNED && 635 desc->channel[chan].type != UTIL_FORMAT_TYPE_VOID) 636 return FALSE; 637 if(desc->channel[chan].size != 8) 638 return FALSE; 639 } 640 641 return TRUE; 642 } 643 644 645 /** 646 * Return total bits needed for the pixel format per block. 647 */ 648 static INLINE uint 649 util_format_get_blocksizebits(enum pipe_format format) 650 { 651 const struct util_format_description *desc = util_format_description(format); 652 653 assert(desc); 654 if (!desc) { 655 return 0; 656 } 657 658 return desc->block.bits; 659 } 660 661 /** 662 * Return bytes per block (not pixel) for the given format. 663 */ 664 static INLINE uint 665 util_format_get_blocksize(enum pipe_format format) 666 { 667 uint bits = util_format_get_blocksizebits(format); 668 669 assert(bits % 8 == 0); 670 671 return bits / 8; 672 } 673 674 static INLINE uint 675 util_format_get_blockwidth(enum pipe_format format) 676 { 677 const struct util_format_description *desc = util_format_description(format); 678 679 assert(desc); 680 if (!desc) { 681 return 1; 682 } 683 684 return desc->block.width; 685 } 686 687 static INLINE uint 688 util_format_get_blockheight(enum pipe_format format) 689 { 690 const struct util_format_description *desc = util_format_description(format); 691 692 assert(desc); 693 if (!desc) { 694 return 1; 695 } 696 697 return desc->block.height; 698 } 699 700 static INLINE unsigned 701 util_format_get_nblocksx(enum pipe_format format, 702 unsigned x) 703 { 704 unsigned blockwidth = util_format_get_blockwidth(format); 705 return (x + blockwidth - 1) / blockwidth; 706 } 707 708 static INLINE unsigned 709 util_format_get_nblocksy(enum pipe_format format, 710 unsigned y) 711 { 712 unsigned blockheight = util_format_get_blockheight(format); 713 return (y + blockheight - 1) / blockheight; 714 } 715 716 static INLINE unsigned 717 util_format_get_nblocks(enum pipe_format format, 718 unsigned width, 719 unsigned height) 720 { 721 return util_format_get_nblocksx(format, width) * util_format_get_nblocksy(format, height); 722 } 723 724 static INLINE size_t 725 util_format_get_stride(enum pipe_format format, 726 unsigned width) 727 { 728 return util_format_get_nblocksx(format, width) * util_format_get_blocksize(format); 729 } 730 731 static INLINE size_t 732 util_format_get_2d_size(enum pipe_format format, 733 size_t stride, 734 unsigned height) 735 { 736 return util_format_get_nblocksy(format, height) * stride; 737 } 738 739 static INLINE uint 740 util_format_get_component_bits(enum pipe_format format, 741 enum util_format_colorspace colorspace, 742 uint component) 743 { 744 const struct util_format_description *desc = util_format_description(format); 745 enum util_format_colorspace desc_colorspace; 746 747 assert(format); 748 if (!format) { 749 return 0; 750 } 751 752 assert(component < 4); 753 754 /* Treat RGB and SRGB as equivalent. */ 755 if (colorspace == UTIL_FORMAT_COLORSPACE_SRGB) { 756 colorspace = UTIL_FORMAT_COLORSPACE_RGB; 757 } 758 if (desc->colorspace == UTIL_FORMAT_COLORSPACE_SRGB) { 759 desc_colorspace = UTIL_FORMAT_COLORSPACE_RGB; 760 } else { 761 desc_colorspace = desc->colorspace; 762 } 763 764 if (desc_colorspace != colorspace) { 765 return 0; 766 } 767 768 switch (desc->swizzle[component]) { 769 case UTIL_FORMAT_SWIZZLE_X: 770 return desc->channel[0].size; 771 case UTIL_FORMAT_SWIZZLE_Y: 772 return desc->channel[1].size; 773 case UTIL_FORMAT_SWIZZLE_Z: 774 return desc->channel[2].size; 775 case UTIL_FORMAT_SWIZZLE_W: 776 return desc->channel[3].size; 777 default: 778 return 0; 779 } 780 } 781 782 static INLINE boolean 783 util_format_has_alpha(enum pipe_format format) 784 { 785 const struct util_format_description *desc = util_format_description(format); 786 787 assert(format); 788 if (!format) { 789 return FALSE; 790 } 791 792 switch (desc->colorspace) { 793 case UTIL_FORMAT_COLORSPACE_RGB: 794 case UTIL_FORMAT_COLORSPACE_SRGB: 795 return desc->swizzle[3] != UTIL_FORMAT_SWIZZLE_1; 796 case UTIL_FORMAT_COLORSPACE_YUV: 797 return FALSE; 798 case UTIL_FORMAT_COLORSPACE_ZS: 799 return FALSE; 800 default: 801 assert(0); 802 return FALSE; 803 } 804 } 805 806 /** 807 * Given a linear RGB colorspace format, return the corresponding SRGB 808 * format, or PIPE_FORMAT_NONE if none. 809 */ 810 static INLINE enum pipe_format 811 util_format_srgb(enum pipe_format format) 812 { 813 switch (format) { 814 case PIPE_FORMAT_L8_UNORM: 815 return PIPE_FORMAT_L8_SRGB; 816 case PIPE_FORMAT_L8A8_UNORM: 817 return PIPE_FORMAT_L8A8_SRGB; 818 case PIPE_FORMAT_R8G8B8_UNORM: 819 return PIPE_FORMAT_R8G8B8_SRGB; 820 case PIPE_FORMAT_A8B8G8R8_UNORM: 821 return PIPE_FORMAT_A8B8G8R8_SRGB; 822 case PIPE_FORMAT_X8B8G8R8_UNORM: 823 return PIPE_FORMAT_X8B8G8R8_SRGB; 824 case PIPE_FORMAT_B8G8R8A8_UNORM: 825 return PIPE_FORMAT_B8G8R8A8_SRGB; 826 case PIPE_FORMAT_B8G8R8X8_UNORM: 827 return PIPE_FORMAT_B8G8R8X8_SRGB; 828 case PIPE_FORMAT_A8R8G8B8_UNORM: 829 return PIPE_FORMAT_A8R8G8B8_SRGB; 830 case PIPE_FORMAT_X8R8G8B8_UNORM: 831 return PIPE_FORMAT_X8R8G8B8_SRGB; 832 case PIPE_FORMAT_DXT1_RGB: 833 return PIPE_FORMAT_DXT1_SRGB; 834 case PIPE_FORMAT_DXT1_RGBA: 835 return PIPE_FORMAT_DXT1_SRGBA; 836 case PIPE_FORMAT_DXT3_RGBA: 837 return PIPE_FORMAT_DXT3_SRGBA; 838 case PIPE_FORMAT_DXT5_RGBA: 839 return PIPE_FORMAT_DXT5_SRGBA; 840 default: 841 return PIPE_FORMAT_NONE; 842 } 843 } 844 845 /** 846 * Given an sRGB format, return the corresponding linear colorspace format. 847 * For non sRGB formats, return the format unchanged. 848 */ 849 static INLINE enum pipe_format 850 util_format_linear(enum pipe_format format) 851 { 852 switch (format) { 853 case PIPE_FORMAT_L8_SRGB: 854 return PIPE_FORMAT_L8_UNORM; 855 case PIPE_FORMAT_L8A8_SRGB: 856 return PIPE_FORMAT_L8A8_UNORM; 857 case PIPE_FORMAT_R8G8B8_SRGB: 858 return PIPE_FORMAT_R8G8B8_UNORM; 859 case PIPE_FORMAT_A8B8G8R8_SRGB: 860 return PIPE_FORMAT_A8B8G8R8_UNORM; 861 case PIPE_FORMAT_X8B8G8R8_SRGB: 862 return PIPE_FORMAT_X8B8G8R8_UNORM; 863 case PIPE_FORMAT_B8G8R8A8_SRGB: 864 return PIPE_FORMAT_B8G8R8A8_UNORM; 865 case PIPE_FORMAT_B8G8R8X8_SRGB: 866 return PIPE_FORMAT_B8G8R8X8_UNORM; 867 case PIPE_FORMAT_A8R8G8B8_SRGB: 868 return PIPE_FORMAT_A8R8G8B8_UNORM; 869 case PIPE_FORMAT_X8R8G8B8_SRGB: 870 return PIPE_FORMAT_X8R8G8B8_UNORM; 871 case PIPE_FORMAT_DXT1_SRGB: 872 return PIPE_FORMAT_DXT1_RGB; 873 case PIPE_FORMAT_DXT1_SRGBA: 874 return PIPE_FORMAT_DXT1_RGBA; 875 case PIPE_FORMAT_DXT3_SRGBA: 876 return PIPE_FORMAT_DXT3_RGBA; 877 case PIPE_FORMAT_DXT5_SRGBA: 878 return PIPE_FORMAT_DXT5_RGBA; 879 default: 880 return format; 881 } 882 } 883 884 /** 885 * Given a depth-stencil format, return the corresponding stencil-only format. 886 * For stencil-only formats, return the format unchanged. 887 */ 888 static INLINE enum pipe_format 889 util_format_stencil_only(enum pipe_format format) 890 { 891 switch (format) { 892 /* mask out the depth component */ 893 case PIPE_FORMAT_Z24_UNORM_S8_UINT: 894 return PIPE_FORMAT_X24S8_UINT; 895 case PIPE_FORMAT_S8_UINT_Z24_UNORM: 896 return PIPE_FORMAT_S8X24_UINT; 897 case PIPE_FORMAT_Z32_FLOAT_S8X24_UINT: 898 return PIPE_FORMAT_X32_S8X24_UINT; 899 900 /* stencil only formats */ 901 case PIPE_FORMAT_X24S8_UINT: 902 case PIPE_FORMAT_S8X24_UINT: 903 case PIPE_FORMAT_X32_S8X24_UINT: 904 case PIPE_FORMAT_S8_UINT: 905 return format; 906 907 default: 908 assert(0); 909 return PIPE_FORMAT_NONE; 910 } 911 } 912 913 /** 914 * Return the number of components stored. 915 * Formats with block size != 1x1 will always have 1 component (the block). 916 */ 917 static INLINE unsigned 918 util_format_get_nr_components(enum pipe_format format) 919 { 920 const struct util_format_description *desc = util_format_description(format); 921 return desc->nr_channels; 922 } 923 924 /** 925 * Return the index of the first non-void channel 926 * -1 if no non-void channels 927 */ 928 static INLINE int 929 util_format_get_first_non_void_channel(enum pipe_format format) 930 { 931 const struct util_format_description *desc = util_format_description(format); 932 int i; 933 934 for (i = 0; i < 4; i++) 935 if (desc->channel[i].type != UTIL_FORMAT_TYPE_VOID) 936 break; 937 938 if (i == 4) 939 return -1; 940 941 return i; 942 } 943 944 /* 945 * Format access functions. 946 */ 947 948 void 949 util_format_read_4f(enum pipe_format format, 950 float *dst, unsigned dst_stride, 951 const void *src, unsigned src_stride, 952 unsigned x, unsigned y, unsigned w, unsigned h); 953 954 void 955 util_format_write_4f(enum pipe_format format, 956 const float *src, unsigned src_stride, 957 void *dst, unsigned dst_stride, 958 unsigned x, unsigned y, unsigned w, unsigned h); 959 960 void 961 util_format_read_4ub(enum pipe_format format, 962 uint8_t *dst, unsigned dst_stride, 963 const void *src, unsigned src_stride, 964 unsigned x, unsigned y, unsigned w, unsigned h); 965 966 void 967 util_format_write_4ub(enum pipe_format format, 968 const uint8_t *src, unsigned src_stride, 969 void *dst, unsigned dst_stride, 970 unsigned x, unsigned y, unsigned w, unsigned h); 971 972 void 973 util_format_read_4ui(enum pipe_format format, 974 unsigned *dst, unsigned dst_stride, 975 const void *src, unsigned src_stride, 976 unsigned x, unsigned y, unsigned w, unsigned h); 977 978 void 979 util_format_write_4ui(enum pipe_format format, 980 const unsigned int *src, unsigned src_stride, 981 void *dst, unsigned dst_stride, 982 unsigned x, unsigned y, unsigned w, unsigned h); 983 984 void 985 util_format_read_4i(enum pipe_format format, 986 int *dst, unsigned dst_stride, 987 const void *src, unsigned src_stride, 988 unsigned x, unsigned y, unsigned w, unsigned h); 989 990 void 991 util_format_write_4i(enum pipe_format format, 992 const int *src, unsigned src_stride, 993 void *dst, unsigned dst_stride, 994 unsigned x, unsigned y, unsigned w, unsigned h); 995 996 /* 997 * Generic format conversion; 998 */ 999 1000 boolean 1001 util_format_fits_8unorm(const struct util_format_description *format_desc); 1002 1003 void 1004 util_format_translate(enum pipe_format dst_format, 1005 void *dst, unsigned dst_stride, 1006 unsigned dst_x, unsigned dst_y, 1007 enum pipe_format src_format, 1008 const void *src, unsigned src_stride, 1009 unsigned src_x, unsigned src_y, 1010 unsigned width, unsigned height); 1011 1012 /* 1013 * Swizzle operations. 1014 */ 1015 1016 /* Compose two sets of swizzles. 1017 * If V is a 4D vector and the function parameters represent functions that 1018 * swizzle vector components, this holds: 1019 * swz2(swz1(V)) = dst(V) 1020 */ 1021 void util_format_compose_swizzles(const unsigned char swz1[4], 1022 const unsigned char swz2[4], 1023 unsigned char dst[4]); 1024 1025 void util_format_swizzle_4f(float *dst, const float *src, 1026 const unsigned char swz[4]); 1027 1028 void util_format_unswizzle_4f(float *dst, const float *src, 1029 const unsigned char swz[4]); 1030 1031 #ifdef __cplusplus 1032 } // extern "C" { 1033 #endif 1034 1035 #endif /* ! U_FORMAT_H */ 1036