1/************************************************************************** 2 * 3 * Copyright (C) 2011 Red Hat Inc. 4 * 5 * Permission is hereby granted, free of charge, to any person obtaining a 6 * copy of this software and associated documentation files (the "Software"), 7 * to deal in the Software without restriction, including without limitation 8 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 9 * and/or sell copies of the Software, and to permit persons to whom the 10 * Software is furnished to do so, subject to the following conditions: 11 * 12 * The above copyright notice and this permission notice shall be included 13 * in all copies or substantial portions of the Software. 14 * 15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 16 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 19 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 20 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 21 * OTHER DEALINGS IN THE SOFTWARE. 22 * 23 **************************************************************************/ 24 25#include <stdio.h> 26#include "u_format.h" 27#include "u_format_rgtc.h" 28#include "util/u_math.h" 29#include "util/rgtc.h" 30 31void 32util_format_rgtc1_unorm_fetch_rgba_8unorm(uint8_t *dst, const uint8_t *src, unsigned i, unsigned j) 33{ 34 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, dst, 1); 35 dst[1] = 0; 36 dst[2] = 0; 37 dst[3] = 255; 38} 39 40void 41util_format_rgtc1_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 42{ 43 const unsigned bw = 4, bh = 4, comps = 4; 44 unsigned x, y, i, j; 45 unsigned block_size = 8; 46 47 for(y = 0; y < height; y += bh) { 48 const uint8_t *src = src_row; 49 for(x = 0; x < width; x += bw) { 50 for(j = 0; j < bh; ++j) { 51 for(i = 0; i < bw; ++i) { 52 uint8_t *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*comps; 53 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, dst, 1); 54 dst[1] = 0; 55 dst[2] = 0; 56 dst[3] = 255; 57 } 58 } 59 src += block_size; 60 } 61 src_row += src_stride; 62 } 63} 64 65void 66util_format_rgtc1_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride, const uint8_t *src_row, 67 unsigned src_stride, unsigned width, unsigned height) 68{ 69 const unsigned bw = 4, bh = 4, bytes_per_block = 8; 70 unsigned x, y, i, j; 71 72 for(y = 0; y < height; y += bh) { 73 uint8_t *dst = dst_row; 74 for(x = 0; x < width; x += bw) { 75 uint8_t tmp[4][4]; /* [bh][bw][comps] */ 76 for(j = 0; j < bh; ++j) { 77 for(i = 0; i < bw; ++i) { 78 tmp[j][i] = src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]; 79 } 80 } 81 util_format_unsigned_encode_rgtc_ubyte(dst, tmp, 4, 4); 82 dst += bytes_per_block; 83 } 84 dst_row += dst_stride / sizeof(*dst_row); 85 } 86} 87 88void 89util_format_rgtc1_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 90{ 91 unsigned x, y, i, j; 92 int block_size = 8; 93 for(y = 0; y < height; y += 4) { 94 const uint8_t *src = src_row; 95 for(x = 0; x < width; x += 4) { 96 for(j = 0; j < 4; ++j) { 97 for(i = 0; i < 4; ++i) { 98 float *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*4; 99 uint8_t tmp_r; 100 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, &tmp_r, 1); 101 dst[0] = ubyte_to_float(tmp_r); 102 dst[1] = 0.0; 103 dst[2] = 0.0; 104 dst[3] = 1.0; 105 } 106 } 107 src += block_size; 108 } 109 src_row += src_stride; 110 } 111} 112 113void 114util_format_rgtc1_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height) 115{ 116 const unsigned bw = 4, bh = 4, bytes_per_block = 8; 117 unsigned x, y, i, j; 118 119 for(y = 0; y < height; y += bh) { 120 uint8_t *dst = dst_row; 121 for(x = 0; x < width; x += bw) { 122 uint8_t tmp[4][4]; /* [bh][bw][comps] */ 123 for(j = 0; j < bh; ++j) { 124 for(i = 0; i < bw; ++i) { 125 tmp[j][i] = float_to_ubyte(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]); 126 } 127 } 128 util_format_unsigned_encode_rgtc_ubyte(dst, tmp, 4, 4); 129 dst += bytes_per_block; 130 } 131 dst_row += dst_stride / sizeof(*dst_row); 132 } 133} 134 135void 136util_format_rgtc1_unorm_fetch_rgba_float(float *dst, const uint8_t *src, unsigned i, unsigned j) 137{ 138 uint8_t tmp_r; 139 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, &tmp_r, 1); 140 dst[0] = ubyte_to_float(tmp_r); 141 dst[1] = 0.0; 142 dst[2] = 0.0; 143 dst[3] = 1.0; 144} 145 146void 147util_format_rgtc1_snorm_fetch_rgba_8unorm(UNUSED uint8_t *dst, UNUSED const uint8_t *src, 148 UNUSED unsigned i, UNUSED unsigned j) 149{ 150 fprintf(stderr,"%s\n", __func__); 151} 152 153void 154util_format_rgtc1_snorm_unpack_rgba_8unorm(UNUSED uint8_t *dst_row, UNUSED unsigned dst_stride, 155 UNUSED const uint8_t *src_row, UNUSED unsigned src_stride, 156 UNUSED unsigned width, UNUSED unsigned height) 157{ 158 fprintf(stderr,"%s\n", __func__); 159} 160 161void 162util_format_rgtc1_snorm_pack_rgba_8unorm(UNUSED uint8_t *dst_row, UNUSED unsigned dst_stride, 163 UNUSED const uint8_t *src_row, UNUSED unsigned src_stride, 164 UNUSED unsigned width, UNUSED unsigned height) 165{ 166 fprintf(stderr,"%s\n", __func__); 167} 168 169void 170util_format_rgtc1_snorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height) 171{ 172 const unsigned bw = 4, bh = 4, bytes_per_block = 8; 173 unsigned x, y, i, j; 174 175 for(y = 0; y < height; y += bh) { 176 int8_t *dst = (int8_t *)dst_row; 177 for(x = 0; x < width; x += bw) { 178 int8_t tmp[4][4]; /* [bh][bw][comps] */ 179 for(j = 0; j < bh; ++j) { 180 for(i = 0; i < bw; ++i) { 181 tmp[j][i] = float_to_byte_tex(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]); 182 } 183 } 184 util_format_signed_encode_rgtc_ubyte(dst, tmp, 4, 4); 185 dst += bytes_per_block; 186 } 187 dst_row += dst_stride / sizeof(*dst_row); 188 } 189} 190 191void 192util_format_rgtc1_snorm_unpack_rgba_float(float *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 193{ 194 unsigned x, y, i, j; 195 int block_size = 8; 196 for(y = 0; y < height; y += 4) { 197 const int8_t *src = (int8_t *)src_row; 198 for(x = 0; x < width; x += 4) { 199 for(j = 0; j < 4; ++j) { 200 for(i = 0; i < 4; ++i) { 201 float *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*4; 202 int8_t tmp_r; 203 util_format_signed_fetch_texel_rgtc(0, src, i, j, &tmp_r, 1); 204 dst[0] = byte_to_float_tex(tmp_r); 205 dst[1] = 0.0; 206 dst[2] = 0.0; 207 dst[3] = 1.0; 208 } 209 } 210 src += block_size; 211 } 212 src_row += src_stride; 213 } 214} 215 216void 217util_format_rgtc1_snorm_fetch_rgba_float(float *dst, const uint8_t *src, unsigned i, unsigned j) 218{ 219 int8_t tmp_r; 220 util_format_signed_fetch_texel_rgtc(0, (int8_t *)src, i, j, &tmp_r, 1); 221 dst[0] = byte_to_float_tex(tmp_r); 222 dst[1] = 0.0; 223 dst[2] = 0.0; 224 dst[3] = 1.0; 225} 226 227 228void 229util_format_rgtc2_unorm_fetch_rgba_8unorm(uint8_t *dst, const uint8_t *src, unsigned i, unsigned j) 230{ 231 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, dst, 2); 232 util_format_unsigned_fetch_texel_rgtc(0, src + 8, i, j, dst + 1, 2); 233 dst[2] = 0; 234 dst[3] = 255; 235} 236 237void 238util_format_rgtc2_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 239{ 240 const unsigned bw = 4, bh = 4, comps = 4; 241 unsigned x, y, i, j; 242 unsigned block_size = 16; 243 244 for(y = 0; y < height; y += bh) { 245 const uint8_t *src = src_row; 246 for(x = 0; x < width; x += bw) { 247 for(j = 0; j < bh; ++j) { 248 for(i = 0; i < bw; ++i) { 249 uint8_t *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*comps; 250 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, dst, 2); 251 util_format_unsigned_fetch_texel_rgtc(0, src + 8, i, j, dst + 1, 2); 252 dst[2] = 0; 253 dst[3] = 255; 254 } 255 } 256 src += block_size; 257 } 258 src_row += src_stride; 259 } 260} 261 262void 263util_format_rgtc2_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 264{ 265 const unsigned bw = 4, bh = 4, bytes_per_block = 16; 266 unsigned x, y, i, j; 267 268 for(y = 0; y < height; y += bh) { 269 uint8_t *dst = dst_row; 270 for(x = 0; x < width; x += bw) { 271 uint8_t tmp_r[4][4]; /* [bh][bw] */ 272 uint8_t tmp_g[4][4]; /* [bh][bw] */ 273 for(j = 0; j < bh; ++j) { 274 for(i = 0; i < bw; ++i) { 275 tmp_r[j][i] = src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]; 276 tmp_g[j][i] = src_row[((y + j)*src_stride/sizeof(*src_row) + (x + i)*4) + 1]; 277 } 278 } 279 util_format_unsigned_encode_rgtc_ubyte(dst, tmp_r, 4, 4); 280 util_format_unsigned_encode_rgtc_ubyte(dst + 8, tmp_g, 4, 4); 281 dst += bytes_per_block; 282 } 283 dst_row += dst_stride / sizeof(*dst_row); 284 } 285} 286 287void 288util_format_rxtc2_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height, unsigned chan2off) 289{ 290 const unsigned bw = 4, bh = 4, bytes_per_block = 16; 291 unsigned x, y, i, j; 292 293 for(y = 0; y < height; y += bh) { 294 uint8_t *dst = dst_row; 295 for(x = 0; x < width; x += bw) { 296 uint8_t tmp_r[4][4]; /* [bh][bw][comps] */ 297 uint8_t tmp_g[4][4]; /* [bh][bw][comps] */ 298 for(j = 0; j < bh; ++j) { 299 for(i = 0; i < bw; ++i) { 300 tmp_r[j][i] = float_to_ubyte(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]); 301 tmp_g[j][i] = float_to_ubyte(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4 + chan2off]); 302 } 303 } 304 util_format_unsigned_encode_rgtc_ubyte(dst, tmp_r, 4, 4); 305 util_format_unsigned_encode_rgtc_ubyte(dst + 8, tmp_g, 4, 4); 306 dst += bytes_per_block; 307 } 308 dst_row += dst_stride / sizeof(*dst_row); 309 } 310} 311 312void 313util_format_rgtc2_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height) 314{ 315 util_format_rxtc2_unorm_pack_rgba_float(dst_row, dst_stride, src_row, src_stride, width, height, 1); 316} 317 318void 319util_format_rgtc2_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 320{ 321 unsigned x, y, i, j; 322 int block_size = 16; 323 for(y = 0; y < height; y += 4) { 324 const uint8_t *src = src_row; 325 for(x = 0; x < width; x += 4) { 326 for(j = 0; j < 4; ++j) { 327 for(i = 0; i < 4; ++i) { 328 float *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*4; 329 uint8_t tmp_r, tmp_g; 330 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, &tmp_r, 2); 331 util_format_unsigned_fetch_texel_rgtc(0, src + 8, i, j, &tmp_g, 2); 332 dst[0] = ubyte_to_float(tmp_r); 333 dst[1] = ubyte_to_float(tmp_g); 334 dst[2] = 0.0; 335 dst[3] = 1.0; 336 } 337 } 338 src += block_size; 339 } 340 src_row += src_stride; 341 } 342} 343 344void 345util_format_rgtc2_unorm_fetch_rgba_float(float *dst, const uint8_t *src, unsigned i, unsigned j) 346{ 347 uint8_t tmp_r, tmp_g; 348 util_format_unsigned_fetch_texel_rgtc(0, src, i, j, &tmp_r, 2); 349 util_format_unsigned_fetch_texel_rgtc(0, src + 8, i, j, &tmp_g, 2); 350 dst[0] = ubyte_to_float(tmp_r); 351 dst[1] = ubyte_to_float(tmp_g); 352 dst[2] = 0.0; 353 dst[3] = 1.0; 354} 355 356 357void 358util_format_rgtc2_snorm_fetch_rgba_8unorm(UNUSED uint8_t *dst, UNUSED const uint8_t *src, 359 UNUSED unsigned i, UNUSED unsigned j) 360{ 361 fprintf(stderr,"%s\n", __func__); 362} 363 364void 365util_format_rgtc2_snorm_unpack_rgba_8unorm(UNUSED uint8_t *dst_row, UNUSED unsigned dst_stride, 366 UNUSED const uint8_t *src_row, UNUSED unsigned src_stride, 367 UNUSED unsigned width, UNUSED unsigned height) 368{ 369 fprintf(stderr,"%s\n", __func__); 370} 371 372void 373util_format_rgtc2_snorm_pack_rgba_8unorm(UNUSED uint8_t *dst_row, UNUSED unsigned dst_stride, 374 UNUSED const uint8_t *src_row, UNUSED unsigned src_stride, 375 UNUSED unsigned width, UNUSED unsigned height) 376{ 377 fprintf(stderr,"%s\n", __func__); 378} 379 380void 381util_format_rgtc2_snorm_unpack_rgba_float(float *dst_row, unsigned dst_stride, const uint8_t *src_row, unsigned src_stride, unsigned width, unsigned height) 382{ 383 unsigned x, y, i, j; 384 int block_size = 16; 385 for(y = 0; y < height; y += 4) { 386 const int8_t *src = (int8_t *)src_row; 387 for(x = 0; x < width; x += 4) { 388 for(j = 0; j < 4; ++j) { 389 for(i = 0; i < 4; ++i) { 390 float *dst = dst_row + (y + j)*dst_stride/sizeof(*dst_row) + (x + i)*4; 391 int8_t tmp_r, tmp_g; 392 util_format_signed_fetch_texel_rgtc(0, src, i, j, &tmp_r, 2); 393 util_format_signed_fetch_texel_rgtc(0, src + 8, i, j, &tmp_g, 2); 394 dst[0] = byte_to_float_tex(tmp_r); 395 dst[1] = byte_to_float_tex(tmp_g); 396 dst[2] = 0.0; 397 dst[3] = 1.0; 398 } 399 } 400 src += block_size; 401 } 402 src_row += src_stride; 403 } 404} 405 406void 407util_format_rxtc2_snorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height, unsigned chan2off) 408{ 409 const unsigned bw = 4, bh = 4, bytes_per_block = 16; 410 unsigned x, y, i, j; 411 412 for(y = 0; y < height; y += bh) { 413 int8_t *dst = (int8_t *)dst_row; 414 for(x = 0; x < width; x += bw) { 415 int8_t tmp_r[4][4]; /* [bh][bw][comps] */ 416 int8_t tmp_g[4][4]; /* [bh][bw][comps] */ 417 for(j = 0; j < bh; ++j) { 418 for(i = 0; i < bw; ++i) { 419 tmp_r[j][i] = float_to_byte_tex(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4]); 420 tmp_g[j][i] = float_to_byte_tex(src_row[(y + j)*src_stride/sizeof(*src_row) + (x + i)*4 + chan2off]); 421 } 422 } 423 util_format_signed_encode_rgtc_ubyte(dst, tmp_r, 4, 4); 424 util_format_signed_encode_rgtc_ubyte(dst + 8, tmp_g, 4, 4); 425 dst += bytes_per_block; 426 } 427 dst_row += dst_stride / sizeof(*dst_row); 428 } 429} 430 431void 432util_format_rgtc2_snorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride, const float *src_row, unsigned src_stride, unsigned width, unsigned height) 433{ 434 util_format_rxtc2_snorm_pack_rgba_float(dst_row, dst_stride, src_row, src_stride, width, height, 1); 435} 436 437void 438util_format_rgtc2_snorm_fetch_rgba_float(float *dst, const uint8_t *src, unsigned i, unsigned j) 439{ 440 int8_t tmp_r, tmp_g; 441 util_format_signed_fetch_texel_rgtc(0, (int8_t *)src, i, j, &tmp_r, 2); 442 util_format_signed_fetch_texel_rgtc(0, (int8_t *)src + 8, i, j, &tmp_g, 2); 443 dst[0] = byte_to_float_tex(tmp_r); 444 dst[1] = byte_to_float_tex(tmp_g); 445 dst[2] = 0.0; 446 dst[3] = 1.0; 447} 448 449