Parcourir la source

swrast: Always use MapTextureImage for mapping textures for swrast.

Now that everything goes through ImageSlices[], we can rely on the
driver's existing texture mapping function.

A big block of code goes away on Radeon that looks like it was to deal with
the validate that happened at SpanRenderStart, which no longer occurs since we
don't need validation for the MapTextureImage hook.

v2: Rewrite comment about ImageSlices, fix duplicated swImages, touch up
    unmap loop.

Reviewed-by: Kenneth Graunke <kenneth@whitecape.org> (v1)
Reviewed-by: Brian Paul <brianp@vmware.com>
undefined
Eric Anholt il y a 12 ans
Parent
révision
adf958d9c2

+ 0
- 2
src/mesa/drivers/dri/i915/intel_tris.c Voir le fichier

@@ -1096,11 +1096,9 @@ intelRunPipeline(struct gl_context * ctx)
intel->NewGLState = 0;
}

intel_map_vertex_shader_textures(ctx);
intel->tnl_pipeline_running = true;
_tnl_run_pipeline(ctx);
intel->tnl_pipeline_running = false;
intel_unmap_vertex_shader_textures(ctx);

_mesa_unlock_context_textures(ctx);
}

+ 5
- 75
src/mesa/drivers/dri/intel/intel_span.c Voir le fichier

@@ -104,32 +104,9 @@ intel_offset_S8(uint32_t stride, uint32_t x, uint32_t y, bool swizzled)
return u;
}

/**
* Map the regions needed by intelSpanRenderStart().
*/
static void
intel_span_map_buffers(struct intel_context *intel)
{
struct gl_context *ctx = &intel->ctx;
struct intel_texture_object *tex_obj;

for (int i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
if (!ctx->Texture.Unit[i]._ReallyEnabled)
continue;
tex_obj = intel_texture_object(ctx->Texture.Unit[i]._Current);
intel_finalize_mipmap_tree(intel, i);
intel_tex_map_images(intel, tex_obj,
GL_MAP_READ_BIT | GL_MAP_WRITE_BIT);
}

_swrast_map_renderbuffers(ctx);
}

/**
* Prepare for software rendering. Map current read/draw framebuffers'
* renderbuffes and all currently bound texture objects.
*
* Old note: Moved locking out to get reasonable span performance.
* renderbuffers and all currently bound texture objects.
*/
void
intelSpanRenderStart(struct gl_context * ctx)
@@ -139,7 +116,9 @@ intelSpanRenderStart(struct gl_context * ctx)
intel_flush(ctx);
intel_prepare_render(intel);
intel_flush(ctx);
intel_span_map_buffers(intel);

_swrast_map_textures(ctx);
_swrast_map_renderbuffers(ctx);
}

/**
@@ -149,18 +128,8 @@ intelSpanRenderStart(struct gl_context * ctx)
void
intelSpanRenderFinish(struct gl_context * ctx)
{
struct intel_context *intel = intel_context(ctx);
GLuint i;

_swrast_flush(ctx);

for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
if (ctx->Texture.Unit[i]._ReallyEnabled) {
struct gl_texture_object *texObj = ctx->Texture.Unit[i]._Current;
intel_tex_unmap_images(intel, intel_texture_object(texObj));
}
}

_swrast_unmap_textures(ctx);
_swrast_unmap_renderbuffers(ctx);
}

@@ -174,42 +143,3 @@ intelInitSpanFuncs(struct gl_context * ctx)
swdd->SpanRenderFinish = intelSpanRenderFinish;
}
}

void
intel_map_vertex_shader_textures(struct gl_context *ctx)
{
struct intel_context *intel = intel_context(ctx);
int i;

if (ctx->VertexProgram._Current == NULL)
return;

for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
if (ctx->Texture.Unit[i]._ReallyEnabled &&
ctx->VertexProgram._Current->Base.TexturesUsed[i] != 0) {
struct gl_texture_object *texObj = ctx->Texture.Unit[i]._Current;

intel_tex_map_images(intel, intel_texture_object(texObj),
GL_MAP_READ_BIT | GL_MAP_WRITE_BIT);
}
}
}

void
intel_unmap_vertex_shader_textures(struct gl_context *ctx)
{
struct intel_context *intel = intel_context(ctx);
int i;

if (ctx->VertexProgram._Current == NULL)
return;

for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
if (ctx->Texture.Unit[i]._ReallyEnabled &&
ctx->VertexProgram._Current->Base.TexturesUsed[i] != 0) {
struct gl_texture_object *texObj = ctx->Texture.Unit[i]._Current;

intel_tex_unmap_images(intel, intel_texture_object(texObj));
}
}
}

+ 0
- 2
src/mesa/drivers/dri/intel/intel_span.h Voir le fichier

@@ -36,8 +36,6 @@ extern void intelInitSpanFuncs(struct gl_context * ctx);
extern void intelSpanRenderFinish(struct gl_context * ctx);
extern void intelSpanRenderStart(struct gl_context * ctx);

void intel_map_vertex_shader_textures(struct gl_context *ctx);
void intel_unmap_vertex_shader_textures(struct gl_context *ctx);
intptr_t intel_offset_S8(uint32_t stride, uint32_t x, uint32_t y, bool swizzled);

#endif

+ 0
- 6
src/mesa/drivers/dri/intel/intel_tex.h Voir le fichier

@@ -64,12 +64,6 @@ void intel_tex_unmap_level_images(struct intel_context *intel,
struct intel_texture_object *intelObj,
int level);

void intel_tex_map_images(struct intel_context *intel,
struct intel_texture_object *intelObj,
GLbitfield mode);

void intel_tex_unmap_images(struct intel_context *intel,
struct intel_texture_object *intelObj);
bool
intel_tex_image_s8z24_create_renderbuffers(struct intel_context *intel,
struct intel_texture_image *image);

+ 0
- 90
src/mesa/drivers/dri/intel/intel_tex_validate.c Voir le fichier

@@ -139,93 +139,3 @@ intel_finalize_mipmap_tree(struct intel_context *intel, GLuint unit)

return true;
}

/**
* \param mode bitmask of GL_MAP_READ_BIT, GL_MAP_WRITE_BIT
*/
static void
intel_tex_map_image_for_swrast(struct intel_context *intel,
struct intel_texture_image *intel_image,
GLbitfield mode)
{
int level;
int face;
struct intel_mipmap_tree *mt;
unsigned int x, y;

if (!intel_image || !intel_image->mt)
return;

level = intel_image->base.Base.Level;
face = intel_image->base.Base.Face;
mt = intel_image->mt;

for (int i = 0; i < mt->level[level].depth; i++)
intel_miptree_slice_resolve_depth(intel, mt, level, i);

void *map = intel_miptree_map_raw(intel, mt);

for (int i = 0; i < mt->level[level].depth; i++) {
intel_miptree_get_image_offset(mt, level, i, &x, &y);
intel_image->base.ImageSlices[i] = (map +
y * mt->region->pitch +
x * mt->cpp);
DBG("%s: (%d,%d,%d) -> (%d, %d)/%d\n",
__FUNCTION__, face, level, i, x, y, mt->region->pitch);
}

intel_image->base.Map = intel_image->base.ImageSlices[0];

assert(mt->region->pitch % mt->region->cpp == 0);
intel_image->base.RowStride = mt->region->pitch / mt->region->cpp;
}

static void
intel_tex_unmap_image_for_swrast(struct intel_context *intel,
struct intel_texture_image *intel_image)
{
if (intel_image && intel_image->mt) {
intel_miptree_unmap_raw(intel, intel_image->mt);
intel_image->base.Map = NULL;
}
}

/**
* \param mode bitmask of GL_MAP_READ_BIT, GL_MAP_WRITE_BIT
*/
void
intel_tex_map_images(struct intel_context *intel,
struct intel_texture_object *intelObj,
GLbitfield mode)
{
GLuint nr_faces = _mesa_num_tex_faces(intelObj->base.Target);
int i, face;

DBG("%s\n", __FUNCTION__);

for (i = intelObj->base.BaseLevel; i <= intelObj->_MaxLevel; i++) {
for (face = 0; face < nr_faces; face++) {
struct intel_texture_image *intel_image =
intel_texture_image(intelObj->base.Image[face][i]);

intel_tex_map_image_for_swrast(intel, intel_image, mode);
}
}
}

void
intel_tex_unmap_images(struct intel_context *intel,
struct intel_texture_object *intelObj)
{
GLuint nr_faces = _mesa_num_tex_faces(intelObj->base.Target);
int i, face;

for (i = intelObj->base.BaseLevel; i <= intelObj->_MaxLevel; i++) {
for (face = 0; face < nr_faces; face++) {
struct intel_texture_image *intel_image =
intel_texture_image(intelObj->base.Image[face][i]);

intel_tex_unmap_image_for_swrast(intel, intel_image);
}
}
}

+ 0
- 21
src/mesa/drivers/dri/radeon/radeon_mipmap_tree.c Voir le fichier

@@ -431,27 +431,6 @@ static void migrate_image_to_miptree(radeon_mipmap_tree *mt,
radeon_bo_unmap(image->mt->bo);

radeon_miptree_unreference(&image->mt);
} else if (image->base.Map) {
/* This condition should be removed, it's here to workaround
* a segfault when mapping textures during software fallbacks.
*/
radeon_print(RADEON_FALLBACKS, RADEON_IMPORTANT,
"%s Trying to map texture in software fallback.\n",
__func__);
const uint32_t srcrowstride = _mesa_format_row_stride(image->base.Base.TexFormat, image->base.Base.Width);
uint32_t rows = image->base.Base.Height * image->base.Base.Depth;

if (_mesa_is_format_compressed(image->base.Base.TexFormat)) {
uint32_t blockWidth, blockHeight;
_mesa_get_format_block_size(image->base.Base.TexFormat, &blockWidth, &blockHeight);
rows = (rows + blockHeight - 1) / blockHeight;
}

copy_rows(dest, dstlvl->rowstride, image->base.Map, srcrowstride,
rows, srcrowstride);

_mesa_align_free(image->base.Map);
image->base.Map = 0;
}

radeon_bo_unmap(mt->bo);

+ 3
- 15
src/mesa/drivers/dri/radeon/radeon_span.c Voir le fichier

@@ -119,18 +119,11 @@ radeon_unmap_framebuffer(struct gl_context *ctx, struct gl_framebuffer *fb)
static void radeonSpanRenderStart(struct gl_context * ctx)
{
radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
int i;

radeon_firevertices(rmesa);

for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
if (ctx->Texture.Unit[i]._ReallyEnabled) {
radeon_validate_texture_miptree(ctx, _mesa_get_samplerobj(ctx, i),
ctx->Texture.Unit[i]._Current);
radeon_swrast_map_texture_images(ctx, ctx->Texture.Unit[i]._Current);
}
}
_swrast_map_textures(ctx);

radeon_map_framebuffer(ctx, ctx->DrawBuffer);
if (ctx->ReadBuffer != ctx->DrawBuffer)
radeon_map_framebuffer(ctx, ctx->ReadBuffer);
@@ -138,13 +131,8 @@ static void radeonSpanRenderStart(struct gl_context * ctx)

static void radeonSpanRenderFinish(struct gl_context * ctx)
{
int i;

_swrast_flush(ctx);

for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++)
if (ctx->Texture.Unit[i]._ReallyEnabled)
radeon_swrast_unmap_texture_images(ctx, ctx->Texture.Unit[i]._Current);
_swrast_unmap_textures(ctx);

radeon_unmap_framebuffer(ctx, ctx->DrawBuffer);
if (ctx->ReadBuffer != ctx->DrawBuffer)

+ 0
- 74
src/mesa/drivers/dri/radeon/radeon_texture.c Voir le fichier

@@ -630,80 +630,6 @@ radeon_init_common_texture_funcs(radeonContextPtr radeon,
radeonInitTextureFormats();
}

static void
radeon_swrast_map_image(radeonContextPtr rmesa,
radeon_texture_image *image)
{
GLuint level, face;
radeon_mipmap_tree *mt;
GLuint texel_size;
radeon_mipmap_level *lvl;

if (!image || !image->mt)
return;

texel_size = _mesa_get_format_bytes(image->base.Base.TexFormat);
level = image->base.Base.Level;
face = image->base.Base.Face;
mt = image->mt;

lvl = &image->mt->levels[level];

radeon_bo_map(mt->bo, 1);
image->base.Map = mt->bo->ptr + lvl->faces[face].offset;

for (int i = 0; i < mt->levels[level].depth; i++) {
image->base.ImageSlices[i] =
image->base.Map + (lvl->rowstride * lvl->height * i);
}

image->base.RowStride = lvl->rowstride / texel_size;
}

static void
radeon_swrast_unmap_image(radeonContextPtr rmesa,
radeon_texture_image *image)
{
if (image && image->mt) {
image->base.Map = NULL;
radeon_bo_unmap(image->mt->bo);
}
}

void
radeon_swrast_map_texture_images(struct gl_context *ctx,
struct gl_texture_object *texObj)
{
radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
GLuint nr_faces = _mesa_num_tex_faces(texObj->Target);
int i, face;

for (i = texObj->BaseLevel; i <= texObj->_MaxLevel; i++) {
for (face = 0; face < nr_faces; face++) {
radeon_texture_image *image = get_radeon_texture_image(texObj->Image[face][i]);
radeon_swrast_map_image(rmesa, image);
}
}
}

void
radeon_swrast_unmap_texture_images(struct gl_context *ctx,
struct gl_texture_object *texObj)
{
radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
GLuint nr_faces = _mesa_num_tex_faces(texObj->Target);
int i, face;

for (i = texObj->BaseLevel; i <= texObj->_MaxLevel; i++) {
for (face = 0; face < nr_faces; face++) {
radeon_texture_image *image = get_radeon_texture_image(texObj->Image[face][i]);
radeon_swrast_unmap_image(rmesa, image);
}
}
}

static radeon_mipmap_tree *radeon_miptree_create_for_teximage(radeonContextPtr rmesa,
struct gl_texture_object *texObj,
struct gl_texture_image *texImage)

+ 0
- 3
src/mesa/drivers/dri/radeon/radeon_texture.h Voir le fichier

@@ -51,9 +51,6 @@ int radeon_validate_texture_miptree(struct gl_context * ctx,
struct gl_texture_object *texObj);


void radeon_swrast_map_texture_images(struct gl_context *ctx, struct gl_texture_object *texObj);
void radeon_swrast_unmap_texture_images(struct gl_context *ctx, struct gl_texture_object *texObj);

gl_format radeonChooseTextureFormat_mesa(struct gl_context * ctx,
GLenum target,
GLint internalFormat,

+ 8
- 2
src/mesa/swrast/s_context.h Voir le fichier

@@ -148,8 +148,14 @@ struct swrast_texture_image
* between all slices.
*/
GLint RowStride;
void **ImageSlices; /**< if 3D texture: array [Depth] of offsets to
each 2D slice in 'Data', in texels */
/**
* When a texture image is mapped for swrast, this array contains pointers
* to the beginning of each slice.
*
* For swrast-allocated textures, these pointers will always stay
* initialized to point within Buffer.
*/
void **ImageSlices;
GLubyte *Map; /**< Pointer to mapped image memory */

/** Malloc'd texture memory */

+ 48
- 10
src/mesa/swrast/s_texture.c Voir le fichier

@@ -266,12 +266,42 @@ _swrast_map_texture(struct gl_context *ctx, struct gl_texture_object *texObj)
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);
struct swrast_texture_image *swImage = swrast_texture_image(texImage);
unsigned int i;

if (!texImage)
continue;

/* In the case of a swrast-allocated texture buffer, the ImageSlices
* and RowStride are always available.
*/
if (swImage->Buffer) {
assert(swImage->ImageSlices[0] == swImage->Buffer);
continue;
}

/* XXX we'll eventually call _swrast_map_teximage() here */
swImage->Map = swImage->Buffer;
for (i = 0; i < texture_slices(texImage); i++) {
GLubyte *map;
GLint rowStride;

if (swImage->ImageSlices[i])
continue;

ctx->Driver.MapTextureImage(ctx, texImage, i,
0, 0,
texImage->Width, texImage->Height,
GL_MAP_READ_BIT | GL_MAP_WRITE_BIT,
&map, &rowStride);

swImage->ImageSlices[i] = map;
/* A swrast-using driver has to return the same rowstride for
* every slice of the same texture, since we don't track them
* separately.
*/
if (i == 0)
swImage->RowStride = rowStride;
else
assert(swImage->RowStride == rowStride);
}
}
}
@@ -287,12 +317,20 @@ _swrast_unmap_texture(struct gl_context *ctx, struct gl_texture_object *texObj)
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);
struct swrast_texture_image *swImage = swrast_texture_image(texImage);
unsigned int i;

if (!texImage)
continue;

if (swImage->Buffer)
return;

/* XXX we'll eventually call _swrast_unmap_teximage() here */
swImage->Map = NULL;
for (i = 0; i < texture_slices(texImage); i++) {
if (swImage->ImageSlices[i]) {
ctx->Driver.UnmapTextureImage(ctx, texImage, i);
swImage->ImageSlices[i] = NULL;
}
}
}
}

Chargement…
Annuler
Enregistrer