diff options
Diffstat (limited to 'mesalib')
-rw-r--r-- | mesalib/src/gallium/auxiliary/util/u_cpu_detect.c | 27 | ||||
-rw-r--r-- | mesalib/src/mesa/drivers/common/meta.c | 23 | ||||
-rw-r--r-- | mesalib/src/mesa/main/mipmap.c | 59 | ||||
-rw-r--r-- | mesalib/src/mesa/main/texcompress_rgtc_tmp.h | 6 | ||||
-rw-r--r-- | mesalib/src/mesa/main/texgetimage.c | 52 |
5 files changed, 116 insertions, 51 deletions
diff --git a/mesalib/src/gallium/auxiliary/util/u_cpu_detect.c b/mesalib/src/gallium/auxiliary/util/u_cpu_detect.c index b118fc8ae..588fc7c72 100644 --- a/mesalib/src/gallium/auxiliary/util/u_cpu_detect.c +++ b/mesalib/src/gallium/auxiliary/util/u_cpu_detect.c @@ -67,7 +67,7 @@ #if defined(PIPE_OS_WINDOWS) #include <windows.h> -#if defined(MSVC) +#if defined(PIPE_CC_MSVC) #include <intrin.h> #endif #endif @@ -211,6 +211,27 @@ cpuid(uint32_t ax, uint32_t *p) p[3] = 0; #endif } + +static INLINE uint64_t xgetbv(void) +{ +#if defined(PIPE_CC_GCC) + uint32_t eax, edx; + + __asm __volatile ( + ".byte 0x0f, 0x01, 0xd0" // xgetbv isn't supported on gcc < 4.4 + : "=a"(eax), + "=d"(edx) + : "c"(0) + ); + + return ((uint64_t)edx << 32) | eax; +#elif defined(PIPE_CC_MSVC) && defined(_MSC_FULL_VER) && defined(_XCR_XFEATURE_ENABLED_MASK) + return _xgetbv(_XCR_XFEATURE_ENABLED_MASK); +#else + return 0; +#endif + +} #endif /* X86 or X86_64 */ void @@ -284,7 +305,9 @@ util_cpu_detect(void) util_cpu_caps.has_sse4_1 = (regs2[2] >> 19) & 1; util_cpu_caps.has_sse4_2 = (regs2[2] >> 20) & 1; util_cpu_caps.has_popcnt = (regs2[2] >> 23) & 1; - util_cpu_caps.has_avx = (regs2[2] >> 28) & 1; + util_cpu_caps.has_avx = ((regs2[2] >> 28) & 1) && // AVX + ((regs2[2] >> 27) & 1) && // OSXSAVE + ((xgetbv() & 6) == 6); // XMM & YMM util_cpu_caps.has_f16c = (regs2[2] >> 29) & 1; util_cpu_caps.has_mmx2 = util_cpu_caps.has_sse; /* SSE cpus supports mmxext too */ diff --git a/mesalib/src/mesa/drivers/common/meta.c b/mesalib/src/mesa/drivers/common/meta.c index e8484299b..4a3497c9a 100644 --- a/mesalib/src/mesa/drivers/common/meta.c +++ b/mesalib/src/mesa/drivers/common/meta.c @@ -4095,10 +4095,29 @@ _mesa_meta_GetTexImage(struct gl_context *ctx, _mesa_get_format_datatype(texImage->TexFormat) == GL_UNSIGNED_NORMALIZED) { struct gl_texture_object *texObj = texImage->TexObject; - const GLuint slice = 0; /* only 2D compressed textures for now */ + GLuint slice; /* Need to unlock the texture here to prevent deadlock... */ _mesa_unlock_texture(ctx, texObj); - decompress_texture_image(ctx, texImage, slice, format, type, pixels); + for (slice = 0; slice < texImage->Depth; slice++) { + void *dst; + if (texImage->TexObject->Target == GL_TEXTURE_2D_ARRAY) { + /* Setup pixel packing. SkipPixels and SkipRows will be applied + * in the decompress_texture_image() function's call to + * glReadPixels but we need to compute the dest slice's address + * here (according to SkipImages and ImageHeight). + */ + struct gl_pixelstore_attrib packing = ctx->Pack; + packing.SkipPixels = 0; + packing.SkipRows = 0; + dst = _mesa_image_address3d(&packing, pixels, texImage->Width, + texImage->Height, format, type, + slice, 0, 0); + } + else { + dst = pixels; + } + decompress_texture_image(ctx, texImage, slice, format, type, dst); + } /* ... and relock it */ _mesa_lock_texture(ctx, texObj); } diff --git a/mesalib/src/mesa/main/mipmap.c b/mesalib/src/mesa/main/mipmap.c index edf725721..583963232 100644 --- a/mesalib/src/mesa/main/mipmap.c +++ b/mesalib/src/mesa/main/mipmap.c @@ -2020,13 +2020,15 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, GLuint level; gl_format temp_format; GLint components; - GLuint temp_src_stride; /* in bytes */ + GLuint temp_src_row_stride, temp_src_img_stride; /* in bytes */ GLubyte *temp_src = NULL, *temp_dst = NULL; GLenum temp_datatype; GLenum temp_base_format; + GLubyte **temp_src_slices, **temp_dst_slices; /* only two types of compressed textures at this time */ assert(texObj->Target == GL_TEXTURE_2D || + texObj->Target == GL_TEXTURE_2D_ARRAY || texObj->Target == GL_TEXTURE_CUBE_MAP_ARB); /* @@ -2051,15 +2053,24 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, /* allocate storage for the temporary, uncompressed image */ - /* 20 extra bytes, just be safe when calling last FetchTexel */ - temp_src_stride = _mesa_format_row_stride(temp_format, srcImage->Width); - temp_src = malloc(temp_src_stride * srcImage->Height + 20); - if (!temp_src) { + temp_src_row_stride = _mesa_format_row_stride(temp_format, srcImage->Width); + temp_src_img_stride = _mesa_format_image_size(temp_format, srcImage->Width, + srcImage->Height, 1); + temp_src = malloc(temp_src_img_stride * srcImage->Depth); + + /* Allocate storage for arrays of slice pointers */ + temp_src_slices = malloc(srcImage->Depth * sizeof(GLubyte *)); + temp_dst_slices = malloc(srcImage->Depth * sizeof(GLubyte *)); + + if (!temp_src || !temp_src_slices || !temp_dst_slices) { + free(temp_src); + free(temp_src_slices); + free(temp_dst_slices); _mesa_error(ctx, GL_OUT_OF_MEMORY, "generate mipmaps"); return; } - /* decompress base image to the temporary */ + /* decompress base image to the temporary src buffer */ { /* save pixel packing mode */ struct gl_pixelstore_attrib save = ctx->Pack; @@ -2075,7 +2086,6 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, ctx->Pack = save; } - for (level = texObj->BaseLevel; level < maxLevel; level++) { /* generate image[level+1] from image[level] */ const struct gl_texture_image *srcImage; @@ -2084,7 +2094,8 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, GLint dstWidth, dstHeight, dstDepth; GLint border; GLboolean nextLevel; - GLuint temp_dst_stride; /* in bytes */ + GLuint temp_dst_row_stride, temp_dst_img_stride; /* in bytes */ + GLuint i; /* get src image parameters */ srcImage = _mesa_select_tex_image(ctx, texObj, target, level); @@ -2100,9 +2111,12 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, if (!nextLevel) break; - temp_dst_stride = _mesa_format_row_stride(temp_format, dstWidth); + /* Compute dst image strides and alloc memory on first iteration */ + temp_dst_row_stride = _mesa_format_row_stride(temp_format, dstWidth); + temp_dst_img_stride = _mesa_format_image_size(temp_format, dstWidth, + dstHeight, 1); if (!temp_dst) { - temp_dst = malloc(temp_dst_stride * dstHeight); + temp_dst = malloc(temp_dst_img_stride * dstDepth); if (!temp_dst) { _mesa_error(ctx, GL_OUT_OF_MEMORY, "generate mipmaps"); break; @@ -2117,13 +2131,23 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, return; } - /* rescale src image to dest image */ + /* for 2D arrays, setup array[depth] of slice pointers */ + for (i = 0; i < srcDepth; i++) { + temp_src_slices[i] = temp_src + temp_src_img_stride * i; + } + for (i = 0; i < dstDepth; i++) { + temp_dst_slices[i] = temp_dst + temp_dst_img_stride * i; + } + + /* Rescale src image to dest image. + * This will loop over the slices of a 2D array. + */ _mesa_generate_mipmap_level(target, temp_datatype, components, border, srcWidth, srcHeight, srcDepth, - (const GLubyte **) &temp_src, - temp_src_stride, + (const GLubyte **) temp_src_slices, + temp_src_row_stride, dstWidth, dstHeight, dstDepth, - &temp_dst, temp_dst_stride); + temp_dst_slices, temp_dst_row_stride); if (!_mesa_prepare_mipmap_level(ctx, texObj, level + 1, dstWidth, dstHeight, dstDepth, @@ -2135,7 +2159,7 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, /* The image space was allocated above so use glTexSubImage now */ ctx->Driver.TexSubImage(ctx, 2, dstImage, - 0, 0, 0, dstWidth, dstHeight, 1, + 0, 0, 0, dstWidth, dstHeight, dstDepth, temp_base_format, temp_datatype, temp_dst, &ctx->DefaultPacking); @@ -2144,12 +2168,15 @@ generate_mipmap_compressed(struct gl_context *ctx, GLenum target, GLubyte *temp = temp_src; temp_src = temp_dst; temp_dst = temp; - temp_src_stride = temp_dst_stride; + temp_src_row_stride = temp_dst_row_stride; + temp_src_img_stride = temp_dst_img_stride; } } /* loop over mipmap levels */ free(temp_src); free(temp_dst); + free(temp_src_slices); + free(temp_dst_slices); } /** diff --git a/mesalib/src/mesa/main/texcompress_rgtc_tmp.h b/mesalib/src/mesa/main/texcompress_rgtc_tmp.h index 277d69b17..5fa9de630 100644 --- a/mesalib/src/mesa/main/texcompress_rgtc_tmp.h +++ b/mesalib/src/mesa/main/texcompress_rgtc_tmp.h @@ -37,9 +37,9 @@ static void TAG(fetch_texel_rgtc)(unsigned srcRowStride, const TYPE *pixdata, const TYPE alpha0 = blksrc[0]; const TYPE alpha1 = blksrc[1]; const char bit_pos = ((j&3) * 4 + (i&3)) * 3; - const TYPE acodelow = blksrc[2 + bit_pos / 8]; - const TYPE acodehigh = (3 + bit_pos / 8) < 8 ? blksrc[3 + bit_pos / 8] : 0; - const TYPE code = (acodelow >> (bit_pos & 0x7) | + const unsigned char acodelow = blksrc[2 + bit_pos / 8]; + const unsigned char acodehigh = (3 + bit_pos / 8) < 8 ? blksrc[3 + bit_pos / 8] : 0; + const unsigned char code = (acodelow >> (bit_pos & 0x7) | (acodehigh << (8 - (bit_pos & 0x7)))) & 0x7; if (code == 0) diff --git a/mesalib/src/mesa/main/texgetimage.c b/mesalib/src/mesa/main/texgetimage.c index 4c672e366..7050f1080 100644 --- a/mesalib/src/mesa/main/texgetimage.c +++ b/mesalib/src/mesa/main/texgetimage.c @@ -233,8 +233,8 @@ get_tex_rgba_compressed(struct gl_context *ctx, GLuint dimensions, const GLuint width = texImage->Width; const GLuint height = texImage->Height; const GLuint depth = texImage->Depth; - GLfloat *tempImage, *srcRow; - GLuint row; + GLfloat *tempImage, *tempSlice, *srcRow; + GLuint row, slice; /* Decompress into temp float buffer, then pack into user buffer */ tempImage = malloc(width * height * depth @@ -244,20 +244,22 @@ get_tex_rgba_compressed(struct gl_context *ctx, GLuint dimensions, return; } - /* Decompress the texture image - results in 'tempImage' */ - { + /* Decompress the texture image slices - results in 'tempImage' */ + for (slice = 0; slice < depth; slice++) { GLubyte *srcMap; GLint srcRowStride; - ctx->Driver.MapTextureImage(ctx, texImage, 0, + tempSlice = tempImage + slice * 4 * width * height; + + ctx->Driver.MapTextureImage(ctx, texImage, slice, 0, 0, width, height, GL_MAP_READ_BIT, &srcMap, &srcRowStride); if (srcMap) { _mesa_decompress_image(texFormat, width, height, - srcMap, srcRowStride, tempImage); + srcMap, srcRowStride, tempSlice); - ctx->Driver.UnmapTextureImage(ctx, texImage, 0); + ctx->Driver.UnmapTextureImage(ctx, texImage, slice); } else { _mesa_error(ctx, GL_OUT_OF_MEMORY, "glGetTexImage"); @@ -294,15 +296,19 @@ get_tex_rgba_compressed(struct gl_context *ctx, GLuint dimensions, rebaseFormat); } - srcRow = tempImage; - for (row = 0; row < height; row++) { - void *dest = _mesa_image_address(dimensions, &ctx->Pack, pixels, - width, height, format, type, - 0, row, 0); - - _mesa_pack_rgba_span_float(ctx, width, (GLfloat (*)[4]) srcRow, - format, type, dest, &ctx->Pack, transferOps); - srcRow += width * 4; + tempSlice = tempImage; + for (slice = 0; slice < depth; slice++) { + srcRow = tempSlice; + for (row = 0; row < height; row++) { + void *dest = _mesa_image_address(dimensions, &ctx->Pack, pixels, + width, height, format, type, + slice, row, 0); + + _mesa_pack_rgba_span_float(ctx, width, (GLfloat (*)[4]) srcRow, + format, type, dest, &ctx->Pack, transferOps); + srcRow += 4 * width; + } + tempSlice += 4 * width * height; } free(tempImage); @@ -616,18 +622,8 @@ _mesa_get_teximage(struct gl_context *ctx, GLenum format, GLenum type, GLvoid *pixels, struct gl_texture_image *texImage) { - GLuint dimensions; - - switch (texImage->TexObject->Target) { - case GL_TEXTURE_1D: - dimensions = 1; - break; - case GL_TEXTURE_3D: - dimensions = 3; - break; - default: - dimensions = 2; - } + const GLuint dimensions = + _mesa_get_texture_dimensions(texImage->TexObject->Target); /* map dest buffer, if PBO */ if (_mesa_is_bufferobj(ctx->Pack.BufferObj)) { |