The open source OpenXR runtime
at prediction-2 1489 lines 79 kB view raw
1/* bcdec.h - v0.97 2 provides functions to decompress blocks of BC compressed images 3 written by Sergii "iOrange" Kudlai in 2022 4 5 This library does not allocate memory and is trying to use as less stack as possible 6 7 The library was never optimized specifically for speed but for the overall size 8 it has zero external dependencies and is not using any runtime functions 9 10 Supported BC formats: 11 BC1 (also known as DXT1) + it's "binary alpha" variant BC1A (DXT1A) 12 BC2 (also known as DXT3) 13 BC3 (also known as DXT5) 14 BC4 (also known as ATI1N) 15 BC5 (also known as ATI2N) 16 BC6H (HDR format) 17 BC7 18 19 BC1/BC2/BC3/BC7 are expected to decompress into 4*4 RGBA blocks 8bit per component (32bit pixel) 20 BC4/BC5 are expected to decompress into 4*4 R/RG blocks 8bit per component (8bit and 16bit pixel) 21 BC6H is expected to decompress into 4*4 RGB blocks of either 32bit float or 16bit "half" per 22 component (96bit or 48bit pixel) 23 24 For more info, issues and suggestions please visit https://github.com/iOrange/bcdec 25 26 Configuration: 27 #define BCDEC_BC4BC5_PRECISE: 28 enables more precise but slower BC4/BC5 decoding + signed/unsigned mode 29 30 CREDITS: 31 Aras Pranckevicius (@aras-p) - BC1/BC3 decoders optimizations (up to 3x the speed) 32 - BC6H/BC7 bits pulling routines optimizations 33 - optimized BC6H by moving unquantize out of the loop 34 - Split BC6H decompression function into 'half' and 35 'float' variants 36 37 Michael Schmidt (@RunDevelopment) - Found better "magic" coefficients for integer interpolation 38 of reference colors in BC1 color block, that match with 39 the floating point interpolation. This also made it faster 40 than integer division by 3! 41 42 bugfixes: 43 @linkmauve 44 45 LICENSE: See end of file for license information. 46*/ 47 48#ifndef BCDEC_HEADER_INCLUDED 49#define BCDEC_HEADER_INCLUDED 50 51#define BCDEC_VERSION_MAJOR 0 52#define BCDEC_VERSION_MINOR 98 53 54/* if BCDEC_STATIC causes problems, try defining BCDECDEF to 'inline' or 'static inline' */ 55#ifndef BCDECDEF 56#ifdef BCDEC_STATIC 57#define BCDECDEF static 58#else 59#ifdef __cplusplus 60#define BCDECDEF extern "C" 61#else 62#define BCDECDEF extern 63#endif 64#endif 65#endif 66 67/* Used information sources: 68 https://docs.microsoft.com/en-us/windows/win32/direct3d10/d3d10-graphics-programming-guide-resources-block-compression 69 https://docs.microsoft.com/en-us/windows/win32/direct3d11/bc6h-format 70 https://docs.microsoft.com/en-us/windows/win32/direct3d11/bc7-format 71 https://docs.microsoft.com/en-us/windows/win32/direct3d11/bc7-format-mode-reference 72 73 ! WARNING ! Khronos's BPTC partitions tables contain mistakes, do not use them! 74 https://www.khronos.org/registry/DataFormat/specs/1.1/dataformat.1.1.html#BPTC 75 76 ! Use tables from here instead ! 77 https://www.khronos.org/registry/OpenGL/extensions/ARB/ARB_texture_compression_bptc.txt 78 79 Leaving it here as it's a nice read 80 https://fgiesen.wordpress.com/2021/10/04/gpu-bcn-decoding/ 81 82 Fast half to float function from here 83 https://gist.github.com/rygorous/2144712 84*/ 85 86#define BCDEC_BC1_BLOCK_SIZE 8 87#define BCDEC_BC2_BLOCK_SIZE 16 88#define BCDEC_BC3_BLOCK_SIZE 16 89#define BCDEC_BC4_BLOCK_SIZE 8 90#define BCDEC_BC5_BLOCK_SIZE 16 91#define BCDEC_BC6H_BLOCK_SIZE 16 92#define BCDEC_BC7_BLOCK_SIZE 16 93 94#define BCDEC_BC1_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC1_BLOCK_SIZE) 95#define BCDEC_BC2_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC2_BLOCK_SIZE) 96#define BCDEC_BC3_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC3_BLOCK_SIZE) 97#define BCDEC_BC4_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC4_BLOCK_SIZE) 98#define BCDEC_BC5_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC5_BLOCK_SIZE) 99#define BCDEC_BC6H_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC6H_BLOCK_SIZE) 100#define BCDEC_BC7_COMPRESSED_SIZE(w, h) ((((w)>>2)*((h)>>2))*BCDEC_BC7_BLOCK_SIZE) 101 102BCDECDEF void bcdec_bc1(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 103BCDECDEF void bcdec_bc2(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 104BCDECDEF void bcdec_bc3(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 105#ifndef BCDEC_BC4BC5_PRECISE 106BCDECDEF void bcdec_bc4(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 107BCDECDEF void bcdec_bc5(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 108#else 109BCDECDEF void bcdec_bc4(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 110BCDECDEF void bcdec_bc5(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 111BCDECDEF void bcdec_bc4_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 112BCDECDEF void bcdec_bc5_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 113#endif 114BCDECDEF void bcdec_bc6h_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 115BCDECDEF void bcdec_bc6h_half(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned); 116BCDECDEF void bcdec_bc7(const void* compressedBlock, void* decompressedBlock, int destinationPitch); 117 118#endif /* BCDEC_HEADER_INCLUDED */ 119 120#ifdef BCDEC_IMPLEMENTATION 121 122static void bcdec__color_block(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int onlyOpaqueMode) { 123 unsigned short c0, c1; 124 unsigned int refColors[4]; /* 0xAABBGGRR */ 125 unsigned char* dstColors; 126 unsigned int colorIndices; 127 int i, j, idx; 128 unsigned int r0, g0, b0, r1, g1, b1, r, g, b; 129 130 c0 = ((unsigned short*)compressedBlock)[0]; 131 c1 = ((unsigned short*)compressedBlock)[1]; 132 133 /* Unpack 565 ref colors */ 134 r0 = (c0 >> 11) & 0x1F; 135 g0 = (c0 >> 5) & 0x3F; 136 b0 = c0 & 0x1F; 137 138 r1 = (c1 >> 11) & 0x1F; 139 g1 = (c1 >> 5) & 0x3F; 140 b1 = c1 & 0x1F; 141 142 /* Expand 565 ref colors to 888 */ 143 r = (r0 * 527 + 23) >> 6; 144 g = (g0 * 259 + 33) >> 6; 145 b = (b0 * 527 + 23) >> 6; 146 refColors[0] = 0xFF000000 | (b << 16) | (g << 8) | r; 147 148 r = (r1 * 527 + 23) >> 6; 149 g = (g1 * 259 + 33) >> 6; 150 b = (b1 * 527 + 23) >> 6; 151 refColors[1] = 0xFF000000 | (b << 16) | (g << 8) | r; 152 153 if (c0 > c1 || onlyOpaqueMode) { /* Standard BC1 mode (also BC3 color block uses ONLY this mode) */ 154 /* color_2 = 2/3*color_0 + 1/3*color_1 155 color_3 = 1/3*color_0 + 2/3*color_1 */ 156 r = ((2 * r0 + r1) * 351 + 61) >> 7; 157 g = ((2 * g0 + g1) * 2763 + 1039) >> 11; 158 b = ((2 * b0 + b1) * 351 + 61) >> 7; 159 refColors[2] = 0xFF000000 | (b << 16) | (g << 8) | r; 160 161 r = ((r0 + r1 * 2) * 351 + 61) >> 7; 162 g = ((g0 + g1 * 2) * 2763 + 1039) >> 11; 163 b = ((b0 + b1 * 2) * 351 + 61) >> 7; 164 refColors[3] = 0xFF000000 | (b << 16) | (g << 8) | r; 165 } else { /* Quite rare BC1A mode */ 166 /* color_2 = 1/2*color_0 + 1/2*color_1; 167 color_3 = 0; */ 168 r = ((r0 + r1) * 1053 + 125) >> 8; 169 g = ((g0 + g1) * 4145 + 1019) >> 11; 170 b = ((b0 + b1) * 1053 + 125) >> 8; 171 refColors[2] = 0xFF000000 | (b << 16) | (g << 8) | r; 172 173 refColors[3] = 0x00000000; 174 } 175 176 colorIndices = ((unsigned int*)compressedBlock)[1]; 177 178 /* Fill out the decompressed color block */ 179 dstColors = (unsigned char*)decompressedBlock; 180 for (i = 0; i < 4; ++i) { 181 for (j = 0; j < 4; ++j) { 182 idx = colorIndices & 0x03; 183 ((unsigned int*)dstColors)[j] = refColors[idx]; 184 colorIndices >>= 2; 185 } 186 187 dstColors += destinationPitch; 188 } 189} 190 191static void bcdec__sharp_alpha_block(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 192 unsigned short* alpha; 193 unsigned char* decompressed; 194 int i, j; 195 196 alpha = (unsigned short*)compressedBlock; 197 decompressed = (unsigned char*)decompressedBlock; 198 199 for (i = 0; i < 4; ++i) { 200 for (j = 0; j < 4; ++j) { 201 decompressed[j * 4] = ((alpha[i] >> (4 * j)) & 0x0F) * 17; 202 } 203 204 decompressed += destinationPitch; 205 } 206} 207 208static void bcdec__smooth_alpha_block(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int pixelSize) { 209 unsigned char* decompressed; 210 unsigned char alpha[8]; 211 int i, j; 212 unsigned long long block, indices; 213 214 block = *(unsigned long long*)compressedBlock; 215 decompressed = (unsigned char*)decompressedBlock; 216 217 alpha[0] = block & 0xFF; 218 alpha[1] = (block >> 8) & 0xFF; 219 220 if (alpha[0] > alpha[1]) { 221 /* 6 interpolated alpha values. */ 222 alpha[2] = (6 * alpha[0] + alpha[1]) / 7; /* 6/7*alpha_0 + 1/7*alpha_1 */ 223 alpha[3] = (5 * alpha[0] + 2 * alpha[1]) / 7; /* 5/7*alpha_0 + 2/7*alpha_1 */ 224 alpha[4] = (4 * alpha[0] + 3 * alpha[1]) / 7; /* 4/7*alpha_0 + 3/7*alpha_1 */ 225 alpha[5] = (3 * alpha[0] + 4 * alpha[1]) / 7; /* 3/7*alpha_0 + 4/7*alpha_1 */ 226 alpha[6] = (2 * alpha[0] + 5 * alpha[1]) / 7; /* 2/7*alpha_0 + 5/7*alpha_1 */ 227 alpha[7] = ( alpha[0] + 6 * alpha[1]) / 7; /* 1/7*alpha_0 + 6/7*alpha_1 */ 228 } 229 else { 230 /* 4 interpolated alpha values. */ 231 alpha[2] = (4 * alpha[0] + alpha[1]) / 5; /* 4/5*alpha_0 + 1/5*alpha_1 */ 232 alpha[3] = (3 * alpha[0] + 2 * alpha[1]) / 5; /* 3/5*alpha_0 + 2/5*alpha_1 */ 233 alpha[4] = (2 * alpha[0] + 3 * alpha[1]) / 5; /* 2/5*alpha_0 + 3/5*alpha_1 */ 234 alpha[5] = ( alpha[0] + 4 * alpha[1]) / 5; /* 1/5*alpha_0 + 4/5*alpha_1 */ 235 alpha[6] = 0x00; 236 alpha[7] = 0xFF; 237 } 238 239 indices = block >> 16; 240 for (i = 0; i < 4; ++i) { 241 for (j = 0; j < 4; ++j) { 242 decompressed[j * pixelSize] = alpha[indices & 0x07]; 243 indices >>= 3; 244 } 245 246 decompressed += destinationPitch; 247 } 248} 249 250#ifdef BCDEC_BC4BC5_PRECISE 251static void bcdec__bc4_block(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int pixelSize, int isSigned) { 252 signed char* sblock; 253 unsigned char* ublock; 254 int alpha[8]; 255 int i, j; 256 unsigned long long block, indices; 257 258 static int aWeights4[4] = { 13107, 26215, 39321, 52429 }; 259 static int aWeights6[6] = { 9363, 18724, 28086, 37450, 46812, 56173 }; 260 261 block = *(unsigned long long*)compressedBlock; 262 263 if (isSigned) { 264 alpha[0] = (char)(block & 0xFF); 265 alpha[1] = (char)((block >> 8) & 0xFF); 266 if (alpha[0] < -127) alpha[0] = -127; /* -128 clamps to -127 */ 267 if (alpha[1] < -127) alpha[1] = -127; /* -128 clamps to -127 */ 268 } else { 269 alpha[0] = block & 0xFF; 270 alpha[1] = (block >> 8) & 0xFF; 271 } 272 273 if (alpha[0] > alpha[1]) { 274 /* 6 interpolated alpha values. */ 275 alpha[2] = (aWeights6[5] * alpha[0] + aWeights6[0] * alpha[1] + 32768) >> 16; /* 6/7*alpha_0 + 1/7*alpha_1 */ 276 alpha[3] = (aWeights6[4] * alpha[0] + aWeights6[1] * alpha[1] + 32768) >> 16; /* 5/7*alpha_0 + 2/7*alpha_1 */ 277 alpha[4] = (aWeights6[3] * alpha[0] + aWeights6[2] * alpha[1] + 32768) >> 16; /* 4/7*alpha_0 + 3/7*alpha_1 */ 278 alpha[5] = (aWeights6[2] * alpha[0] + aWeights6[3] * alpha[1] + 32768) >> 16; /* 3/7*alpha_0 + 4/7*alpha_1 */ 279 alpha[6] = (aWeights6[1] * alpha[0] + aWeights6[4] * alpha[1] + 32768) >> 16; /* 2/7*alpha_0 + 5/7*alpha_1 */ 280 alpha[7] = (aWeights6[0] * alpha[0] + aWeights6[5] * alpha[1] + 32768) >> 16; /* 1/7*alpha_0 + 6/7*alpha_1 */ 281 } else { 282 /* 4 interpolated alpha values. */ 283 alpha[2] = (aWeights4[3] * alpha[0] + aWeights4[0] * alpha[1] + 32768) >> 16; /* 4/5*alpha_0 + 1/5*alpha_1 */ 284 alpha[3] = (aWeights4[2] * alpha[0] + aWeights4[1] * alpha[1] + 32768) >> 16; /* 3/5*alpha_0 + 2/5*alpha_1 */ 285 alpha[4] = (aWeights4[1] * alpha[0] + aWeights4[2] * alpha[1] + 32768) >> 16; /* 2/5*alpha_0 + 3/5*alpha_1 */ 286 alpha[5] = (aWeights4[0] * alpha[0] + aWeights4[3] * alpha[1] + 32768) >> 16; /* 1/5*alpha_0 + 4/5*alpha_1 */ 287 alpha[6] = isSigned ? -127 : 0; 288 alpha[7] = isSigned ? 127 : 255; 289 } 290 291 indices = block >> 16; 292 if (isSigned) { 293 sblock = (char*)decompressedBlock; 294 for (i = 0; i < 4; ++i) { 295 for (j = 0; j < 4; ++j) { 296 sblock[j * pixelSize] = (char)alpha[indices & 0x07]; 297 indices >>= 3; 298 } 299 sblock += destinationPitch; 300 } 301 } else { 302 ublock = (unsigned char*)decompressedBlock; 303 for (i = 0; i < 4; ++i) { 304 for (j = 0; j < 4; ++j) { 305 ublock[j * pixelSize] = (unsigned char)alpha[indices & 0x07]; 306 indices >>= 3; 307 } 308 ublock += destinationPitch; 309 } 310 } 311} 312 313static void bcdec__bc4_block_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int pixelSize, int isSigned) { 314 float* decompressed; 315 float alpha[8]; 316 int i, j; 317 unsigned long long block, indices; 318 319 block = *(unsigned long long*)compressedBlock; 320 decompressed = (float*)decompressedBlock; 321 322 if (isSigned) { 323 alpha[0] = (float)((char)(block & 0xFF)) / 127.0f; 324 alpha[1] = (float)((char)((block >> 8) & 0xFF)) / 127.0f; 325 if (alpha[0] < -1.0f) alpha[0] = -1.0f; /* -128 clamps to -127 */ 326 if (alpha[1] < -1.0f) alpha[1] = -1.0f; /* -128 clamps to -127 */ 327 } else { 328 alpha[0] = (float)(block & 0xFF) / 255.0f; 329 alpha[1] = (float)((block >> 8) & 0xFF) / 255.0f; 330 } 331 332 if (alpha[0] > alpha[1]) { 333 /* 6 interpolated alpha values. */ 334 alpha[2] = (6.0f * alpha[0] + alpha[1]) / 7.0f; /* 6/7*alpha_0 + 1/7*alpha_1 */ 335 alpha[3] = (5.0f * alpha[0] + 2.0f * alpha[1]) / 7.0f; /* 5/7*alpha_0 + 2/7*alpha_1 */ 336 alpha[4] = (4.0f * alpha[0] + 3.0f * alpha[1]) / 7.0f; /* 4/7*alpha_0 + 3/7*alpha_1 */ 337 alpha[5] = (3.0f * alpha[0] + 4.0f * alpha[1]) / 7.0f; /* 3/7*alpha_0 + 4/7*alpha_1 */ 338 alpha[6] = (2.0f * alpha[0] + 5.0f * alpha[1]) / 7.0f; /* 2/7*alpha_0 + 5/7*alpha_1 */ 339 alpha[7] = ( alpha[0] + 6.0f * alpha[1]) / 7.0f; /* 1/7*alpha_0 + 6/7*alpha_1 */ 340 } else { 341 /* 4 interpolated alpha values. */ 342 alpha[2] = (4.0f * alpha[0] + alpha[1]) / 5.0f; /* 4/5*alpha_0 + 1/5*alpha_1 */ 343 alpha[3] = (3.0f * alpha[0] + 2.0f * alpha[1]) / 5.0f; /* 3/5*alpha_0 + 2/5*alpha_1 */ 344 alpha[4] = (2.0f * alpha[0] + 3.0f * alpha[1]) / 5.0f; /* 2/5*alpha_0 + 3/5*alpha_1 */ 345 alpha[5] = ( alpha[0] + 4.0f * alpha[1]) / 5.0f; /* 1/5*alpha_0 + 4/5*alpha_1 */ 346 alpha[6] = isSigned ? -1.0f : 0.0f; 347 alpha[7] = 1.0f; 348 } 349 350 indices = block >> 16; 351 for (i = 0; i < 4; ++i) { 352 for (j = 0; j < 4; ++j) { 353 decompressed[j * pixelSize] = alpha[indices & 0x07]; 354 indices >>= 3; 355 } 356 decompressed += destinationPitch; 357 } 358} 359#endif /* BCDEC_BC4BC5_PRECISE */ 360 361typedef struct bcdec__bitstream { 362 unsigned long long low; 363 unsigned long long high; 364} bcdec__bitstream_t; 365 366static int bcdec__bitstream_read_bits(bcdec__bitstream_t* bstream, int numBits) { 367 unsigned int mask = (1 << numBits) - 1; 368 /* Read the low N bits */ 369 unsigned int bits = (bstream->low & mask); 370 371 bstream->low >>= numBits; 372 /* Put the low N bits of "high" into the high 64-N bits of "low". */ 373 bstream->low |= (bstream->high & mask) << (sizeof(bstream->high) * 8 - numBits); 374 bstream->high >>= numBits; 375 376 return bits; 377} 378 379static int bcdec__bitstream_read_bit(bcdec__bitstream_t* bstream) { 380 return bcdec__bitstream_read_bits(bstream, 1); 381} 382 383/* reversed bits pulling, used in BC6H decoding 384 why ?? just why ??? */ 385static int bcdec__bitstream_read_bits_r(bcdec__bitstream_t* bstream, int numBits) { 386 int bits = bcdec__bitstream_read_bits(bstream, numBits); 387 /* Reverse the bits. */ 388 int result = 0; 389 while (numBits--) { 390 result <<= 1; 391 result |= (bits & 1); 392 bits >>= 1; 393 } 394 return result; 395} 396 397 398 399BCDECDEF void bcdec_bc1(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 400 bcdec__color_block(compressedBlock, decompressedBlock, destinationPitch, 0); 401} 402 403BCDECDEF void bcdec_bc2(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 404 bcdec__color_block(((char*)compressedBlock) + 8, decompressedBlock, destinationPitch, 1); 405 bcdec__sharp_alpha_block(compressedBlock, ((char*)decompressedBlock) + 3, destinationPitch); 406} 407 408BCDECDEF void bcdec_bc3(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 409 bcdec__color_block(((char*)compressedBlock) + 8, decompressedBlock, destinationPitch, 1); 410 bcdec__smooth_alpha_block(compressedBlock, ((char*)decompressedBlock) + 3, destinationPitch, 4); 411} 412 413#ifndef BCDEC_BC4BC5_PRECISE 414BCDECDEF void bcdec_bc4(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 415 bcdec__smooth_alpha_block(compressedBlock, decompressedBlock, destinationPitch, 1); 416#else 417BCDECDEF void bcdec_bc4(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 418 bcdec__bc4_block(compressedBlock, decompressedBlock, destinationPitch, 1, isSigned); 419#endif 420} 421 422#ifndef BCDEC_BC4BC5_PRECISE 423BCDECDEF void bcdec_bc5(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 424 bcdec__smooth_alpha_block(compressedBlock, decompressedBlock, destinationPitch, 2); 425 bcdec__smooth_alpha_block(((char*)compressedBlock) + 8, ((char*)decompressedBlock) + 1, destinationPitch, 2); 426#else 427BCDECDEF void bcdec_bc5(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 428 bcdec__bc4_block(compressedBlock, decompressedBlock, destinationPitch, 2, isSigned); 429 bcdec__bc4_block(((char*)compressedBlock) + 8, ((char*)decompressedBlock) + 1, destinationPitch, 2, isSigned); 430#endif 431} 432 433#ifdef BCDEC_BC4BC5_PRECISE 434BCDECDEF void bcdec_bc4_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 435 bcdec__bc4_block_float(compressedBlock, decompressedBlock, destinationPitch, 1, isSigned); 436} 437 438BCDECDEF void bcdec_bc5_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 439 bcdec__bc4_block_float(compressedBlock, decompressedBlock, destinationPitch, 2, isSigned); 440 bcdec__bc4_block_float(((char*)compressedBlock) + 8, ((float*)decompressedBlock) + 1, destinationPitch, 2, isSigned); 441} 442#endif /* BCDEC_BC4BC5_PRECISE */ 443 444/* http://graphics.stanford.edu/~seander/bithacks.html#VariableSignExtend */ 445static int bcdec__extend_sign(int val, int bits) { 446 return (val << (32 - bits)) >> (32 - bits); 447} 448 449static int bcdec__transform_inverse(int val, int a0, int bits, int isSigned) { 450 /* If the precision of A0 is "p" bits, then the transform algorithm is: 451 B0 = (B0 + A0) & ((1 << p) - 1) */ 452 val = (val + a0) & ((1 << bits) - 1); 453 if (isSigned) { 454 val = bcdec__extend_sign(val, bits); 455 } 456 return val; 457} 458 459/* pretty much copy-paste from documentation */ 460static int bcdec__unquantize(int val, int bits, int isSigned) { 461 int unq, s = 0; 462 463 if (!isSigned) { 464 if (bits >= 15) { 465 unq = val; 466 } else if (!val) { 467 unq = 0; 468 } else if (val == ((1 << bits) - 1)) { 469 unq = 0xFFFF; 470 } else { 471 unq = ((val << 16) + 0x8000) >> bits; 472 } 473 } else { 474 if (bits >= 16) { 475 unq = val; 476 } else { 477 if (val < 0) { 478 s = 1; 479 val = -val; 480 } 481 482 if (val == 0) { 483 unq = 0; 484 } else if (val >= ((1 << (bits - 1)) - 1)) { 485 unq = 0x7FFF; 486 } else { 487 unq = ((val << 15) + 0x4000) >> (bits - 1); 488 } 489 490 if (s) { 491 unq = -unq; 492 } 493 } 494 } 495 return unq; 496} 497 498static int bcdec__interpolate(int a, int b, int* weights, int index) { 499 return (a * (64 - weights[index]) + b * weights[index] + 32) >> 6; 500} 501 502static unsigned short bcdec__finish_unquantize(int val, int isSigned) { 503 int s; 504 505 if (!isSigned) { 506 return (unsigned short)((val * 31) >> 6); /* scale the magnitude by 31 / 64 */ 507 } else { 508 val = (val < 0) ? -(((-val) * 31) >> 5) : (val * 31) >> 5; /* scale the magnitude by 31 / 32 */ 509 s = 0; 510 if (val < 0) { 511 s = 0x8000; 512 val = -val; 513 } 514 return (unsigned short)(s | val); 515 } 516} 517 518/* modified half_to_float_fast4 from https://gist.github.com/rygorous/2144712 */ 519static float bcdec__half_to_float_quick(unsigned short half) { 520 typedef union { 521 unsigned int u; 522 float f; 523 } FP32; 524 525 static const FP32 magic = { 113 << 23 }; 526 static const unsigned int shifted_exp = 0x7c00 << 13; /* exponent mask after shift */ 527 FP32 o; 528 unsigned int exp; 529 530 o.u = (half & 0x7fff) << 13; /* exponent/mantissa bits */ 531 exp = shifted_exp & o.u; /* just the exponent */ 532 o.u += (127 - 15) << 23; /* exponent adjust */ 533 534 /* handle exponent special cases */ 535 if (exp == shifted_exp) { /* Inf/NaN? */ 536 o.u += (128 - 16) << 23; /* extra exp adjust */ 537 } else if (exp == 0) { /* Zero/Denormal? */ 538 o.u += 1 << 23; /* extra exp adjust */ 539 o.f -= magic.f; /* renormalize */ 540 } 541 542 o.u |= (half & 0x8000) << 16; /* sign bit */ 543 return o.f; 544} 545 546BCDECDEF void bcdec_bc6h_half(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 547 static char actual_bits_count[4][14] = { 548 { 10, 7, 11, 11, 11, 9, 8, 8, 8, 6, 10, 11, 12, 16 }, /* W */ 549 { 5, 6, 5, 4, 4, 5, 6, 5, 5, 6, 10, 9, 8, 4 }, /* dR */ 550 { 5, 6, 4, 5, 4, 5, 5, 6, 5, 6, 10, 9, 8, 4 }, /* dG */ 551 { 5, 6, 4, 4, 5, 5, 5, 5, 6, 6, 10, 9, 8, 4 } /* dB */ 552 }; 553 554 /* There are 32 possible partition sets for a two-region tile. 555 Each 4x4 block represents a single shape. 556 Here also every fix-up index has MSB bit set. */ 557 static unsigned char partition_sets[32][4][4] = { 558 { {128, 0, 1, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 0, 1, 129} }, /* 0 */ 559 { {128, 0, 0, 1}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 0, 129} }, /* 1 */ 560 { {128, 1, 1, 1}, {0, 1, 1, 1}, { 0, 1, 1, 1}, {0, 1, 1, 129} }, /* 2 */ 561 { {128, 0, 0, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 1, 1, 129} }, /* 3 */ 562 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 1, 129} }, /* 4 */ 563 { {128, 0, 1, 1}, {0, 1, 1, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 5 */ 564 { {128, 0, 0, 1}, {0, 0, 1, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 6 */ 565 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 0, 1, 1}, {0, 1, 1, 129} }, /* 7 */ 566 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 1}, {0, 0, 1, 129} }, /* 8 */ 567 { {128, 0, 1, 1}, {0, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 9 */ 568 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 10 */ 569 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 1}, {0, 1, 1, 129} }, /* 11 */ 570 { {128, 0, 0, 1}, {0, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 12 */ 571 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 13 */ 572 { {128, 0, 0, 0}, {1, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 14 */ 573 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 0}, {1, 1, 1, 129} }, /* 15 */ 574 { {128, 0, 0, 0}, {1, 0, 0, 0}, { 1, 1, 1, 0}, {1, 1, 1, 129} }, /* 16 */ 575 { {128, 1, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 0}, {0, 0, 0, 0} }, /* 17 */ 576 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 1, 0} }, /* 18 */ 577 { {128, 1, 129, 1}, {0, 0, 1, 1}, { 0, 0, 0, 1}, {0, 0, 0, 0} }, /* 19 */ 578 { {128, 0, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 0}, {0, 0, 0, 0} }, /* 20 */ 579 { {128, 0, 0, 0}, {1, 0, 0, 0}, {129, 1, 0, 0}, {1, 1, 1, 0} }, /* 21 */ 580 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 0, 0} }, /* 22 */ 581 { {128, 1, 1, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 0, 0, 129} }, /* 23 */ 582 { {128, 0, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 0, 0} }, /* 24 */ 583 { {128, 0, 0, 0}, {1, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 0, 0} }, /* 25 */ 584 { {128, 1, 129, 0}, {0, 1, 1, 0}, { 0, 1, 1, 0}, {0, 1, 1, 0} }, /* 26 */ 585 { {128, 0, 129, 1}, {0, 1, 1, 0}, { 0, 1, 1, 0}, {1, 1, 0, 0} }, /* 27 */ 586 { {128, 0, 0, 1}, {0, 1, 1, 1}, {129, 1, 1, 0}, {1, 0, 0, 0} }, /* 28 */ 587 { {128, 0, 0, 0}, {1, 1, 1, 1}, {129, 1, 1, 1}, {0, 0, 0, 0} }, /* 29 */ 588 { {128, 1, 129, 1}, {0, 0, 0, 1}, { 1, 0, 0, 0}, {1, 1, 1, 0} }, /* 30 */ 589 { {128, 0, 129, 1}, {1, 0, 0, 1}, { 1, 0, 0, 1}, {1, 1, 0, 0} } /* 31 */ 590 }; 591 592 static int aWeight3[8] = { 0, 9, 18, 27, 37, 46, 55, 64 }; 593 static int aWeight4[16] = { 0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64 }; 594 595 bcdec__bitstream_t bstream; 596 int mode, partition, numPartitions, i, j, partitionSet, indexBits, index, ep_i, actualBits0Mode; 597 int r[4], g[4], b[4]; /* wxyz */ 598 unsigned short* decompressed; 599 int* weights; 600 601 decompressed = (unsigned short*)decompressedBlock; 602 603 bstream.low = ((unsigned long long*)compressedBlock)[0]; 604 bstream.high = ((unsigned long long*)compressedBlock)[1]; 605 606 r[0] = r[1] = r[2] = r[3] = 0; 607 g[0] = g[1] = g[2] = g[3] = 0; 608 b[0] = b[1] = b[2] = b[3] = 0; 609 610 mode = bcdec__bitstream_read_bits(&bstream, 2); 611 if (mode > 1) { 612 mode |= (bcdec__bitstream_read_bits(&bstream, 3) << 2); 613 } 614 615 /* modes >= 11 (10 in my code) are using 0 one, others will read it from the bitstream */ 616 partition = 0; 617 618 switch (mode) { 619 /* mode 1 */ 620 case 0b00: { 621 /* Partitition indices: 46 bits 622 Partition: 5 bits 623 Color Endpoints: 75 bits (10.555, 10.555, 10.555) */ 624 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 625 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 626 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 627 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 628 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 629 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 630 r[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* rx[4:0] */ 631 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 632 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 633 g[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* gx[4:0] */ 634 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 635 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 636 b[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bx[4:0] */ 637 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 638 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 639 r[2] |= bcdec__bitstream_read_bits(&bstream, 5); /* ry[4:0] */ 640 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 641 r[3] |= bcdec__bitstream_read_bits(&bstream, 5); /* rz[4:0] */ 642 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 643 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 644 mode = 0; 645 } break; 646 647 /* mode 2 */ 648 case 0b01: { 649 /* Partitition indices: 46 bits 650 Partition: 5 bits 651 Color Endpoints: 75 bits (7666, 7666, 7666) */ 652 g[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gy[5] */ 653 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 654 g[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gz[5] */ 655 r[0] |= bcdec__bitstream_read_bits(&bstream, 7); /* rw[6:0] */ 656 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 657 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 658 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 659 g[0] |= bcdec__bitstream_read_bits(&bstream, 7); /* gw[6:0] */ 660 b[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* by[5] */ 661 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 662 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 663 b[0] |= bcdec__bitstream_read_bits(&bstream, 7); /* bw[6:0] */ 664 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 665 b[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* bz[5] */ 666 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 667 r[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* rx[5:0] */ 668 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 669 g[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* gx[5:0] */ 670 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 671 b[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* bx[5:0] */ 672 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 673 r[2] |= bcdec__bitstream_read_bits(&bstream, 6); /* ry[5:0] */ 674 r[3] |= bcdec__bitstream_read_bits(&bstream, 6); /* rz[5:0] */ 675 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 676 mode = 1; 677 } break; 678 679 /* mode 3 */ 680 case 0b00010: { 681 /* Partitition indices: 46 bits 682 Partition: 5 bits 683 Color Endpoints: 72 bits (11.555, 11.444, 11.444) */ 684 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 685 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 686 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 687 r[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* rx[4:0] */ 688 r[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* rw[10] */ 689 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 690 g[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* gx[3:0] */ 691 g[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* gw[10] */ 692 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 693 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 694 b[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* bx[3:0] */ 695 b[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* bw[10] */ 696 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 697 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 698 r[2] |= bcdec__bitstream_read_bits(&bstream, 5); /* ry[4:0] */ 699 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 700 r[3] |= bcdec__bitstream_read_bits(&bstream, 5); /* rz[4:0] */ 701 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 702 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 703 mode = 2; 704 } break; 705 706 /* mode 4 */ 707 case 0b00110: { 708 /* Partitition indices: 46 bits 709 Partition: 5 bits 710 Color Endpoints: 72 bits (11.444, 11.555, 11.444) */ 711 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 712 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 713 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 714 r[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* rx[3:0] */ 715 r[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* rw[10] */ 716 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 717 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 718 g[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* gx[4:0] */ 719 g[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* gw[10] */ 720 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 721 b[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* bx[3:0] */ 722 b[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* bw[10] */ 723 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 724 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 725 r[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* ry[3:0] */ 726 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 727 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 728 r[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* rz[3:0] */ 729 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 730 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 731 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 732 mode = 3; 733 } break; 734 735 /* mode 5 */ 736 case 0b01010: { 737 /* Partitition indices: 46 bits 738 Partition: 5 bits 739 Color Endpoints: 72 bits (11.444, 11.444, 11.555) */ 740 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 741 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 742 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 743 r[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* rx[3:0] */ 744 r[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* rw[10] */ 745 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 746 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 747 g[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* gx[3:0] */ 748 g[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* gw[10] */ 749 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 750 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 751 b[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bx[4:0] */ 752 b[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* bw[10] */ 753 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 754 r[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* ry[3:0] */ 755 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 756 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 757 r[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* rz[3:0] */ 758 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 759 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 760 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 761 mode = 4; 762 } break; 763 764 /* mode 6 */ 765 case 0b01110: { 766 /* Partitition indices: 46 bits 767 Partition: 5 bits 768 Color Endpoints: 72 bits (9555, 9555, 9555) */ 769 r[0] |= bcdec__bitstream_read_bits(&bstream, 9); /* rw[8:0] */ 770 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 771 g[0] |= bcdec__bitstream_read_bits(&bstream, 9); /* gw[8:0] */ 772 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 773 b[0] |= bcdec__bitstream_read_bits(&bstream, 9); /* bw[8:0] */ 774 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 775 r[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* rx[4:0] */ 776 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 777 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 778 g[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* gx[4:0] */ 779 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 780 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gx[3:0] */ 781 b[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bx[4:0] */ 782 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 783 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 784 r[2] |= bcdec__bitstream_read_bits(&bstream, 5); /* ry[4:0] */ 785 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 786 r[3] |= bcdec__bitstream_read_bits(&bstream, 5); /* rz[4:0] */ 787 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 788 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 789 mode = 5; 790 } break; 791 792 /* mode 7 */ 793 case 0b10010: { 794 /* Partitition indices: 46 bits 795 Partition: 5 bits 796 Color Endpoints: 72 bits (8666, 8555, 8555) */ 797 r[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* rw[7:0] */ 798 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 799 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 800 g[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* gw[7:0] */ 801 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 802 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 803 b[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* bw[7:0] */ 804 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 805 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 806 r[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* rx[5:0] */ 807 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 808 g[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* gx[4:0] */ 809 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 810 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 811 b[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bx[4:0] */ 812 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 813 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 814 r[2] |= bcdec__bitstream_read_bits(&bstream, 6); /* ry[5:0] */ 815 r[3] |= bcdec__bitstream_read_bits(&bstream, 6); /* rz[5:0] */ 816 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 817 mode = 6; 818 } break; 819 820 /* mode 8 */ 821 case 0b10110: { 822 /* Partitition indices: 46 bits 823 Partition: 5 bits 824 Color Endpoints: 72 bits (8555, 8666, 8555) */ 825 r[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* rw[7:0] */ 826 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 827 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 828 g[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* gw[7:0] */ 829 g[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gy[5] */ 830 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 831 b[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* bw[7:0] */ 832 g[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gz[5] */ 833 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 834 r[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* rx[4:0] */ 835 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 836 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 837 g[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* gx[5:0] */ 838 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* zx[3:0] */ 839 b[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bx[4:0] */ 840 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 841 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 842 r[2] |= bcdec__bitstream_read_bits(&bstream, 5); /* ry[4:0] */ 843 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 844 r[3] |= bcdec__bitstream_read_bits(&bstream, 5); /* rz[4:0] */ 845 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 846 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 847 mode = 7; 848 } break; 849 850 /* mode 9 */ 851 case 0b11010: { 852 /* Partitition indices: 46 bits 853 Partition: 5 bits 854 Color Endpoints: 72 bits (8555, 8555, 8666) */ 855 r[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* rw[7:0] */ 856 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 857 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 858 g[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* gw[7:0] */ 859 b[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* by[5] */ 860 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 861 b[0] |= bcdec__bitstream_read_bits(&bstream, 8); /* bw[7:0] */ 862 b[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* bz[5] */ 863 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 864 r[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* bw[4:0] */ 865 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 866 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 867 g[1] |= bcdec__bitstream_read_bits(&bstream, 5); /* gx[4:0] */ 868 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 869 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 870 b[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* bx[5:0] */ 871 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 872 r[2] |= bcdec__bitstream_read_bits(&bstream, 5); /* ry[4:0] */ 873 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 874 r[3] |= bcdec__bitstream_read_bits(&bstream, 5); /* rz[4:0] */ 875 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 876 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 877 mode = 8; 878 } break; 879 880 /* mode 10 */ 881 case 0b11110: { 882 /* Partitition indices: 46 bits 883 Partition: 5 bits 884 Color Endpoints: 72 bits (6666, 6666, 6666) */ 885 r[0] |= bcdec__bitstream_read_bits(&bstream, 6); /* rw[5:0] */ 886 g[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gz[4] */ 887 b[3] |= bcdec__bitstream_read_bit(&bstream); /* bz[0] */ 888 b[3] |= bcdec__bitstream_read_bit(&bstream) << 1; /* bz[1] */ 889 b[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* by[4] */ 890 g[0] |= bcdec__bitstream_read_bits(&bstream, 6); /* gw[5:0] */ 891 g[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gy[5] */ 892 b[2] |= bcdec__bitstream_read_bit(&bstream) << 5; /* by[5] */ 893 b[3] |= bcdec__bitstream_read_bit(&bstream) << 2; /* bz[2] */ 894 g[2] |= bcdec__bitstream_read_bit(&bstream) << 4; /* gy[4] */ 895 b[0] |= bcdec__bitstream_read_bits(&bstream, 6); /* bw[5:0] */ 896 g[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* gz[5] */ 897 b[3] |= bcdec__bitstream_read_bit(&bstream) << 3; /* bz[3] */ 898 b[3] |= bcdec__bitstream_read_bit(&bstream) << 5; /* bz[5] */ 899 b[3] |= bcdec__bitstream_read_bit(&bstream) << 4; /* bz[4] */ 900 r[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* rx[5:0] */ 901 g[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* gy[3:0] */ 902 g[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* gx[5:0] */ 903 g[3] |= bcdec__bitstream_read_bits(&bstream, 4); /* gz[3:0] */ 904 b[1] |= bcdec__bitstream_read_bits(&bstream, 6); /* bx[5:0] */ 905 b[2] |= bcdec__bitstream_read_bits(&bstream, 4); /* by[3:0] */ 906 r[2] |= bcdec__bitstream_read_bits(&bstream, 6); /* ry[5:0] */ 907 r[3] |= bcdec__bitstream_read_bits(&bstream, 6); /* rz[5:0] */ 908 partition = bcdec__bitstream_read_bits(&bstream, 5); /* d[4:0] */ 909 mode = 9; 910 } break; 911 912 /* mode 11 */ 913 case 0b00011: { 914 /* Partitition indices: 63 bits 915 Partition: 0 bits 916 Color Endpoints: 60 bits (10.10, 10.10, 10.10) */ 917 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 918 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 919 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 920 r[1] |= bcdec__bitstream_read_bits(&bstream, 10); /* rx[9:0] */ 921 g[1] |= bcdec__bitstream_read_bits(&bstream, 10); /* gx[9:0] */ 922 b[1] |= bcdec__bitstream_read_bits(&bstream, 10); /* bx[9:0] */ 923 mode = 10; 924 } break; 925 926 /* mode 12 */ 927 case 0b00111: { 928 /* Partitition indices: 63 bits 929 Partition: 0 bits 930 Color Endpoints: 60 bits (11.9, 11.9, 11.9) */ 931 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 932 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 933 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 934 r[1] |= bcdec__bitstream_read_bits(&bstream, 9); /* rx[8:0] */ 935 r[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* rw[10] */ 936 g[1] |= bcdec__bitstream_read_bits(&bstream, 9); /* gx[8:0] */ 937 g[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* gw[10] */ 938 b[1] |= bcdec__bitstream_read_bits(&bstream, 9); /* bx[8:0] */ 939 b[0] |= bcdec__bitstream_read_bit(&bstream) << 10; /* bw[10] */ 940 mode = 11; 941 } break; 942 943 /* mode 13 */ 944 case 0b01011: { 945 /* Partitition indices: 63 bits 946 Partition: 0 bits 947 Color Endpoints: 60 bits (12.8, 12.8, 12.8) */ 948 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 949 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 950 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 951 r[1] |= bcdec__bitstream_read_bits(&bstream, 8); /* rx[7:0] */ 952 r[0] |= bcdec__bitstream_read_bits_r(&bstream, 2) << 10;/* rx[10:11] */ 953 g[1] |= bcdec__bitstream_read_bits(&bstream, 8); /* gx[7:0] */ 954 g[0] |= bcdec__bitstream_read_bits_r(&bstream, 2) << 10;/* gx[10:11] */ 955 b[1] |= bcdec__bitstream_read_bits(&bstream, 8); /* bx[7:0] */ 956 b[0] |= bcdec__bitstream_read_bits_r(&bstream, 2) << 10;/* bx[10:11] */ 957 mode = 12; 958 } break; 959 960 /* mode 14 */ 961 case 0b01111: { 962 /* Partitition indices: 63 bits 963 Partition: 0 bits 964 Color Endpoints: 60 bits (16.4, 16.4, 16.4) */ 965 r[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* rw[9:0] */ 966 g[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* gw[9:0] */ 967 b[0] |= bcdec__bitstream_read_bits(&bstream, 10); /* bw[9:0] */ 968 r[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* rx[3:0] */ 969 r[0] |= bcdec__bitstream_read_bits_r(&bstream, 6) << 10;/* rw[10:15] */ 970 g[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* gx[3:0] */ 971 g[0] |= bcdec__bitstream_read_bits_r(&bstream, 6) << 10;/* gw[10:15] */ 972 b[1] |= bcdec__bitstream_read_bits(&bstream, 4); /* bx[3:0] */ 973 b[0] |= bcdec__bitstream_read_bits_r(&bstream, 6) << 10;/* bw[10:15] */ 974 mode = 13; 975 } break; 976 977 default: { 978 /* Modes 10011, 10111, 11011, and 11111 (not shown) are reserved. 979 Do not use these in your encoder. If the hardware is passed blocks 980 with one of these modes specified, the resulting decompressed block 981 must contain all zeroes in all channels except for the alpha channel. */ 982 for (i = 0; i < 4; ++i) { 983 for (j = 0; j < 4; ++j) { 984 decompressed[j * 3 + 0] = 0; 985 decompressed[j * 3 + 1] = 0; 986 decompressed[j * 3 + 2] = 0; 987 } 988 decompressed += destinationPitch; 989 } 990 991 return; 992 } 993 } 994 995 numPartitions = (mode >= 10) ? 0 : 1; 996 997 actualBits0Mode = actual_bits_count[0][mode]; 998 if (isSigned) { 999 r[0] = bcdec__extend_sign(r[0], actualBits0Mode); 1000 g[0] = bcdec__extend_sign(g[0], actualBits0Mode); 1001 b[0] = bcdec__extend_sign(b[0], actualBits0Mode); 1002 } 1003 1004 /* Mode 11 (like Mode 10) does not use delta compression, 1005 and instead stores both color endpoints explicitly. */ 1006 if ((mode != 9 && mode != 10) || isSigned) { 1007 for (i = 1; i < (numPartitions + 1) * 2; ++i) { 1008 r[i] = bcdec__extend_sign(r[i], actual_bits_count[1][mode]); 1009 g[i] = bcdec__extend_sign(g[i], actual_bits_count[2][mode]); 1010 b[i] = bcdec__extend_sign(b[i], actual_bits_count[3][mode]); 1011 } 1012 } 1013 1014 if (mode != 9 && mode != 10) { 1015 for (i = 1; i < (numPartitions + 1) * 2; ++i) { 1016 r[i] = bcdec__transform_inverse(r[i], r[0], actualBits0Mode, isSigned); 1017 g[i] = bcdec__transform_inverse(g[i], g[0], actualBits0Mode, isSigned); 1018 b[i] = bcdec__transform_inverse(b[i], b[0], actualBits0Mode, isSigned); 1019 } 1020 } 1021 1022 for (i = 0; i < (numPartitions + 1) * 2; ++i) { 1023 r[i] = bcdec__unquantize(r[i], actualBits0Mode, isSigned); 1024 g[i] = bcdec__unquantize(g[i], actualBits0Mode, isSigned); 1025 b[i] = bcdec__unquantize(b[i], actualBits0Mode, isSigned); 1026 } 1027 1028 weights = (mode >= 10) ? aWeight4 : aWeight3; 1029 for (i = 0; i < 4; ++i) { 1030 for (j = 0; j < 4; ++j) { 1031 partitionSet = (mode >= 10) ? ((i|j) ? 0 : 128) : partition_sets[partition][i][j]; 1032 1033 indexBits = (mode >= 10) ? 4 : 3; 1034 /* fix-up index is specified with one less bit */ 1035 /* The fix-up index for subset 0 is always index 0 */ 1036 if (partitionSet & 0x80) { 1037 indexBits--; 1038 } 1039 partitionSet &= 0x01; 1040 1041 index = bcdec__bitstream_read_bits(&bstream, indexBits); 1042 1043 ep_i = partitionSet * 2; 1044 decompressed[j * 3 + 0] = bcdec__finish_unquantize( 1045 bcdec__interpolate(r[ep_i], r[ep_i+1], weights, index), isSigned); 1046 decompressed[j * 3 + 1] = bcdec__finish_unquantize( 1047 bcdec__interpolate(g[ep_i], g[ep_i+1], weights, index), isSigned); 1048 decompressed[j * 3 + 2] = bcdec__finish_unquantize( 1049 bcdec__interpolate(b[ep_i], b[ep_i+1], weights, index), isSigned); 1050 } 1051 1052 decompressed += destinationPitch; 1053 } 1054} 1055 1056BCDECDEF void bcdec_bc6h_float(const void* compressedBlock, void* decompressedBlock, int destinationPitch, int isSigned) { 1057 unsigned short block[16*3]; 1058 float* decompressed; 1059 const unsigned short* b; 1060 int i, j; 1061 1062 bcdec_bc6h_half(compressedBlock, block, 4*3, isSigned); 1063 b = block; 1064 decompressed = (float*)decompressedBlock; 1065 for (i = 0; i < 4; ++i) { 1066 for (j = 0; j < 4; ++j) { 1067 decompressed[j * 3 + 0] = bcdec__half_to_float_quick(*b++); 1068 decompressed[j * 3 + 1] = bcdec__half_to_float_quick(*b++); 1069 decompressed[j * 3 + 2] = bcdec__half_to_float_quick(*b++); 1070 } 1071 decompressed += destinationPitch; 1072 } 1073} 1074 1075static void bcdec__swap_values(int* a, int* b) { 1076 a[0] ^= b[0], b[0] ^= a[0], a[0] ^= b[0]; 1077} 1078 1079BCDECDEF void bcdec_bc7(const void* compressedBlock, void* decompressedBlock, int destinationPitch) { 1080 static char actual_bits_count[2][8] = { 1081 { 4, 6, 5, 7, 5, 7, 7, 5 }, /* RGBA */ 1082 { 0, 0, 0, 0, 6, 8, 7, 5 }, /* Alpha */ 1083 }; 1084 1085 /* There are 64 possible partition sets for a two-region tile. 1086 Each 4x4 block represents a single shape. 1087 Here also every fix-up index has MSB bit set. */ 1088 static unsigned char partition_sets[2][64][4][4] = { 1089 { /* Partition table for 2-subset BPTC */ 1090 { {128, 0, 1, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 0, 1, 129} }, /* 0 */ 1091 { {128, 0, 0, 1}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 0, 129} }, /* 1 */ 1092 { {128, 1, 1, 1}, {0, 1, 1, 1}, { 0, 1, 1, 1}, {0, 1, 1, 129} }, /* 2 */ 1093 { {128, 0, 0, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 1, 1, 129} }, /* 3 */ 1094 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 1, 129} }, /* 4 */ 1095 { {128, 0, 1, 1}, {0, 1, 1, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 5 */ 1096 { {128, 0, 0, 1}, {0, 0, 1, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 6 */ 1097 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 0, 1, 1}, {0, 1, 1, 129} }, /* 7 */ 1098 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 1}, {0, 0, 1, 129} }, /* 8 */ 1099 { {128, 0, 1, 1}, {0, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 9 */ 1100 { {128, 0, 0, 0}, {0, 0, 0, 1}, { 0, 1, 1, 1}, {1, 1, 1, 129} }, /* 10 */ 1101 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 1}, {0, 1, 1, 129} }, /* 11 */ 1102 { {128, 0, 0, 1}, {0, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 12 */ 1103 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 13 */ 1104 { {128, 0, 0, 0}, {1, 1, 1, 1}, { 1, 1, 1, 1}, {1, 1, 1, 129} }, /* 14 */ 1105 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 0}, {1, 1, 1, 129} }, /* 15 */ 1106 { {128, 0, 0, 0}, {1, 0, 0, 0}, { 1, 1, 1, 0}, {1, 1, 1, 129} }, /* 16 */ 1107 { {128, 1, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 0}, {0, 0, 0, 0} }, /* 17 */ 1108 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 1, 0} }, /* 18 */ 1109 { {128, 1, 129, 1}, {0, 0, 1, 1}, { 0, 0, 0, 1}, {0, 0, 0, 0} }, /* 19 */ 1110 { {128, 0, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 0}, {0, 0, 0, 0} }, /* 20 */ 1111 { {128, 0, 0, 0}, {1, 0, 0, 0}, {129, 1, 0, 0}, {1, 1, 1, 0} }, /* 21 */ 1112 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 0, 0} }, /* 22 */ 1113 { {128, 1, 1, 1}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {0, 0, 0, 129} }, /* 23 */ 1114 { {128, 0, 129, 1}, {0, 0, 0, 1}, { 0, 0, 0, 1}, {0, 0, 0, 0} }, /* 24 */ 1115 { {128, 0, 0, 0}, {1, 0, 0, 0}, {129, 0, 0, 0}, {1, 1, 0, 0} }, /* 25 */ 1116 { {128, 1, 129, 0}, {0, 1, 1, 0}, { 0, 1, 1, 0}, {0, 1, 1, 0} }, /* 26 */ 1117 { {128, 0, 129, 1}, {0, 1, 1, 0}, { 0, 1, 1, 0}, {1, 1, 0, 0} }, /* 27 */ 1118 { {128, 0, 0, 1}, {0, 1, 1, 1}, {129, 1, 1, 0}, {1, 0, 0, 0} }, /* 28 */ 1119 { {128, 0, 0, 0}, {1, 1, 1, 1}, {129, 1, 1, 1}, {0, 0, 0, 0} }, /* 29 */ 1120 { {128, 1, 129, 1}, {0, 0, 0, 1}, { 1, 0, 0, 0}, {1, 1, 1, 0} }, /* 30 */ 1121 { {128, 0, 129, 1}, {1, 0, 0, 1}, { 1, 0, 0, 1}, {1, 1, 0, 0} }, /* 31 */ 1122 { {128, 1, 0, 1}, {0, 1, 0, 1}, { 0, 1, 0, 1}, {0, 1, 0, 129} }, /* 32 */ 1123 { {128, 0, 0, 0}, {1, 1, 1, 1}, { 0, 0, 0, 0}, {1, 1, 1, 129} }, /* 33 */ 1124 { {128, 1, 0, 1}, {1, 0, 129, 0}, { 0, 1, 0, 1}, {1, 0, 1, 0} }, /* 34 */ 1125 { {128, 0, 1, 1}, {0, 0, 1, 1}, {129, 1, 0, 0}, {1, 1, 0, 0} }, /* 35 */ 1126 { {128, 0, 129, 1}, {1, 1, 0, 0}, { 0, 0, 1, 1}, {1, 1, 0, 0} }, /* 36 */ 1127 { {128, 1, 0, 1}, {0, 1, 0, 1}, {129, 0, 1, 0}, {1, 0, 1, 0} }, /* 37 */ 1128 { {128, 1, 1, 0}, {1, 0, 0, 1}, { 0, 1, 1, 0}, {1, 0, 0, 129} }, /* 38 */ 1129 { {128, 1, 0, 1}, {1, 0, 1, 0}, { 1, 0, 1, 0}, {0, 1, 0, 129} }, /* 39 */ 1130 { {128, 1, 129, 1}, {0, 0, 1, 1}, { 1, 1, 0, 0}, {1, 1, 1, 0} }, /* 40 */ 1131 { {128, 0, 0, 1}, {0, 0, 1, 1}, {129, 1, 0, 0}, {1, 0, 0, 0} }, /* 41 */ 1132 { {128, 0, 129, 1}, {0, 0, 1, 0}, { 0, 1, 0, 0}, {1, 1, 0, 0} }, /* 42 */ 1133 { {128, 0, 129, 1}, {1, 0, 1, 1}, { 1, 1, 0, 1}, {1, 1, 0, 0} }, /* 43 */ 1134 { {128, 1, 129, 0}, {1, 0, 0, 1}, { 1, 0, 0, 1}, {0, 1, 1, 0} }, /* 44 */ 1135 { {128, 0, 1, 1}, {1, 1, 0, 0}, { 1, 1, 0, 0}, {0, 0, 1, 129} }, /* 45 */ 1136 { {128, 1, 1, 0}, {0, 1, 1, 0}, { 1, 0, 0, 1}, {1, 0, 0, 129} }, /* 46 */ 1137 { {128, 0, 0, 0}, {0, 1, 129, 0}, { 0, 1, 1, 0}, {0, 0, 0, 0} }, /* 47 */ 1138 { {128, 1, 0, 0}, {1, 1, 129, 0}, { 0, 1, 0, 0}, {0, 0, 0, 0} }, /* 48 */ 1139 { {128, 0, 129, 0}, {0, 1, 1, 1}, { 0, 0, 1, 0}, {0, 0, 0, 0} }, /* 49 */ 1140 { {128, 0, 0, 0}, {0, 0, 129, 0}, { 0, 1, 1, 1}, {0, 0, 1, 0} }, /* 50 */ 1141 { {128, 0, 0, 0}, {0, 1, 0, 0}, {129, 1, 1, 0}, {0, 1, 0, 0} }, /* 51 */ 1142 { {128, 1, 1, 0}, {1, 1, 0, 0}, { 1, 0, 0, 1}, {0, 0, 1, 129} }, /* 52 */ 1143 { {128, 0, 1, 1}, {0, 1, 1, 0}, { 1, 1, 0, 0}, {1, 0, 0, 129} }, /* 53 */ 1144 { {128, 1, 129, 0}, {0, 0, 1, 1}, { 1, 0, 0, 1}, {1, 1, 0, 0} }, /* 54 */ 1145 { {128, 0, 129, 1}, {1, 0, 0, 1}, { 1, 1, 0, 0}, {0, 1, 1, 0} }, /* 55 */ 1146 { {128, 1, 1, 0}, {1, 1, 0, 0}, { 1, 1, 0, 0}, {1, 0, 0, 129} }, /* 56 */ 1147 { {128, 1, 1, 0}, {0, 0, 1, 1}, { 0, 0, 1, 1}, {1, 0, 0, 129} }, /* 57 */ 1148 { {128, 1, 1, 1}, {1, 1, 1, 0}, { 1, 0, 0, 0}, {0, 0, 0, 129} }, /* 58 */ 1149 { {128, 0, 0, 1}, {1, 0, 0, 0}, { 1, 1, 1, 0}, {0, 1, 1, 129} }, /* 59 */ 1150 { {128, 0, 0, 0}, {1, 1, 1, 1}, { 0, 0, 1, 1}, {0, 0, 1, 129} }, /* 60 */ 1151 { {128, 0, 129, 1}, {0, 0, 1, 1}, { 1, 1, 1, 1}, {0, 0, 0, 0} }, /* 61 */ 1152 { {128, 0, 129, 0}, {0, 0, 1, 0}, { 1, 1, 1, 0}, {1, 1, 1, 0} }, /* 62 */ 1153 { {128, 1, 0, 0}, {0, 1, 0, 0}, { 0, 1, 1, 1}, {0, 1, 1, 129} } /* 63 */ 1154 }, 1155 { /* Partition table for 3-subset BPTC */ 1156 { {128, 0, 1, 129}, {0, 0, 1, 1}, { 0, 2, 2, 1}, { 2, 2, 2, 130} }, /* 0 */ 1157 { {128, 0, 0, 129}, {0, 0, 1, 1}, {130, 2, 1, 1}, { 2, 2, 2, 1} }, /* 1 */ 1158 { {128, 0, 0, 0}, {2, 0, 0, 1}, {130, 2, 1, 1}, { 2, 2, 1, 129} }, /* 2 */ 1159 { {128, 2, 2, 130}, {0, 0, 2, 2}, { 0, 0, 1, 1}, { 0, 1, 1, 129} }, /* 3 */ 1160 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 1, 2, 2}, { 1, 1, 2, 130} }, /* 4 */ 1161 { {128, 0, 1, 129}, {0, 0, 1, 1}, { 0, 0, 2, 2}, { 0, 0, 2, 130} }, /* 5 */ 1162 { {128, 0, 2, 130}, {0, 0, 2, 2}, { 1, 1, 1, 1}, { 1, 1, 1, 129} }, /* 6 */ 1163 { {128, 0, 1, 1}, {0, 0, 1, 1}, {130, 2, 1, 1}, { 2, 2, 1, 129} }, /* 7 */ 1164 { {128, 0, 0, 0}, {0, 0, 0, 0}, {129, 1, 1, 1}, { 2, 2, 2, 130} }, /* 8 */ 1165 { {128, 0, 0, 0}, {1, 1, 1, 1}, {129, 1, 1, 1}, { 2, 2, 2, 130} }, /* 9 */ 1166 { {128, 0, 0, 0}, {1, 1, 129, 1}, { 2, 2, 2, 2}, { 2, 2, 2, 130} }, /* 10 */ 1167 { {128, 0, 1, 2}, {0, 0, 129, 2}, { 0, 0, 1, 2}, { 0, 0, 1, 130} }, /* 11 */ 1168 { {128, 1, 1, 2}, {0, 1, 129, 2}, { 0, 1, 1, 2}, { 0, 1, 1, 130} }, /* 12 */ 1169 { {128, 1, 2, 2}, {0, 129, 2, 2}, { 0, 1, 2, 2}, { 0, 1, 2, 130} }, /* 13 */ 1170 { {128, 0, 1, 129}, {0, 1, 1, 2}, { 1, 1, 2, 2}, { 1, 2, 2, 130} }, /* 14 */ 1171 { {128, 0, 1, 129}, {2, 0, 0, 1}, {130, 2, 0, 0}, { 2, 2, 2, 0} }, /* 15 */ 1172 { {128, 0, 0, 129}, {0, 0, 1, 1}, { 0, 1, 1, 2}, { 1, 1, 2, 130} }, /* 16 */ 1173 { {128, 1, 1, 129}, {0, 0, 1, 1}, {130, 0, 0, 1}, { 2, 2, 0, 0} }, /* 17 */ 1174 { {128, 0, 0, 0}, {1, 1, 2, 2}, {129, 1, 2, 2}, { 1, 1, 2, 130} }, /* 18 */ 1175 { {128, 0, 2, 130}, {0, 0, 2, 2}, { 0, 0, 2, 2}, { 1, 1, 1, 129} }, /* 19 */ 1176 { {128, 1, 1, 129}, {0, 1, 1, 1}, { 0, 2, 2, 2}, { 0, 2, 2, 130} }, /* 20 */ 1177 { {128, 0, 0, 129}, {0, 0, 0, 1}, {130, 2, 2, 1}, { 2, 2, 2, 1} }, /* 21 */ 1178 { {128, 0, 0, 0}, {0, 0, 129, 1}, { 0, 1, 2, 2}, { 0, 1, 2, 130} }, /* 22 */ 1179 { {128, 0, 0, 0}, {1, 1, 0, 0}, {130, 2, 129, 0}, { 2, 2, 1, 0} }, /* 23 */ 1180 { {128, 1, 2, 130}, {0, 129, 2, 2}, { 0, 0, 1, 1}, { 0, 0, 0, 0} }, /* 24 */ 1181 { {128, 0, 1, 2}, {0, 0, 1, 2}, {129, 1, 2, 2}, { 2, 2, 2, 130} }, /* 25 */ 1182 { {128, 1, 1, 0}, {1, 2, 130, 1}, {129, 2, 2, 1}, { 0, 1, 1, 0} }, /* 26 */ 1183 { {128, 0, 0, 0}, {0, 1, 129, 0}, { 1, 2, 130, 1}, { 1, 2, 2, 1} }, /* 27 */ 1184 { {128, 0, 2, 2}, {1, 1, 0, 2}, {129, 1, 0, 2}, { 0, 0, 2, 130} }, /* 28 */ 1185 { {128, 1, 1, 0}, {0, 129, 1, 0}, { 2, 0, 0, 2}, { 2, 2, 2, 130} }, /* 29 */ 1186 { {128, 0, 1, 1}, {0, 1, 2, 2}, { 0, 1, 130, 2}, { 0, 0, 1, 129} }, /* 30 */ 1187 { {128, 0, 0, 0}, {2, 0, 0, 0}, {130, 2, 1, 1}, { 2, 2, 2, 129} }, /* 31 */ 1188 { {128, 0, 0, 0}, {0, 0, 0, 2}, {129, 1, 2, 2}, { 1, 2, 2, 130} }, /* 32 */ 1189 { {128, 2, 2, 130}, {0, 0, 2, 2}, { 0, 0, 1, 2}, { 0, 0, 1, 129} }, /* 33 */ 1190 { {128, 0, 1, 129}, {0, 0, 1, 2}, { 0, 0, 2, 2}, { 0, 2, 2, 130} }, /* 34 */ 1191 { {128, 1, 2, 0}, {0, 129, 2, 0}, { 0, 1, 130, 0}, { 0, 1, 2, 0} }, /* 35 */ 1192 { {128, 0, 0, 0}, {1, 1, 129, 1}, { 2, 2, 130, 2}, { 0, 0, 0, 0} }, /* 36 */ 1193 { {128, 1, 2, 0}, {1, 2, 0, 1}, {130, 0, 129, 2}, { 0, 1, 2, 0} }, /* 37 */ 1194 { {128, 1, 2, 0}, {2, 0, 1, 2}, {129, 130, 0, 1}, { 0, 1, 2, 0} }, /* 38 */ 1195 { {128, 0, 1, 1}, {2, 2, 0, 0}, { 1, 1, 130, 2}, { 0, 0, 1, 129} }, /* 39 */ 1196 { {128, 0, 1, 1}, {1, 1, 130, 2}, { 2, 2, 0, 0}, { 0, 0, 1, 129} }, /* 40 */ 1197 { {128, 1, 0, 129}, {0, 1, 0, 1}, { 2, 2, 2, 2}, { 2, 2, 2, 130} }, /* 41 */ 1198 { {128, 0, 0, 0}, {0, 0, 0, 0}, {130, 1, 2, 1}, { 2, 1, 2, 129} }, /* 42 */ 1199 { {128, 0, 2, 2}, {1, 129, 2, 2}, { 0, 0, 2, 2}, { 1, 1, 2, 130} }, /* 43 */ 1200 { {128, 0, 2, 130}, {0, 0, 1, 1}, { 0, 0, 2, 2}, { 0, 0, 1, 129} }, /* 44 */ 1201 { {128, 2, 2, 0}, {1, 2, 130, 1}, { 0, 2, 2, 0}, { 1, 2, 2, 129} }, /* 45 */ 1202 { {128, 1, 0, 1}, {2, 2, 130, 2}, { 2, 2, 2, 2}, { 0, 1, 0, 129} }, /* 46 */ 1203 { {128, 0, 0, 0}, {2, 1, 2, 1}, {130, 1, 2, 1}, { 2, 1, 2, 129} }, /* 47 */ 1204 { {128, 1, 0, 129}, {0, 1, 0, 1}, { 0, 1, 0, 1}, { 2, 2, 2, 130} }, /* 48 */ 1205 { {128, 2, 2, 130}, {0, 1, 1, 1}, { 0, 2, 2, 2}, { 0, 1, 1, 129} }, /* 49 */ 1206 { {128, 0, 0, 2}, {1, 129, 1, 2}, { 0, 0, 0, 2}, { 1, 1, 1, 130} }, /* 50 */ 1207 { {128, 0, 0, 0}, {2, 129, 1, 2}, { 2, 1, 1, 2}, { 2, 1, 1, 130} }, /* 51 */ 1208 { {128, 2, 2, 2}, {0, 129, 1, 1}, { 0, 1, 1, 1}, { 0, 2, 2, 130} }, /* 52 */ 1209 { {128, 0, 0, 2}, {1, 1, 1, 2}, {129, 1, 1, 2}, { 0, 0, 0, 130} }, /* 53 */ 1210 { {128, 1, 1, 0}, {0, 129, 1, 0}, { 0, 1, 1, 0}, { 2, 2, 2, 130} }, /* 54 */ 1211 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 2, 1, 129, 2}, { 2, 1, 1, 130} }, /* 55 */ 1212 { {128, 1, 1, 0}, {0, 129, 1, 0}, { 2, 2, 2, 2}, { 2, 2, 2, 130} }, /* 56 */ 1213 { {128, 0, 2, 2}, {0, 0, 1, 1}, { 0, 0, 129, 1}, { 0, 0, 2, 130} }, /* 57 */ 1214 { {128, 0, 2, 2}, {1, 1, 2, 2}, {129, 1, 2, 2}, { 0, 0, 2, 130} }, /* 58 */ 1215 { {128, 0, 0, 0}, {0, 0, 0, 0}, { 0, 0, 0, 0}, { 2, 129, 1, 130} }, /* 59 */ 1216 { {128, 0, 0, 130}, {0, 0, 0, 1}, { 0, 0, 0, 2}, { 0, 0, 0, 129} }, /* 60 */ 1217 { {128, 2, 2, 2}, {1, 2, 2, 2}, { 0, 2, 2, 2}, {129, 2, 2, 130} }, /* 61 */ 1218 { {128, 1, 0, 129}, {2, 2, 2, 2}, { 2, 2, 2, 2}, { 2, 2, 2, 130} }, /* 62 */ 1219 { {128, 1, 1, 129}, {2, 0, 1, 1}, {130, 2, 0, 1}, { 2, 2, 2, 0} } /* 63 */ 1220 } 1221 }; 1222 1223 static int aWeight2[] = { 0, 21, 43, 64 }; 1224 static int aWeight3[] = { 0, 9, 18, 27, 37, 46, 55, 64 }; 1225 static int aWeight4[] = { 0, 4, 9, 13, 17, 21, 26, 30, 34, 38, 43, 47, 51, 55, 60, 64 }; 1226 1227 static unsigned char sModeHasPBits = 0b11001011; 1228 1229 bcdec__bitstream_t bstream; 1230 int mode, partition, numPartitions, numEndpoints, i, j, k, rotation, partitionSet; 1231 int indexSelectionBit, indexBits, indexBits2, index, index2; 1232 int endpoints[6][4]; 1233 char indices[4][4]; 1234 int r, g, b, a; 1235 int* weights, * weights2; 1236 unsigned char* decompressed; 1237 1238 decompressed = (unsigned char*)decompressedBlock; 1239 1240 bstream.low = ((unsigned long long*)compressedBlock)[0]; 1241 bstream.high = ((unsigned long long*)compressedBlock)[1]; 1242 1243 for (mode = 0; mode < 8 && (0 == bcdec__bitstream_read_bit(&bstream)); ++mode); 1244 1245 /* unexpected mode, clear the block (transparent black) */ 1246 if (mode >= 8) { 1247 for (i = 0; i < 4; ++i) { 1248 for (j = 0; j < 4; ++j) { 1249 decompressed[j * 4 + 0] = 0; 1250 decompressed[j * 4 + 1] = 0; 1251 decompressed[j * 4 + 2] = 0; 1252 decompressed[j * 4 + 3] = 0; 1253 } 1254 decompressed += destinationPitch; 1255 } 1256 1257 return; 1258 } 1259 1260 partition = 0; 1261 numPartitions = 1; 1262 rotation = 0; 1263 indexSelectionBit = 0; 1264 1265 if (mode == 0 || mode == 1 || mode == 2 || mode == 3 || mode == 7) { 1266 numPartitions = (mode == 0 || mode == 2) ? 3 : 2; 1267 partition = bcdec__bitstream_read_bits(&bstream, (mode == 0) ? 4 : 6); 1268 } 1269 1270 numEndpoints = numPartitions * 2; 1271 1272 if (mode == 4 || mode == 5) { 1273 rotation = bcdec__bitstream_read_bits(&bstream, 2); 1274 1275 if (mode == 4) { 1276 indexSelectionBit = bcdec__bitstream_read_bit(&bstream); 1277 } 1278 } 1279 1280 /* Extract endpoints */ 1281 /* RGB */ 1282 for (i = 0; i < 3; ++i) { 1283 for (j = 0; j < numEndpoints; ++j) { 1284 endpoints[j][i] = bcdec__bitstream_read_bits(&bstream, actual_bits_count[0][mode]); 1285 } 1286 } 1287 /* Alpha (if any) */ 1288 if (actual_bits_count[1][mode] > 0) { 1289 for (j = 0; j < numEndpoints; ++j) { 1290 endpoints[j][3] = bcdec__bitstream_read_bits(&bstream, actual_bits_count[1][mode]); 1291 } 1292 } 1293 1294 /* Fully decode endpoints */ 1295 /* First handle modes that have P-bits */ 1296 if (mode == 0 || mode == 1 || mode == 3 || mode == 6 || mode == 7) { 1297 for (i = 0; i < numEndpoints; ++i) { 1298 /* component-wise left-shift */ 1299 for (j = 0; j < 4; ++j) { 1300 endpoints[i][j] <<= 1; 1301 } 1302 } 1303 1304 /* if P-bit is shared */ 1305 if (mode == 1) { 1306 i = bcdec__bitstream_read_bit(&bstream); 1307 j = bcdec__bitstream_read_bit(&bstream); 1308 1309 /* rgb component-wise insert pbits */ 1310 for (k = 0; k < 3; ++k) { 1311 endpoints[0][k] |= i; 1312 endpoints[1][k] |= i; 1313 endpoints[2][k] |= j; 1314 endpoints[3][k] |= j; 1315 } 1316 } else if (sModeHasPBits & (1 << mode)) { 1317 /* unique P-bit per endpoint */ 1318 for (i = 0; i < numEndpoints; ++i) { 1319 j = bcdec__bitstream_read_bit(&bstream); 1320 for (k = 0; k < 4; ++k) { 1321 endpoints[i][k] |= j; 1322 } 1323 } 1324 } 1325 } 1326 1327 for (i = 0; i < numEndpoints; ++i) { 1328 /* get color components precision including pbit */ 1329 j = actual_bits_count[0][mode] + ((sModeHasPBits >> mode) & 1); 1330 1331 for (k = 0; k < 3; ++k) { 1332 /* left shift endpoint components so that their MSB lies in bit 7 */ 1333 endpoints[i][k] = endpoints[i][k] << (8 - j); 1334 /* Replicate each component's MSB into the LSBs revealed by the left-shift operation above */ 1335 endpoints[i][k] = endpoints[i][k] | (endpoints[i][k] >> j); 1336 } 1337 1338 /* get alpha component precision including pbit */ 1339 j = actual_bits_count[1][mode] + ((sModeHasPBits >> mode) & 1); 1340 1341 /* left shift endpoint components so that their MSB lies in bit 7 */ 1342 endpoints[i][3] = endpoints[i][3] << (8 - j); 1343 /* Replicate each component's MSB into the LSBs revealed by the left-shift operation above */ 1344 endpoints[i][3] = endpoints[i][3] | (endpoints[i][3] >> j); 1345 } 1346 1347 /* If this mode does not explicitly define the alpha component */ 1348 /* set alpha equal to 1.0 */ 1349 if (!actual_bits_count[1][mode]) { 1350 for (j = 0; j < numEndpoints; ++j) { 1351 endpoints[j][3] = 0xFF; 1352 } 1353 } 1354 1355 /* Determine weights tables */ 1356 indexBits = (mode == 0 || mode == 1) ? 3 : ((mode == 6) ? 4 : 2); 1357 indexBits2 = (mode == 4) ? 3 : ((mode == 5) ? 2 : 0); 1358 weights = (indexBits == 2) ? aWeight2 : ((indexBits == 3) ? aWeight3 : aWeight4); 1359 weights2 = (indexBits2 == 2) ? aWeight2 : aWeight3; 1360 1361 /* Quite inconvenient that indices aren't interleaved so we have to make 2 passes here */ 1362 /* Pass #1: collecting color indices */ 1363 for (i = 0; i < 4; ++i) { 1364 for (j = 0; j < 4; ++j) { 1365 partitionSet = (numPartitions == 1) ? ((i | j) ? 0 : 128) : partition_sets[numPartitions - 2][partition][i][j]; 1366 1367 indexBits = (mode == 0 || mode == 1) ? 3 : ((mode == 6) ? 4 : 2); 1368 /* fix-up index is specified with one less bit */ 1369 /* The fix-up index for subset 0 is always index 0 */ 1370 if (partitionSet & 0x80) { 1371 indexBits--; 1372 } 1373 1374 indices[i][j] = bcdec__bitstream_read_bits(&bstream, indexBits); 1375 } 1376 } 1377 1378 /* Pass #2: reading alpha indices (if any) and interpolating & rotating */ 1379 for (i = 0; i < 4; ++i) { 1380 for (j = 0; j < 4; ++j) { 1381 partitionSet = (numPartitions == 1) ? ((i|j) ? 0 : 128) : partition_sets[numPartitions - 2][partition][i][j]; 1382 partitionSet &= 0x03; 1383 1384 index = indices[i][j]; 1385 1386 if (!indexBits2) { 1387 r = bcdec__interpolate(endpoints[partitionSet * 2][0], endpoints[partitionSet * 2 + 1][0], weights, index); 1388 g = bcdec__interpolate(endpoints[partitionSet * 2][1], endpoints[partitionSet * 2 + 1][1], weights, index); 1389 b = bcdec__interpolate(endpoints[partitionSet * 2][2], endpoints[partitionSet * 2 + 1][2], weights, index); 1390 a = bcdec__interpolate(endpoints[partitionSet * 2][3], endpoints[partitionSet * 2 + 1][3], weights, index); 1391 } else { 1392 index2 = bcdec__bitstream_read_bits(&bstream, (i|j) ? indexBits2 : (indexBits2 - 1)); 1393 /* The index value for interpolating color comes from the secondary index bits for the texel 1394 if the mode has an index selection bit and its value is one, and from the primary index bits otherwise. 1395 The alpha index comes from the secondary index bits if the block has a secondary index and 1396 the block either doesn’t have an index selection bit or that bit is zero, and from the primary index bits otherwise. */ 1397 if (!indexSelectionBit) { 1398 r = bcdec__interpolate(endpoints[partitionSet * 2][0], endpoints[partitionSet * 2 + 1][0], weights, index); 1399 g = bcdec__interpolate(endpoints[partitionSet * 2][1], endpoints[partitionSet * 2 + 1][1], weights, index); 1400 b = bcdec__interpolate(endpoints[partitionSet * 2][2], endpoints[partitionSet * 2 + 1][2], weights, index); 1401 a = bcdec__interpolate(endpoints[partitionSet * 2][3], endpoints[partitionSet * 2 + 1][3], weights2, index2); 1402 } else { 1403 r = bcdec__interpolate(endpoints[partitionSet * 2][0], endpoints[partitionSet * 2 + 1][0], weights2, index2); 1404 g = bcdec__interpolate(endpoints[partitionSet * 2][1], endpoints[partitionSet * 2 + 1][1], weights2, index2); 1405 b = bcdec__interpolate(endpoints[partitionSet * 2][2], endpoints[partitionSet * 2 + 1][2], weights2, index2); 1406 a = bcdec__interpolate(endpoints[partitionSet * 2][3], endpoints[partitionSet * 2 + 1][3], weights, index); 1407 } 1408 } 1409 1410 switch (rotation) { 1411 case 1: { /* 01 – Block format is Scalar(R) Vector(AGB) - swap A and R */ 1412 bcdec__swap_values(&a, &r); 1413 } break; 1414 case 2: { /* 10 – Block format is Scalar(G) Vector(RAB) - swap A and G */ 1415 bcdec__swap_values(&a, &g); 1416 } break; 1417 case 3: { /* 11 - Block format is Scalar(B) Vector(RGA) - swap A and B */ 1418 bcdec__swap_values(&a, &b); 1419 } break; 1420 } 1421 1422 decompressed[j * 4 + 0] = r; 1423 decompressed[j * 4 + 1] = g; 1424 decompressed[j * 4 + 2] = b; 1425 decompressed[j * 4 + 3] = a; 1426 } 1427 1428 decompressed += destinationPitch; 1429 } 1430} 1431 1432#endif /* BCDEC_IMPLEMENTATION */ 1433 1434/* LICENSE: 1435 1436This software is available under 2 licenses -- choose whichever you prefer. 1437 1438------------------------------------------------------------------------------ 1439ALTERNATIVE A - MIT License 1440 1441Copyright (c) 2022 Sergii Kudlai 1442 1443Permission is hereby granted, free of charge, to any person obtaining a copy of 1444this software and associated documentation files (the "Software"), to deal in 1445the Software without restriction, including without limitation the rights to 1446use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies 1447of the Software, and to permit persons to whom the Software is furnished to do 1448so, subject to the following conditions: 1449 1450The above copyright notice and this permission notice shall be included in all 1451copies or substantial portions of the Software. 1452 1453THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1454IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1455FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 1456AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1457LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 1458OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 1459SOFTWARE. 1460 1461------------------------------------------------------------------------------ 1462ALTERNATIVE B - The Unlicense 1463 1464This is free and unencumbered software released into the public domain. 1465 1466Anyone is free to copy, modify, publish, use, compile, sell, or 1467distribute this software, either in source code form or as a compiled 1468binary, for any purpose, commercial or non-commercial, and by any 1469means. 1470 1471In jurisdictions that recognize copyright laws, the author or authors 1472of this software dedicate any and all copyright interest in the 1473software to the public domain. We make this dedication for the benefit 1474of the public at large and to the detriment of our heirs and 1475successors. We intend this dedication to be an overt act of 1476relinquishment in perpetuity of all present and future rights to this 1477software under copyright law. 1478 1479THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 1480EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 1481MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 1482IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR 1483OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 1484ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 1485OTHER DEALINGS IN THE SOFTWARE. 1486 1487For more information, please refer to <https://unlicense.org> 1488 1489*/