mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-31 20:18:19 +02:00
radeon: fix compressed texture upload on all radeons
tested on r200, texcmp works. May need more verification
This commit is contained in:
parent
8123897615
commit
9fd8da299b
2 changed files with 75 additions and 22 deletions
|
|
@ -56,6 +56,29 @@ static GLuint radeon_compressed_texture_size(GLcontext *ctx,
|
|||
return size;
|
||||
}
|
||||
|
||||
|
||||
static int radeon_compressed_num_bytes(GLuint mesaFormat)
|
||||
{
|
||||
int bytes = 0;
|
||||
switch(mesaFormat) {
|
||||
|
||||
case MESA_FORMAT_RGB_FXT1:
|
||||
case MESA_FORMAT_RGBA_FXT1:
|
||||
case MESA_FORMAT_RGB_DXT1:
|
||||
case MESA_FORMAT_RGBA_DXT1:
|
||||
bytes = 2;
|
||||
break;
|
||||
|
||||
case MESA_FORMAT_RGBA_DXT3:
|
||||
case MESA_FORMAT_RGBA_DXT5:
|
||||
bytes = 4;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
return bytes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compute sizes and fill in offset and blit information for the given
|
||||
* image (determined by \p face and \p level).
|
||||
|
|
@ -73,18 +96,14 @@ static void compute_tex_image_offset(radeon_mipmap_tree *mt,
|
|||
/* TODO: Is this correct? Need test cases for compressed textures! */
|
||||
GLuint align;
|
||||
|
||||
if (mt->target == GL_TEXTURE_RECTANGLE_NV)
|
||||
align = 64 / mt->bpp;
|
||||
else
|
||||
align = 32 / mt->bpp;
|
||||
lvl->rowstride = (lvl->width + align - 1) & ~(align - 1);
|
||||
lvl->rowstride = (lvl->width * mt->bpp + 63) & ~63;
|
||||
lvl->size = radeon_compressed_texture_size(mt->radeon->glCtx,
|
||||
lvl->width, lvl->height, lvl->depth, mt->compressed);
|
||||
lvl->width, lvl->height, lvl->depth, mt->compressed);
|
||||
} else if (mt->target == GL_TEXTURE_RECTANGLE_NV) {
|
||||
lvl->rowstride = (lvl->width * mt->bpp + 63) & ~63;
|
||||
lvl->size = lvl->rowstride * lvl->height;
|
||||
} else if (mt->tilebits & RADEON_TXO_MICRO_TILE) {
|
||||
/* tile pattern is 16 bytes x2. mipmaps stay 32 byte aligned,
|
||||
/* tile pattern is 16 bytes x2. mipmaps stay 32 byte aligned,
|
||||
* though the actual offset may be different (if texture is less than
|
||||
* 32 bytes width) to the untiled case */
|
||||
lvl->rowstride = (lvl->width * mt->bpp * 2 + 31) & ~31;
|
||||
|
|
@ -160,7 +179,7 @@ radeon_mipmap_tree* radeon_miptree_create(radeonContextPtr rmesa, radeonTexObj *
|
|||
mt->width0 = width0;
|
||||
mt->height0 = height0;
|
||||
mt->depth0 = depth0;
|
||||
mt->bpp = bpp;
|
||||
mt->bpp = compressed ? radeon_compressed_num_bytes(compressed) : bpp;
|
||||
mt->tilebits = tilebits;
|
||||
mt->compressed = compressed;
|
||||
|
||||
|
|
@ -255,7 +274,12 @@ GLboolean radeon_miptree_matches_image(radeon_mipmap_tree *mt,
|
|||
if (face >= mt->faces || level < mt->firstLevel || level > mt->lastLevel)
|
||||
return GL_FALSE;
|
||||
|
||||
if (texImage->TexFormat->TexelBytes != mt->bpp)
|
||||
if (texImage->IsCompressed != mt->compressed)
|
||||
return GL_FALSE;
|
||||
|
||||
if (!texImage->IsCompressed &&
|
||||
!mt->compressed &&
|
||||
texImage->TexFormat->TexelBytes != mt->bpp)
|
||||
return GL_FALSE;
|
||||
|
||||
lvl = &mt->levels[level - mt->firstLevel];
|
||||
|
|
|
|||
|
|
@ -32,6 +32,7 @@
|
|||
#include "main/imports.h"
|
||||
#include "main/context.h"
|
||||
#include "main/mipmap.h"
|
||||
#include "main/texcompress.h"
|
||||
#include "main/texformat.h"
|
||||
#include "main/texstore.h"
|
||||
#include "main/teximage.h"
|
||||
|
|
@ -453,16 +454,26 @@ static void radeon_teximage(
|
|||
radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
|
||||
radeonTexObj* t = radeon_tex_obj(texObj);
|
||||
radeon_texture_image* image = get_radeon_texture_image(texImage);
|
||||
GLuint dstRowStride;
|
||||
GLint postConvWidth = width;
|
||||
GLint postConvHeight = height;
|
||||
GLuint texelBytes;
|
||||
|
||||
radeon_firevertices(rmesa);
|
||||
|
||||
t->validated = GL_FALSE;
|
||||
|
||||
if (ctx->_ImageTransferState & IMAGE_CONVOLUTION_BIT) {
|
||||
_mesa_adjust_image_for_convolution(ctx, dims, &postConvWidth,
|
||||
&postConvHeight);
|
||||
}
|
||||
|
||||
/* Choose and fill in the texture format for this image */
|
||||
texImage->TexFormat = radeonChooseTextureFormat(ctx, internalFormat, format, type);
|
||||
_mesa_set_fetch_functions(texImage, dims);
|
||||
|
||||
if (texImage->TexFormat->TexelBytes == 0) {
|
||||
texelBytes = 0;
|
||||
texImage->IsCompressed = GL_TRUE;
|
||||
texImage->CompressedSize =
|
||||
ctx->Driver.CompressedTextureSize(ctx, texImage->Width,
|
||||
|
|
@ -471,6 +482,16 @@ static void radeon_teximage(
|
|||
} else {
|
||||
texImage->IsCompressed = GL_FALSE;
|
||||
texImage->CompressedSize = 0;
|
||||
|
||||
texelBytes = texImage->TexFormat->TexelBytes;
|
||||
/* Minimum pitch of 32 bytes */
|
||||
if (postConvWidth * texelBytes < 32) {
|
||||
postConvWidth = 32 / texelBytes;
|
||||
texImage->RowStride = postConvWidth;
|
||||
}
|
||||
if (!image->mt) {
|
||||
assert(texImage->RowStride == postConvWidth);
|
||||
}
|
||||
}
|
||||
|
||||
/* Allocate memory for image */
|
||||
|
|
@ -479,16 +500,22 @@ static void radeon_teximage(
|
|||
if (!t->mt)
|
||||
radeon_try_alloc_miptree(rmesa, t, texImage, face, level);
|
||||
if (t->mt && radeon_miptree_matches_image(t->mt, texImage, face, level)) {
|
||||
radeon_mipmap_level *lvl;
|
||||
image->mt = t->mt;
|
||||
image->mtlevel = level - t->mt->firstLevel;
|
||||
image->mtface = face;
|
||||
radeon_miptree_reference(t->mt);
|
||||
lvl = &image->mt->levels[image->mtlevel];
|
||||
dstRowStride = lvl->rowstride;
|
||||
} else {
|
||||
int size;
|
||||
if (texImage->IsCompressed) {
|
||||
size = texImage->CompressedSize;
|
||||
dstRowStride =
|
||||
_mesa_compressed_row_stride(texImage->TexFormat->MesaFormat, width);
|
||||
} else {
|
||||
size = texImage->Width * texImage->Height * texImage->Depth * texImage->TexFormat->TexelBytes;
|
||||
dstRowStride = postConvWidth * texelBytes;
|
||||
}
|
||||
texImage->Data = _mesa_alloc_texmemory(size);
|
||||
}
|
||||
|
|
@ -509,13 +536,6 @@ static void radeon_teximage(
|
|||
if (compressed) {
|
||||
memcpy(texImage->Data, pixels, imageSize);
|
||||
} else {
|
||||
GLuint dstRowStride;
|
||||
if (image->mt) {
|
||||
radeon_mipmap_level *lvl = &image->mt->levels[image->mtlevel];
|
||||
dstRowStride = lvl->rowstride;
|
||||
} else {
|
||||
dstRowStride = texImage->Width * texImage->TexFormat->TexelBytes;
|
||||
}
|
||||
if (!texImage->TexFormat->StoreImage(ctx, dims,
|
||||
texImage->_BaseFormat,
|
||||
texImage->TexFormat,
|
||||
|
|
@ -534,11 +554,11 @@ static void radeon_teximage(
|
|||
radeon_generate_mipmap(ctx, texObj->Target, texObj);
|
||||
}
|
||||
|
||||
if (pixels)
|
||||
radeon_teximage_unmap(image);
|
||||
|
||||
_mesa_unmap_teximage_pbo(ctx, packing);
|
||||
|
||||
if (pixels)
|
||||
radeon_teximage_unmap(image);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -579,7 +599,7 @@ void radeonCompressedTexImage2D(GLcontext * ctx, GLenum target,
|
|||
GLuint face = radeon_face_for_target(target);
|
||||
|
||||
radeon_teximage(ctx, 2, face, level, internalFormat, width, height, 1,
|
||||
imageSize, 0, 0, data, 0, texObj, texImage, 1);
|
||||
imageSize, 0, 0, data, &ctx->Unpack, texObj, texImage, 1);
|
||||
}
|
||||
|
||||
void radeonTexImage3D(GLcontext * ctx, GLenum target, GLint level,
|
||||
|
|
@ -760,13 +780,22 @@ static void migrate_image_to_miptree(radeon_mipmap_tree *mt, radeon_texture_imag
|
|||
|
||||
radeon_miptree_unreference(image->mt);
|
||||
} else {
|
||||
uint srcrowstride = image->base.Width * image->base.TexFormat->TexelBytes;
|
||||
uint32_t srcrowstride;
|
||||
uint32_t height;
|
||||
/* need to confirm this value is correct */
|
||||
if (mt->compressed) {
|
||||
height = image->base.Height / 4;
|
||||
srcrowstride = image->base.RowStride * mt->bpp;
|
||||
} else {
|
||||
height = image->base.Height * image->base.Depth;
|
||||
srcrowstride = image->base.Width * image->base.TexFormat->TexelBytes;
|
||||
}
|
||||
|
||||
// if (mt->tilebits)
|
||||
// WARN_ONCE("%s: tiling not supported yet", __FUNCTION__);
|
||||
|
||||
copy_rows(dest, dstlvl->rowstride, image->base.Data, srcrowstride,
|
||||
image->base.Height * image->base.Depth, srcrowstride);
|
||||
height, srcrowstride);
|
||||
|
||||
_mesa_free_texmemory(image->base.Data);
|
||||
image->base.Data = 0;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue