radeon_texture.c revision 3996ed555e0a024051e4d161c8d31b2530d8cdc5
1/* 2 * Copyright (C) 2009 Maciej Cencora. 3 * Copyright (C) 2008 Nicolai Haehnle. 4 * Copyright (C) The Weather Channel, Inc. 2002. All Rights Reserved. 5 * 6 * The Weather Channel (TM) funded Tungsten Graphics to develop the 7 * initial release of the Radeon 8500 driver under the XFree86 license. 8 * This notice must be preserved. 9 * 10 * Permission is hereby granted, free of charge, to any person obtaining 11 * a copy of this software and associated documentation files (the 12 * "Software"), to deal in the Software without restriction, including 13 * without limitation the rights to use, copy, modify, merge, publish, 14 * distribute, sublicense, and/or sell copies of the Software, and to 15 * permit persons to whom the Software is furnished to do so, subject to 16 * the following conditions: 17 * 18 * The above copyright notice and this permission notice (including the 19 * next paragraph) shall be included in all copies or substantial 20 * portions of the Software. 21 * 22 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 23 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 24 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 25 * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE 26 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 27 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 28 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 29 * 30 */ 31 32#include "main/glheader.h" 33#include "main/imports.h" 34#include "main/context.h" 35#include "main/enums.h" 36#include "main/mfeatures.h" 37#include "main/mipmap.h" 38#include "main/pbo.h" 39#include "main/texcompress.h" 40#include "main/texstore.h" 41#include "main/teximage.h" 42#include "main/texobj.h" 43#include "drivers/common/meta.h" 44 45#include "xmlpool.h" /* for symbolic values of enum-type options */ 46 47#include "radeon_common.h" 48 49#include "radeon_mipmap_tree.h" 50 51 52void copy_rows(void* dst, GLuint dststride, const void* src, GLuint srcstride, 53 GLuint numrows, GLuint rowsize) 54{ 55 assert(rowsize <= dststride); 56 assert(rowsize <= srcstride); 57 58 radeon_print(RADEON_TEXTURE, RADEON_TRACE, 59 "%s dst %p, stride %u, src %p, stride %u, " 60 "numrows %u, rowsize %u.\n", 61 __func__, dst, dststride, 62 src, srcstride, 63 numrows, rowsize); 64 65 if (rowsize == srcstride && rowsize == dststride) { 66 memcpy(dst, src, numrows*rowsize); 67 } else { 68 GLuint i; 69 for(i = 0; i < numrows; ++i) { 70 memcpy(dst, src, rowsize); 71 dst += dststride; 72 src += srcstride; 73 } 74 } 75} 76 77/* textures */ 78/** 79 * Allocate an empty texture image object. 80 */ 81struct gl_texture_image *radeonNewTextureImage(struct gl_context *ctx) 82{ 83 return CALLOC(sizeof(radeon_texture_image)); 84} 85 86 87/** 88 * Delete a texture image object. 89 */ 90static void 91radeonDeleteTextureImage(struct gl_context *ctx, struct gl_texture_image *img) 92{ 93 /* nothing special (yet) for radeon_texture_image */ 94 _mesa_delete_texture_image(ctx, img); 95} 96 97 98/** 99 * Free memory associated with this texture image. 100 */ 101void radeonFreeTextureImageBuffer(struct gl_context *ctx, struct gl_texture_image *timage) 102{ 103 radeon_texture_image* image = get_radeon_texture_image(timage); 104 105 if (image->mt) { 106 radeon_miptree_unreference(&image->mt); 107 assert(!image->base.Buffer); 108 } else { 109 _swrast_free_texture_image_buffer(ctx, timage); 110 } 111 if (image->bo) { 112 radeon_bo_unref(image->bo); 113 image->bo = NULL; 114 } 115 if (image->base.Buffer) { 116 _mesa_align_free(image->base.Buffer); 117 image->base.Buffer = NULL; 118 } 119 120 if (image->base.ImageOffsets) { 121 free(image->base.ImageOffsets); 122 image->base.ImageOffsets = NULL; 123 } 124} 125 126/* Set Data pointer and additional data for mapped texture image */ 127static void teximage_set_map_data(radeon_texture_image *image) 128{ 129 radeon_mipmap_level *lvl; 130 131 if (!image->mt) { 132 radeon_warning("%s(%p) Trying to set map data without miptree.\n", 133 __func__, image); 134 135 return; 136 } 137 138 lvl = &image->mt->levels[image->mtlevel]; 139 140 image->base.Data = image->mt->bo->ptr + lvl->faces[image->mtface].offset; 141 image->base.RowStride = lvl->rowstride / _mesa_get_format_bytes(image->base.Base.TexFormat); 142} 143 144 145/** 146 * Map a single texture image for glTexImage and friends. 147 */ 148void radeon_teximage_map(radeon_texture_image *image, GLboolean write_enable) 149{ 150 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 151 "%s(img %p), write_enable %s.\n", 152 __func__, image, 153 write_enable ? "true": "false"); 154 if (image->mt) { 155 assert(!image->base.Data); 156 157 radeon_bo_map(image->mt->bo, write_enable); 158 teximage_set_map_data(image); 159 } 160} 161 162 163void radeon_teximage_unmap(radeon_texture_image *image) 164{ 165 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 166 "%s(img %p)\n", 167 __func__, image); 168 if (image->mt) { 169 assert(image->base.Data); 170 171 image->base.Data = 0; 172 radeon_bo_unmap(image->mt->bo); 173 } 174} 175 176static void map_override(struct gl_context *ctx, radeonTexObj *t) 177{ 178 radeon_texture_image *img = get_radeon_texture_image(t->base.Image[0][0]); 179 180 radeon_bo_map(t->bo, GL_FALSE); 181 182 img->base.Data = t->bo->ptr; 183} 184 185static void unmap_override(struct gl_context *ctx, radeonTexObj *t) 186{ 187 radeon_texture_image *img = get_radeon_texture_image(t->base.Image[0][0]); 188 189 radeon_bo_unmap(t->bo); 190 191 img->base.Data = NULL; 192} 193 194/** 195 * Map a validated texture for reading during software rendering. 196 */ 197void radeonMapTexture(struct gl_context *ctx, struct gl_texture_object *texObj) 198{ 199 radeonTexObj* t = radeon_tex_obj(texObj); 200 int face, level; 201 202 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 203 "%s(%p, tex %p)\n", 204 __func__, ctx, texObj); 205 206 if (!radeon_validate_texture_miptree(ctx, texObj)) { 207 radeon_error("%s(%p, tex %p) Failed to validate miptree for " 208 "sw fallback.\n", 209 __func__, ctx, texObj); 210 return; 211 } 212 213 if (t->image_override && t->bo) { 214 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 215 "%s(%p, tex %p) Work around for missing miptree in r100.\n", 216 __func__, ctx, texObj); 217 218 map_override(ctx, t); 219 } 220 221 /* for r100 3D sw fallbacks don't have mt */ 222 if (!t->mt) { 223 radeon_warning("%s(%p, tex %p) No miptree in texture.\n", 224 __func__, ctx, texObj); 225 return; 226 } 227 228 radeon_bo_map(t->mt->bo, GL_FALSE); 229 for(face = 0; face < t->mt->faces; ++face) { 230 for(level = t->minLod; level <= t->maxLod; ++level) 231 teximage_set_map_data(get_radeon_texture_image(texObj->Image[face][level])); 232 } 233} 234 235void radeonUnmapTexture(struct gl_context *ctx, struct gl_texture_object *texObj) 236{ 237 radeonTexObj* t = radeon_tex_obj(texObj); 238 int face, level; 239 240 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 241 "%s(%p, tex %p)\n", 242 __func__, ctx, texObj); 243 244 if (t->image_override && t->bo) 245 unmap_override(ctx, t); 246 /* for r100 3D sw fallbacks don't have mt */ 247 if (!t->mt) 248 return; 249 250 for(face = 0; face < t->mt->faces; ++face) { 251 for(level = t->minLod; level <= t->maxLod; ++level) { 252 radeon_texture_image *image = 253 get_radeon_texture_image(texObj->Image[face][level]); 254 image->base.Data = NULL; 255 } 256 } 257 radeon_bo_unmap(t->mt->bo); 258} 259 260 261/** 262 * Map texture memory/buffer into user space. 263 * Note: the region of interest parameters are ignored here. 264 * \param mapOut returns start of mapping of region of interest 265 * \param rowStrideOut returns row stride in bytes 266 */ 267static void 268radeon_map_texture_image(struct gl_context *ctx, 269 struct gl_texture_image *texImage, 270 GLuint slice, 271 GLuint x, GLuint y, GLuint w, GLuint h, 272 GLbitfield mode, 273 GLubyte **map, 274 GLint *stride) 275{ 276 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 277 radeon_texture_image *image = get_radeon_texture_image(texImage); 278 radeon_mipmap_tree *mt = image->mt; 279 GLuint texel_size = _mesa_get_format_bytes(texImage->TexFormat); 280 GLuint width = texImage->Width; 281 GLuint height = texImage->Height; 282 struct radeon_bo *bo = !image->mt ? image->bo : image->mt->bo; 283 unsigned int bw, bh; 284 GLboolean write = (mode & GL_MAP_WRITE_BIT) != 0; 285 286 _mesa_get_format_block_size(texImage->TexFormat, &bw, &bh); 287 assert(y % bh == 0); 288 y /= bh; 289 height /= bh; 290 291 if (bo && radeon_bo_is_referenced_by_cs(bo, rmesa->cmdbuf.cs)) { 292 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 293 "%s for texture that is " 294 "queued for GPU processing.\n", 295 __func__); 296 radeon_firevertices(rmesa); 297 } 298 299 if (image->bo) { 300 /* TFP case */ 301 radeon_bo_map(image->bo, write); 302 *stride = get_texture_image_row_stride(rmesa, texImage->TexFormat, width, 0); 303 *map = bo->ptr; 304 } else if (likely(mt)) { 305 radeon_bo_map(mt->bo, write); 306 radeon_mipmap_level *lvl = &image->mt->levels[texImage->Level]; 307 void *base = mt->bo->ptr + lvl->faces[image->mtface].offset; 308 309 *stride = lvl->rowstride; 310 *map = base + (slice * height) * *stride; 311 } else { 312 /* texture data is in malloc'd memory */ 313 314 assert(map); 315 316 *stride = _mesa_format_row_stride(texImage->TexFormat, width); 317 *map = image->base.Buffer + (slice * height) * *stride; 318 } 319 320 *map += y * *stride + x * texel_size; 321} 322 323static void 324radeon_unmap_texture_image(struct gl_context *ctx, 325 struct gl_texture_image *texImage, GLuint slice) 326{ 327 radeon_texture_image *image = get_radeon_texture_image(texImage); 328 329 if (image->bo) 330 radeon_bo_unmap(image->bo); 331 else if (image->mt) 332 radeon_bo_unmap(image->mt->bo); 333} 334 335void radeonGenerateMipmap(struct gl_context* ctx, GLenum target, struct gl_texture_object *texObj) 336{ 337 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 338 struct radeon_bo *bo; 339 GLuint face = _mesa_tex_target_to_face(target); 340 radeon_texture_image *baseimage = get_radeon_texture_image(texObj->Image[face][texObj->BaseLevel]); 341 bo = !baseimage->mt ? baseimage->bo : baseimage->mt->bo; 342 343 radeon_print(RADEON_TEXTURE, RADEON_TRACE, 344 "%s(%p, target %s, tex %p)\n", 345 __func__, ctx, _mesa_lookup_enum_by_nr(target), 346 texObj); 347 348 if (bo && radeon_bo_is_referenced_by_cs(bo, rmesa->cmdbuf.cs)) { 349 radeon_print(RADEON_TEXTURE, RADEON_NORMAL, 350 "%s(%p, tex %p) Trying to generate mipmap for texture " 351 "in processing by GPU.\n", 352 __func__, ctx, texObj); 353 radeon_firevertices(rmesa); 354 } 355 356 if (_mesa_meta_check_generate_mipmap_fallback(ctx, target, texObj)) { 357 _mesa_generate_mipmap(ctx, target, texObj); 358 } else { 359 _mesa_meta_GenerateMipmap(ctx, target, texObj); 360 } 361} 362 363 364/* try to find a format which will only need a memcopy */ 365static gl_format radeonChoose8888TexFormat(radeonContextPtr rmesa, 366 GLenum srcFormat, 367 GLenum srcType, GLboolean fbo) 368{ 369 const GLuint ui = 1; 370 const GLubyte littleEndian = *((const GLubyte *)&ui); 371 372 /* r100 can only do this */ 373 if (IS_R100_CLASS(rmesa->radeonScreen) || fbo) 374 return _dri_texformat_argb8888; 375 376 if ((srcFormat == GL_RGBA && srcType == GL_UNSIGNED_INT_8_8_8_8) || 377 (srcFormat == GL_RGBA && srcType == GL_UNSIGNED_BYTE && !littleEndian) || 378 (srcFormat == GL_ABGR_EXT && srcType == GL_UNSIGNED_INT_8_8_8_8_REV) || 379 (srcFormat == GL_ABGR_EXT && srcType == GL_UNSIGNED_BYTE && littleEndian)) { 380 return MESA_FORMAT_RGBA8888; 381 } else if ((srcFormat == GL_RGBA && srcType == GL_UNSIGNED_INT_8_8_8_8_REV) || 382 (srcFormat == GL_RGBA && srcType == GL_UNSIGNED_BYTE && littleEndian) || 383 (srcFormat == GL_ABGR_EXT && srcType == GL_UNSIGNED_INT_8_8_8_8) || 384 (srcFormat == GL_ABGR_EXT && srcType == GL_UNSIGNED_BYTE && !littleEndian)) { 385 return MESA_FORMAT_RGBA8888_REV; 386 } else if (IS_R200_CLASS(rmesa->radeonScreen)) { 387 return _dri_texformat_argb8888; 388 } else if (srcFormat == GL_BGRA && ((srcType == GL_UNSIGNED_BYTE && !littleEndian) || 389 srcType == GL_UNSIGNED_INT_8_8_8_8)) { 390 return MESA_FORMAT_ARGB8888_REV; 391 } else if (srcFormat == GL_BGRA && ((srcType == GL_UNSIGNED_BYTE && littleEndian) || 392 srcType == GL_UNSIGNED_INT_8_8_8_8_REV)) { 393 return MESA_FORMAT_ARGB8888; 394 } else 395 return _dri_texformat_argb8888; 396} 397 398gl_format radeonChooseTextureFormat_mesa(struct gl_context * ctx, 399 GLint internalFormat, 400 GLenum format, 401 GLenum type) 402{ 403 return radeonChooseTextureFormat(ctx, internalFormat, format, 404 type, 0); 405} 406 407gl_format radeonChooseTextureFormat(struct gl_context * ctx, 408 GLint internalFormat, 409 GLenum format, 410 GLenum type, GLboolean fbo) 411{ 412 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 413 const GLboolean do32bpt = 414 (rmesa->texture_depth == DRI_CONF_TEXTURE_DEPTH_32); 415 const GLboolean force16bpt = 416 (rmesa->texture_depth == DRI_CONF_TEXTURE_DEPTH_FORCE_16); 417 (void)format; 418 419 radeon_print(RADEON_TEXTURE, RADEON_TRACE, 420 "%s InternalFormat=%s(%d) type=%s format=%s\n", 421 __func__, 422 _mesa_lookup_enum_by_nr(internalFormat), internalFormat, 423 _mesa_lookup_enum_by_nr(type), _mesa_lookup_enum_by_nr(format)); 424 radeon_print(RADEON_TEXTURE, RADEON_TRACE, 425 "%s do32bpt=%d force16bpt=%d\n", 426 __func__, do32bpt, force16bpt); 427 428 switch (internalFormat) { 429 case 4: 430 case GL_RGBA: 431 case GL_COMPRESSED_RGBA: 432 switch (type) { 433 case GL_UNSIGNED_INT_10_10_10_2: 434 case GL_UNSIGNED_INT_2_10_10_10_REV: 435 return do32bpt ? _dri_texformat_argb8888 : 436 _dri_texformat_argb1555; 437 case GL_UNSIGNED_SHORT_4_4_4_4: 438 case GL_UNSIGNED_SHORT_4_4_4_4_REV: 439 return _dri_texformat_argb4444; 440 case GL_UNSIGNED_SHORT_5_5_5_1: 441 case GL_UNSIGNED_SHORT_1_5_5_5_REV: 442 return _dri_texformat_argb1555; 443 default: 444 return do32bpt ? radeonChoose8888TexFormat(rmesa, format, type, fbo) : 445 _dri_texformat_argb4444; 446 } 447 448 case 3: 449 case GL_RGB: 450 case GL_COMPRESSED_RGB: 451 switch (type) { 452 case GL_UNSIGNED_SHORT_4_4_4_4: 453 case GL_UNSIGNED_SHORT_4_4_4_4_REV: 454 return _dri_texformat_argb4444; 455 case GL_UNSIGNED_SHORT_5_5_5_1: 456 case GL_UNSIGNED_SHORT_1_5_5_5_REV: 457 return _dri_texformat_argb1555; 458 case GL_UNSIGNED_SHORT_5_6_5: 459 case GL_UNSIGNED_SHORT_5_6_5_REV: 460 return _dri_texformat_rgb565; 461 default: 462 return do32bpt ? _dri_texformat_argb8888 : 463 _dri_texformat_rgb565; 464 } 465 466 case GL_RGBA8: 467 case GL_RGB10_A2: 468 case GL_RGBA12: 469 case GL_RGBA16: 470 return !force16bpt ? 471 radeonChoose8888TexFormat(rmesa, format, type, fbo) : 472 _dri_texformat_argb4444; 473 474 case GL_RGBA4: 475 case GL_RGBA2: 476 return _dri_texformat_argb4444; 477 478 case GL_RGB5_A1: 479 return _dri_texformat_argb1555; 480 481 case GL_RGB8: 482 case GL_RGB10: 483 case GL_RGB12: 484 case GL_RGB16: 485 return !force16bpt ? _dri_texformat_argb8888 : 486 _dri_texformat_rgb565; 487 488 case GL_RGB5: 489 case GL_RGB4: 490 case GL_R3_G3_B2: 491 return _dri_texformat_rgb565; 492 493 case GL_ALPHA: 494 case GL_ALPHA4: 495 case GL_ALPHA8: 496 case GL_ALPHA12: 497 case GL_ALPHA16: 498 case GL_COMPRESSED_ALPHA: 499 /* r200: can't use a8 format since interpreting hw I8 as a8 would result 500 in wrong rgb values (same as alpha value instead of 0). */ 501 if (IS_R200_CLASS(rmesa->radeonScreen)) 502 return _dri_texformat_al88; 503 else 504 return MESA_FORMAT_A8; 505 case 1: 506 case GL_LUMINANCE: 507 case GL_LUMINANCE4: 508 case GL_LUMINANCE8: 509 case GL_LUMINANCE12: 510 case GL_LUMINANCE16: 511 case GL_COMPRESSED_LUMINANCE: 512 return MESA_FORMAT_L8; 513 514 case 2: 515 case GL_LUMINANCE_ALPHA: 516 case GL_LUMINANCE4_ALPHA4: 517 case GL_LUMINANCE6_ALPHA2: 518 case GL_LUMINANCE8_ALPHA8: 519 case GL_LUMINANCE12_ALPHA4: 520 case GL_LUMINANCE12_ALPHA12: 521 case GL_LUMINANCE16_ALPHA16: 522 case GL_COMPRESSED_LUMINANCE_ALPHA: 523 return _dri_texformat_al88; 524 525 case GL_INTENSITY: 526 case GL_INTENSITY4: 527 case GL_INTENSITY8: 528 case GL_INTENSITY12: 529 case GL_INTENSITY16: 530 case GL_COMPRESSED_INTENSITY: 531 return MESA_FORMAT_I8; 532 533 case GL_YCBCR_MESA: 534 if (type == GL_UNSIGNED_SHORT_8_8_APPLE || 535 type == GL_UNSIGNED_BYTE) 536 return MESA_FORMAT_YCBCR; 537 else 538 return MESA_FORMAT_YCBCR_REV; 539 540 case GL_RGB_S3TC: 541 case GL_RGB4_S3TC: 542 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT: 543 return MESA_FORMAT_RGB_DXT1; 544 545 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT: 546 return MESA_FORMAT_RGBA_DXT1; 547 548 case GL_RGBA_S3TC: 549 case GL_RGBA4_S3TC: 550 case GL_COMPRESSED_RGBA_S3TC_DXT3_EXT: 551 return MESA_FORMAT_RGBA_DXT3; 552 553 case GL_COMPRESSED_RGBA_S3TC_DXT5_EXT: 554 return MESA_FORMAT_RGBA_DXT5; 555 556 case GL_ALPHA16F_ARB: 557 return MESA_FORMAT_ALPHA_FLOAT16; 558 case GL_ALPHA32F_ARB: 559 return MESA_FORMAT_ALPHA_FLOAT32; 560 case GL_LUMINANCE16F_ARB: 561 return MESA_FORMAT_LUMINANCE_FLOAT16; 562 case GL_LUMINANCE32F_ARB: 563 return MESA_FORMAT_LUMINANCE_FLOAT32; 564 case GL_LUMINANCE_ALPHA16F_ARB: 565 return MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16; 566 case GL_LUMINANCE_ALPHA32F_ARB: 567 return MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32; 568 case GL_INTENSITY16F_ARB: 569 return MESA_FORMAT_INTENSITY_FLOAT16; 570 case GL_INTENSITY32F_ARB: 571 return MESA_FORMAT_INTENSITY_FLOAT32; 572 case GL_RGB16F_ARB: 573 return MESA_FORMAT_RGBA_FLOAT16; 574 case GL_RGB32F_ARB: 575 return MESA_FORMAT_RGBA_FLOAT32; 576 case GL_RGBA16F_ARB: 577 return MESA_FORMAT_RGBA_FLOAT16; 578 case GL_RGBA32F_ARB: 579 return MESA_FORMAT_RGBA_FLOAT32; 580 581 case GL_DEPTH_COMPONENT: 582 case GL_DEPTH_COMPONENT16: 583 case GL_DEPTH_COMPONENT24: 584 case GL_DEPTH_COMPONENT32: 585 case GL_DEPTH_STENCIL_EXT: 586 case GL_DEPTH24_STENCIL8_EXT: 587 return MESA_FORMAT_S8_Z24; 588 589 /* EXT_texture_sRGB */ 590 case GL_SRGB: 591 case GL_SRGB8: 592 case GL_SRGB_ALPHA: 593 case GL_SRGB8_ALPHA8: 594 case GL_COMPRESSED_SRGB: 595 case GL_COMPRESSED_SRGB_ALPHA: 596 return MESA_FORMAT_SARGB8; 597 598 case GL_SLUMINANCE: 599 case GL_SLUMINANCE8: 600 case GL_COMPRESSED_SLUMINANCE: 601 return MESA_FORMAT_SL8; 602 603 case GL_SLUMINANCE_ALPHA: 604 case GL_SLUMINANCE8_ALPHA8: 605 case GL_COMPRESSED_SLUMINANCE_ALPHA: 606 return MESA_FORMAT_SLA8; 607 608 case GL_COMPRESSED_SRGB_S3TC_DXT1_EXT: 609 return MESA_FORMAT_SRGB_DXT1; 610 case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT: 611 return MESA_FORMAT_SRGBA_DXT1; 612 case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT: 613 return MESA_FORMAT_SRGBA_DXT3; 614 case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT: 615 return MESA_FORMAT_SRGBA_DXT5; 616 617 default: 618 _mesa_problem(ctx, 619 "unexpected internalFormat 0x%x in %s", 620 (int)internalFormat, __func__); 621 return MESA_FORMAT_NONE; 622 } 623 624 return MESA_FORMAT_NONE; /* never get here */ 625} 626 627/** Check if given image is valid within current texture object. 628 */ 629static int image_matches_texture_obj(struct gl_texture_object *texObj, 630 struct gl_texture_image *texImage, 631 unsigned level) 632{ 633 const struct gl_texture_image *baseImage = texObj->Image[0][texObj->BaseLevel]; 634 635 if (!baseImage) 636 return 0; 637 638 if (level < texObj->BaseLevel || level > texObj->MaxLevel) 639 return 0; 640 641 const unsigned levelDiff = level - texObj->BaseLevel; 642 const unsigned refWidth = MAX2(baseImage->Width >> levelDiff, 1); 643 const unsigned refHeight = MAX2(baseImage->Height >> levelDiff, 1); 644 const unsigned refDepth = MAX2(baseImage->Depth >> levelDiff, 1); 645 646 return (texImage->Width == refWidth && 647 texImage->Height == refHeight && 648 texImage->Depth == refDepth); 649} 650 651static void teximage_assign_miptree(radeonContextPtr rmesa, 652 struct gl_texture_object *texObj, 653 struct gl_texture_image *texImage, 654 unsigned face, 655 unsigned level) 656{ 657 radeonTexObj *t = radeon_tex_obj(texObj); 658 radeon_texture_image* image = get_radeon_texture_image(texImage); 659 660 /* Since miptree holds only images for levels <BaseLevel..MaxLevel> 661 * don't allocate the miptree if the teximage won't fit. 662 */ 663 if (!image_matches_texture_obj(texObj, texImage, level)) 664 return; 665 666 /* Try using current miptree, or create new if there isn't any */ 667 if (!t->mt || !radeon_miptree_matches_image(t->mt, texImage, face, level)) { 668 radeon_miptree_unreference(&t->mt); 669 radeon_try_alloc_miptree(rmesa, t); 670 radeon_print(RADEON_TEXTURE, RADEON_NORMAL, 671 "%s: texObj %p, texImage %p, face %d, level %d, " 672 "texObj miptree doesn't match, allocated new miptree %p\n", 673 __FUNCTION__, texObj, texImage, face, level, t->mt); 674 } 675 676 /* Miptree alocation may have failed, 677 * when there was no image for baselevel specified */ 678 if (t->mt) { 679 image->mtface = face; 680 image->mtlevel = level; 681 radeon_miptree_reference(t->mt, &image->mt); 682 } else 683 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 684 "%s Failed to allocate miptree.\n", __func__); 685} 686 687 688/** 689 * Update a subregion of the given texture image. 690 */ 691static void radeon_store_teximage(struct gl_context* ctx, int dims, 692 GLint xoffset, GLint yoffset, GLint zoffset, 693 GLsizei width, GLsizei height, GLsizei depth, 694 GLsizei imageSize, 695 GLenum format, GLenum type, 696 const GLvoid * pixels, 697 const struct gl_pixelstore_attrib *packing, 698 struct gl_texture_object *texObj, 699 struct gl_texture_image *texImage, 700 int compressed) 701{ 702 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 703 radeonTexObj *t = radeon_tex_obj(texObj); 704 radeon_texture_image* image = get_radeon_texture_image(texImage); 705 GLuint texel_size = _mesa_get_format_bytes(texImage->TexFormat); 706 707 GLuint dstRowStride; 708 GLuint alignedWidth; 709 GLint i; 710 711 radeon_print(RADEON_TEXTURE, RADEON_TRACE, 712 "%s(%p, tex %p, image %p) compressed %d\n", 713 __func__, ctx, texObj, texImage, compressed); 714 715 if (image->mt) { 716 dstRowStride = image->mt->levels[image->mtlevel].rowstride; 717 } else if (t->bo) { 718 /* TFP case */ 719 dstRowStride = get_texture_image_row_stride(rmesa, texImage->TexFormat, width, 0); 720 } else { 721 dstRowStride = _mesa_format_row_stride(texImage->TexFormat, texImage->Width); 722 } 723 724 assert(dstRowStride); 725 726 /* fill in the ImageOffsets array */ 727 alignedWidth = dstRowStride / texel_size; 728 for (i = 0; i < texImage->Depth; ++i) { 729 image->base.ImageOffsets[i] = alignedWidth * texImage->Height * i; 730 } 731 /* and fill in RowStride (in texels) */ 732 image->base.RowStride = alignedWidth; 733 734 radeon_teximage_map(image, GL_TRUE); 735 736 if (compressed) { 737 uint32_t srcRowStride, bytesPerRow, rows, block_width, block_height; 738 GLubyte *img_start; 739 740 _mesa_get_format_block_size(texImage->TexFormat, &block_width, &block_height); 741 742 if (!image->mt) { 743 dstRowStride = _mesa_format_row_stride(texImage->TexFormat, texImage->Width); 744 img_start = _mesa_compressed_image_address(xoffset, yoffset, 0, 745 texImage->TexFormat, 746 texImage->Width, image->base.Data); 747 } 748 else { 749 uint32_t offset; 750 offset = dstRowStride / texel_size * yoffset / block_height + xoffset / block_width; 751 offset *= texel_size; 752 img_start = image->base.Data + offset; 753 } 754 srcRowStride = _mesa_format_row_stride(texImage->TexFormat, width); 755 bytesPerRow = srcRowStride; 756 rows = (height + block_height - 1) / block_height; 757 758 copy_rows(img_start, dstRowStride, pixels, srcRowStride, rows, bytesPerRow); 759 } 760 else { 761 GLubyte *slices[512]; 762 GLuint i; 763 assert(depth <= 512); 764 for (i = 0; i < depth; i++) { 765 slices[i] = (GLubyte *) image->base.Data 766 + image->base.ImageOffsets[i] * texel_size; 767 } 768 if (!_mesa_texstore(ctx, dims, texImage->_BaseFormat, 769 texImage->TexFormat, 770 xoffset, yoffset, zoffset, 771 dstRowStride, 772 slices, 773 width, height, depth, 774 format, type, pixels, packing)) { 775 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glTexSubImage"); 776 } 777 } 778 779 radeon_teximage_unmap(image); 780} 781 782/** 783 * All glTexImage calls go through this function. 784 */ 785static void radeon_teximage( 786 struct gl_context *ctx, int dims, 787 GLenum target, GLint level, 788 GLint internalFormat, 789 GLint width, GLint height, GLint depth, 790 GLsizei imageSize, 791 GLenum format, GLenum type, const GLvoid * pixels, 792 const struct gl_pixelstore_attrib *packing, 793 struct gl_texture_object *texObj, 794 struct gl_texture_image *texImage, 795 int compressed) 796{ 797 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 798 radeonTexObj* t = radeon_tex_obj(texObj); 799 radeon_texture_image* image = get_radeon_texture_image(texImage); 800 GLuint face = _mesa_tex_target_to_face(target); 801 802 radeon_print(RADEON_TEXTURE, RADEON_NORMAL, 803 "%s %dd: texObj %p, texImage %p, face %d, level %d\n", 804 __func__, dims, texObj, texImage, face, level); 805 806 t->validated = GL_FALSE; 807 808 radeonFreeTextureImageBuffer(ctx, texImage); 809 810 if (!t->bo) { 811 teximage_assign_miptree(rmesa, texObj, texImage, face, level); 812 if (!image->mt) { 813 int size = _mesa_format_image_size(texImage->TexFormat, 814 texImage->Width, 815 texImage->Height, 816 texImage->Depth); 817 image->base.Buffer = _mesa_align_malloc(size, 512); 818 819 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 820 "%s %dd: texObj %p, texImage %p, " 821 " no miptree assigned, using local memory %p\n", 822 __func__, dims, texObj, texImage, image->base.Buffer); 823 } 824 } 825 826 { 827 struct radeon_bo *bo; 828 bo = !image->mt ? image->bo : image->mt->bo; 829 if (bo && radeon_bo_is_referenced_by_cs(bo, rmesa->cmdbuf.cs)) { 830 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 831 "%s Calling teximage for texture that is " 832 "queued for GPU processing.\n", 833 __func__); 834 radeon_firevertices(rmesa); 835 } 836 } 837 838 image->base.ImageOffsets = 839 (GLuint *) malloc(texImage->Depth * sizeof(GLuint)); 840 841 842 /* Upload texture image; note that the spec allows pixels to be NULL */ 843 if (compressed) { 844 pixels = _mesa_validate_pbo_compressed_teximage( 845 ctx, imageSize, pixels, packing, "glCompressedTexImage"); 846 } else { 847 pixels = _mesa_validate_pbo_teximage( 848 ctx, dims, width, height, depth, 849 format, type, pixels, packing, "glTexImage"); 850 } 851 852 if (pixels) { 853 radeon_store_teximage(ctx, dims, 854 0, 0, 0, 855 width, height, depth, 856 imageSize, format, type, 857 pixels, packing, 858 texObj, texImage, 859 compressed); 860 } 861 862 _mesa_unmap_teximage_pbo(ctx, packing); 863} 864 865void radeonTexImage1D(struct gl_context * ctx, GLenum target, GLint level, 866 GLint internalFormat, 867 GLint width, GLint border, 868 GLenum format, GLenum type, const GLvoid * pixels, 869 const struct gl_pixelstore_attrib *packing, 870 struct gl_texture_object *texObj, 871 struct gl_texture_image *texImage) 872{ 873 radeon_teximage(ctx, 1, target, level, internalFormat, width, 1, 1, 874 0, format, type, pixels, packing, texObj, texImage, 0); 875} 876 877void radeonTexImage2D(struct gl_context * ctx, GLenum target, GLint level, 878 GLint internalFormat, 879 GLint width, GLint height, GLint border, 880 GLenum format, GLenum type, const GLvoid * pixels, 881 const struct gl_pixelstore_attrib *packing, 882 struct gl_texture_object *texObj, 883 struct gl_texture_image *texImage) 884 885{ 886 radeon_teximage(ctx, 2, target, level, internalFormat, width, height, 1, 887 0, format, type, pixels, packing, texObj, texImage, 0); 888} 889 890void radeonCompressedTexImage2D(struct gl_context * ctx, GLenum target, 891 GLint level, GLint internalFormat, 892 GLint width, GLint height, GLint border, 893 GLsizei imageSize, const GLvoid * data, 894 struct gl_texture_object *texObj, 895 struct gl_texture_image *texImage) 896{ 897 radeon_teximage(ctx, 2, target, level, internalFormat, width, height, 1, 898 imageSize, 0, 0, data, &ctx->Unpack, texObj, texImage, 1); 899} 900 901void radeonTexImage3D(struct gl_context * ctx, GLenum target, GLint level, 902 GLint internalFormat, 903 GLint width, GLint height, GLint depth, 904 GLint border, 905 GLenum format, GLenum type, const GLvoid * pixels, 906 const struct gl_pixelstore_attrib *packing, 907 struct gl_texture_object *texObj, 908 struct gl_texture_image *texImage) 909{ 910 radeon_teximage(ctx, 3, target, level, internalFormat, width, height, depth, 911 0, format, type, pixels, packing, texObj, texImage, 0); 912} 913 914/** 915 * All glTexSubImage calls go through this function. 916 */ 917static void radeon_texsubimage(struct gl_context* ctx, int dims, GLenum target, int level, 918 GLint xoffset, GLint yoffset, GLint zoffset, 919 GLsizei width, GLsizei height, GLsizei depth, 920 GLsizei imageSize, 921 GLenum format, GLenum type, 922 const GLvoid * pixels, 923 const struct gl_pixelstore_attrib *packing, 924 struct gl_texture_object *texObj, 925 struct gl_texture_image *texImage, 926 int compressed) 927{ 928 radeonContextPtr rmesa = RADEON_CONTEXT(ctx); 929 radeonTexObj* t = radeon_tex_obj(texObj); 930 radeon_texture_image* image = get_radeon_texture_image(texImage); 931 932 radeon_print(RADEON_TEXTURE, RADEON_NORMAL, 933 "%s %dd: texObj %p, texImage %p, face %d, level %d\n", 934 __func__, dims, texObj, texImage, 935 _mesa_tex_target_to_face(target), level); 936 { 937 struct radeon_bo *bo; 938 bo = !image->mt ? image->bo : image->mt->bo; 939 if (bo && radeon_bo_is_referenced_by_cs(bo, rmesa->cmdbuf.cs)) { 940 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 941 "%s Calling texsubimage for texture that is " 942 "queued for GPU processing.\n", 943 __func__); 944 radeon_firevertices(rmesa); 945 } 946 } 947 948 949 t->validated = GL_FALSE; 950 if (compressed) { 951 pixels = _mesa_validate_pbo_compressed_teximage( 952 ctx, imageSize, pixels, packing, "glCompressedTexSubImage"); 953 } else { 954 pixels = _mesa_validate_pbo_teximage(ctx, dims, 955 width, height, depth, format, type, pixels, packing, "glTexSubImage"); 956 } 957 958 if (pixels) { 959 radeon_store_teximage(ctx, dims, 960 xoffset, yoffset, zoffset, 961 width, height, depth, 962 imageSize, format, type, 963 pixels, packing, 964 texObj, texImage, 965 compressed); 966 } 967 968 _mesa_unmap_teximage_pbo(ctx, packing); 969} 970 971void radeonTexSubImage1D(struct gl_context * ctx, GLenum target, GLint level, 972 GLint xoffset, 973 GLsizei width, 974 GLenum format, GLenum type, 975 const GLvoid * pixels, 976 const struct gl_pixelstore_attrib *packing, 977 struct gl_texture_object *texObj, 978 struct gl_texture_image *texImage) 979{ 980 radeon_texsubimage(ctx, 1, target, level, xoffset, 0, 0, width, 1, 1, 0, 981 format, type, pixels, packing, texObj, texImage, 0); 982} 983 984void radeonTexSubImage2D(struct gl_context * ctx, GLenum target, GLint level, 985 GLint xoffset, GLint yoffset, 986 GLsizei width, GLsizei height, 987 GLenum format, GLenum type, 988 const GLvoid * pixels, 989 const struct gl_pixelstore_attrib *packing, 990 struct gl_texture_object *texObj, 991 struct gl_texture_image *texImage) 992{ 993 radeon_texsubimage(ctx, 2, target, level, xoffset, yoffset, 0, width, height, 1, 994 0, format, type, pixels, packing, texObj, texImage, 995 0); 996} 997 998void radeonCompressedTexSubImage2D(struct gl_context * ctx, GLenum target, 999 GLint level, GLint xoffset, 1000 GLint yoffset, GLsizei width, 1001 GLsizei height, GLenum format, 1002 GLsizei imageSize, const GLvoid * data, 1003 struct gl_texture_object *texObj, 1004 struct gl_texture_image *texImage) 1005{ 1006 radeon_texsubimage(ctx, 2, target, level, xoffset, yoffset, 0, width, height, 1, 1007 imageSize, format, 0, data, &ctx->Unpack, texObj, texImage, 1); 1008} 1009 1010 1011void radeonTexSubImage3D(struct gl_context * ctx, GLenum target, GLint level, 1012 GLint xoffset, GLint yoffset, GLint zoffset, 1013 GLsizei width, GLsizei height, GLsizei depth, 1014 GLenum format, GLenum type, 1015 const GLvoid * pixels, 1016 const struct gl_pixelstore_attrib *packing, 1017 struct gl_texture_object *texObj, 1018 struct gl_texture_image *texImage) 1019{ 1020 radeon_texsubimage(ctx, 3, target, level, xoffset, yoffset, zoffset, width, height, depth, 0, 1021 format, type, pixels, packing, texObj, texImage, 0); 1022} 1023 1024unsigned radeonIsFormatRenderable(gl_format mesa_format) 1025{ 1026 if (mesa_format == _dri_texformat_argb8888 || mesa_format == _dri_texformat_rgb565 || 1027 mesa_format == _dri_texformat_argb1555 || mesa_format == _dri_texformat_argb4444) 1028 return 1; 1029 1030 switch (mesa_format) 1031 { 1032 case MESA_FORMAT_Z16: 1033 case MESA_FORMAT_S8_Z24: 1034 return 1; 1035 default: 1036 return 0; 1037 } 1038} 1039 1040#if FEATURE_OES_EGL_image 1041void radeon_image_target_texture_2d(struct gl_context *ctx, GLenum target, 1042 struct gl_texture_object *texObj, 1043 struct gl_texture_image *texImage, 1044 GLeglImageOES image_handle) 1045{ 1046 radeonContextPtr radeon = RADEON_CONTEXT(ctx); 1047 radeonTexObj *t = radeon_tex_obj(texObj); 1048 radeon_texture_image *radeonImage = get_radeon_texture_image(texImage); 1049 __DRIscreen *screen; 1050 __DRIimage *image; 1051 1052 screen = radeon->dri.screen; 1053 image = screen->dri2.image->lookupEGLImage(screen, image_handle, 1054 screen->loaderPrivate); 1055 if (image == NULL) 1056 return; 1057 1058 radeonFreeTextureImageBuffer(ctx, texImage); 1059 1060 texImage->Width = image->width; 1061 texImage->Height = image->height; 1062 texImage->Depth = 1; 1063 texImage->_BaseFormat = GL_RGBA; 1064 texImage->TexFormat = image->format; 1065 radeonImage->base.RowStride = image->pitch; 1066 texImage->InternalFormat = image->internal_format; 1067 1068 if(t->mt) 1069 { 1070 radeon_miptree_unreference(&t->mt); 1071 t->mt = NULL; 1072 } 1073 1074 /* NOTE: The following is *very* ugly and will probably break. But 1075 I don't know how to deal with it, without creating a whole new 1076 function like radeon_miptree_from_bo() so I'm going with the 1077 easy but error-prone way. */ 1078 1079 radeon_try_alloc_miptree(radeon, t); 1080 1081 radeonImage->mtface = _mesa_tex_target_to_face(target); 1082 radeonImage->mtlevel = 0; 1083 radeon_miptree_reference(t->mt, &radeonImage->mt); 1084 1085 if (t->mt == NULL) 1086 { 1087 radeon_print(RADEON_TEXTURE, RADEON_VERBOSE, 1088 "%s Failed to allocate miptree.\n", __func__); 1089 return; 1090 } 1091 1092 /* Particularly ugly: this is guaranteed to break, if image->bo is 1093 not of the required size for a miptree. */ 1094 radeon_bo_unref(t->mt->bo); 1095 radeon_bo_ref(image->bo); 1096 t->mt->bo = image->bo; 1097 1098 if (!radeon_miptree_matches_image(t->mt, &radeonImage->base.Base, 1099 radeonImage->mtface, 0)) 1100 fprintf(stderr, "miptree doesn't match image\n"); 1101} 1102#endif 1103 1104void 1105radeon_init_common_texture_funcs(radeonContextPtr radeon, 1106 struct dd_function_table *functions) 1107{ 1108 functions->NewTextureImage = radeonNewTextureImage; 1109 functions->DeleteTextureImage = radeonDeleteTextureImage; 1110 functions->FreeTextureImageBuffer = radeonFreeTextureImageBuffer; 1111 functions->MapTexture = radeonMapTexture; 1112 functions->UnmapTexture = radeonUnmapTexture; 1113 functions->MapTextureImage = radeon_map_texture_image; 1114 functions->UnmapTextureImage = radeon_unmap_texture_image; 1115 1116 functions->ChooseTextureFormat = radeonChooseTextureFormat_mesa; 1117 1118 functions->TexImage1D = radeonTexImage1D; 1119 functions->TexImage2D = radeonTexImage2D; 1120 functions->TexImage3D = radeonTexImage3D; 1121 functions->TexSubImage1D = radeonTexSubImage1D; 1122 functions->TexSubImage2D = radeonTexSubImage2D; 1123 functions->TexSubImage3D = radeonTexSubImage3D; 1124 functions->CompressedTexImage2D = radeonCompressedTexImage2D; 1125 functions->CompressedTexSubImage2D = radeonCompressedTexSubImage2D; 1126 1127 functions->GenerateMipmap = radeonGenerateMipmap; 1128 1129 if (radeon->radeonScreen->kernel_mm) { 1130 functions->CopyTexSubImage2D = radeonCopyTexSubImage2D; 1131 } 1132 1133#if FEATURE_OES_EGL_image 1134 functions->EGLImageTargetTexture2D = radeon_image_target_texture_2d; 1135#endif 1136 1137 driInitTextureFormats(); 1138} 1139