void _mesa_update_fetch_functions(struct gl_context *ctx, GLuint unit) { struct gl_texture_object *texObj = ctx->Texture.Unit[unit]._Current; struct gl_sampler_object *samp; GLuint face, i; GLuint dims; if (!texObj) return; samp = _mesa_get_samplerobj(ctx, unit); dims = _mesa_get_texture_dimensions(texObj->Target); for (face = 0; face < 6; face++) { for (i = 0; i < MAX_TEXTURE_LEVELS; i++) { if (texObj->Image[face][i]) { set_fetch_functions(samp, swrast_texture_image(texObj->Image[face][i]), dims); } } } }
/** * Update the renderbuffer wrapper for rendering to a texture. * For example, update the width, height of the RB based on the texture size, * update the internal format info, etc. */ static void update_wrapper(struct gl_context *ctx, struct gl_renderbuffer_attachment *att) { struct gl_renderbuffer *rb = att->Renderbuffer; struct swrast_renderbuffer *srb = swrast_renderbuffer(rb); struct swrast_texture_image *swImage; gl_format format; GLuint zOffset; (void) ctx; swImage = swrast_texture_image(rb->TexImage); assert(swImage); format = swImage->Base.TexFormat; if (att->Texture->Target == GL_TEXTURE_1D_ARRAY_EXT) { zOffset = 0; } else { zOffset = att->Zoffset; } /* Want to store linear values, not sRGB */ rb->Format = _mesa_get_srgb_format_linear(format); srb->Buffer = swImage->ImageSlices[zOffset]; }
/** * Called via ctx->Driver.FreeTextureImageBuffer() */ void _swrast_free_texture_image_buffer(struct gl_context *ctx, struct gl_texture_image *texImage) { struct swrast_texture_image *swImage = swrast_texture_image(texImage); if (swImage->Buffer) { _mesa_align_free(swImage->Buffer); swImage->Buffer = NULL; } if (swImage->ImageOffsets) { free(swImage->ImageOffsets); swImage->ImageOffsets = NULL; } }
void _mesa_update_fetch_functions(struct gl_texture_object *texObj) { GLuint face, i; GLuint dims; dims = _mesa_get_texture_dimensions(texObj->Target); for (face = 0; face < 6; face++) { for (i = 0; i < MAX_TEXTURE_LEVELS; i++) { if (texObj->Image[face][i]) { set_fetch_functions(swrast_texture_image(texObj->Image[face][i]), dims); } } } }
/** * Code that overrides ctx->Driver.AllocTextureImageBuffer may use this to * initialize the fields of swrast_texture_image without allocating the image * buffer or initializing ImageOffsets or RowStride. * * Returns GL_TRUE on success, GL_FALSE on memory allocation failure. */ void _swrast_init_texture_image(struct gl_texture_image *texImage, GLsizei width, GLsizei height, GLsizei depth) { struct swrast_texture_image *swImg = swrast_texture_image(texImage); if ((width == 1 || _mesa_is_pow_two(texImage->Width2)) && (height == 1 || _mesa_is_pow_two(texImage->Height2)) && (depth == 1 || _mesa_is_pow_two(texImage->Depth2))) swImg->_IsPowerOfTwo = GL_TRUE; else swImg->_IsPowerOfTwo = GL_FALSE; /* Compute Width/Height/DepthScale for mipmap lod computation */ swImg->WidthScale = (GLfloat) texImage->Width; swImg->HeightScale = (GLfloat) texImage->Height; swImg->DepthScale = (GLfloat) texImage->Depth; }
/** * Update the renderbuffer wrapper for rendering to a texture. * For example, update the width, height of the RB based on the texture size, * update the internal format info, etc. */ static void update_wrapper(struct gl_context *ctx, struct gl_renderbuffer_attachment *att) { struct gl_renderbuffer *rb = att->Renderbuffer; struct swrast_renderbuffer *srb = swrast_renderbuffer(rb); struct swrast_texture_image *swImage; gl_format format; GLuint zOffset; (void) ctx; swImage = swrast_texture_image(_mesa_get_attachment_teximage(att)); assert(swImage); format = swImage->Base.TexFormat; if (att->Texture->Target == GL_TEXTURE_1D_ARRAY_EXT) { zOffset = 0; } else { zOffset = att->Zoffset; } rb->Width = swImage->Base.Width; rb->Height = swImage->Base.Height; rb->InternalFormat = swImage->Base.InternalFormat; rb->_BaseFormat = _mesa_get_format_base_format(format); /* Want to store linear values, not sRGB */ rb->Format = _mesa_get_srgb_format_linear(format); /* Set the gl_renderbuffer::Buffer field so that mapping the buffer * succeeds. */ if (att->Texture->Target == GL_TEXTURE_3D || att->Texture->Target == GL_TEXTURE_2D_ARRAY_EXT) { srb->Buffer = swImage->Buffer + swImage->ImageOffsets[zOffset] * _mesa_get_format_bytes(format); } else { srb->Buffer = swImage->Buffer; } }
void _swrast_unmap_texture(struct gl_context *ctx, struct gl_texture_object *texObj) { const GLuint faces = texObj->Target == GL_TEXTURE_CUBE_MAP ? 6 : 1; GLuint face, level; for (face = 0; face < faces; face++) { for (level = texObj->BaseLevel; level < MAX_TEXTURE_LEVELS; level++) { struct gl_texture_image *texImage = texObj->Image[face][level]; if (texImage) { struct swrast_texture_image *swImage = swrast_texture_image(texImage); /* XXX we'll eventually call _swrast_unmap_teximage() here */ swImage->Map = NULL; } } } }
static void swrastSetTexBuffer2(__DRIcontext *pDRICtx, GLint target, GLint texture_format, __DRIdrawable *dPriv) { struct dri_context *dri_ctx; int x, y, w, h; __DRIscreen *sPriv = dPriv->driScreenPriv; struct gl_texture_unit *texUnit; struct gl_texture_object *texObj; struct gl_texture_image *texImage; struct swrast_texture_image *swImage; uint32_t internalFormat; gl_format texFormat; dri_ctx = pDRICtx->driverPrivate; internalFormat = (texture_format == __DRI_TEXTURE_FORMAT_RGB ? 3 : 4); texUnit = _mesa_get_current_tex_unit(&dri_ctx->Base); texObj = _mesa_select_tex_object(&dri_ctx->Base, texUnit, target); texImage = _mesa_get_tex_image(&dri_ctx->Base, texObj, target, 0); swImage = swrast_texture_image(texImage); _mesa_lock_texture(&dri_ctx->Base, texObj); sPriv->swrast_loader->getDrawableInfo(dPriv, &x, &y, &w, &h, dPriv->loaderPrivate); if (texture_format == __DRI_TEXTURE_FORMAT_RGB) texFormat = MESA_FORMAT_XRGB8888; else texFormat = MESA_FORMAT_ARGB8888; _mesa_init_teximage_fields(&dri_ctx->Base, texImage, w, h, 1, 0, internalFormat, texFormat); sPriv->swrast_loader->getImage(dPriv, x, y, w, h, (char *)swImage->Buffer, dPriv->loaderPrivate); _mesa_unlock_texture(&dri_ctx->Base, texObj); }
/** * Called via ctx->Driver.AllocTextureImageBuffer() */ GLboolean _swrast_alloc_texture_image_buffer(struct gl_context *ctx, struct gl_texture_image *texImage, gl_format format, GLsizei width, GLsizei height, GLsizei depth) { struct swrast_texture_image *swImg = swrast_texture_image(texImage); GLuint bytes = _mesa_format_image_size(format, width, height, depth); GLuint i; /* This _should_ be true (revisit if these ever fail) */ assert(texImage->Width == width); assert(texImage->Height == height); assert(texImage->Depth == depth); assert(!swImg->Buffer); swImg->Buffer = _mesa_align_malloc(bytes, 512); if (!swImg->Buffer) return GL_FALSE; /* RowStride and ImageOffsets[] describe how to address texels in 'Data' */ swImg->RowStride = width; /* Allocate the ImageOffsets array and initialize to typical values. * We allocate the array for 1D/2D textures too in order to avoid special- * case code in the texstore routines. */ swImg->ImageOffsets = (GLuint *) malloc(depth * sizeof(GLuint)); if (!swImg->ImageOffsets) return GL_FALSE; for (i = 0; i < depth; i++) { swImg->ImageOffsets[i] = i * width * height; } _swrast_init_texture_image(texImage, width, height, depth); return GL_TRUE; }
/** * Map a 2D slice of a texture image into user space. * (x,y,w,h) defines a region of interest (ROI). Reading/writing texels * outside of the ROI is undefined. * * \param texImage the texture image * \param slice the 3D image slice or array texture slice * \param x, y, w, h region of interest * \param mode bitmask of GL_MAP_READ_BIT, GL_MAP_WRITE_BIT * \param mapOut returns start of mapping of region of interest * \param rowStrideOut returns row stride (in bytes) */ void _swrast_map_teximage(struct gl_context *ctx, struct gl_texture_image *texImage, GLuint slice, GLuint x, GLuint y, GLuint w, GLuint h, GLbitfield mode, GLubyte **mapOut, GLint *rowStrideOut) { struct swrast_texture_image *swImage = swrast_texture_image(texImage); GLubyte *map; GLint stride, texelSize; GLuint bw, bh; _mesa_check_map_teximage(texImage, slice, x, y, w, h); texelSize = _mesa_get_format_bytes(texImage->TexFormat); stride = _mesa_format_row_stride(texImage->TexFormat, texImage->Width); _mesa_get_format_block_size(texImage->TexFormat, &bw, &bh); assert(x % bw == 0); assert(y % bh == 0); if (!swImage->Buffer) { /* probably ran out of memory when allocating tex mem */ *mapOut = NULL; return; } map = swImage->Buffer; /* apply x/y offset to map address */ map += stride * (y / bh) + texelSize * (x / bw); *mapOut = map; *rowStrideOut = stride; }