diff options
author | Christoph Bumiller <[email protected]> | 2009-08-14 18:23:55 +0200 |
---|---|---|
committer | Christoph Bumiller <[email protected]> | 2009-08-14 18:23:55 +0200 |
commit | 442a5e434381987a426192e2b7d34847de50a0ed (patch) | |
tree | c8b33bcf3c9f8aa81d3557ed2510da8c5a6ee813 /src/gallium/drivers/nv50/nv50_miptree.c | |
parent | 3506d7d3e2b5ed57cb3f0653421226a863555ae1 (diff) |
nv50: fix mipmap offsets and tiling
The hardware expects a texture's tile mode to change with
the mipmap level.
Also, only multiply by block size once to obtain size.
Diffstat (limited to 'src/gallium/drivers/nv50/nv50_miptree.c')
-rw-r--r-- | src/gallium/drivers/nv50/nv50_miptree.c | 11 |
1 files changed, 9 insertions, 2 deletions
diff --git a/src/gallium/drivers/nv50/nv50_miptree.c b/src/gallium/drivers/nv50/nv50_miptree.c index c8392799ed8..7493ef3af2a 100644 --- a/src/gallium/drivers/nv50/nv50_miptree.c +++ b/src/gallium/drivers/nv50/nv50_miptree.c @@ -87,20 +87,27 @@ nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp) lvl->image_offset = CALLOC(mt->image_nr, sizeof(int)); lvl->pitch = align(pt->width[l] * pt->block.size, 64); + lvl->tile_mode = tile_mode; width = MAX2(1, width >> 1); height = MAX2(1, height >> 1); depth = MAX2(1, depth >> 1); + + if (tile_mode && height <= (tile_h >> 1)) { + tile_mode--; + tile_h >>= 1; + } } for (i = 0; i < mt->image_nr; i++) { for (l = 0; l <= pt->last_level; l++) { struct nv50_miptree_level *lvl = &mt->level[l]; int size; + tile_h = 1 << (lvl->tile_mode + 2); size = align(pt->width[l], 8) * pt->block.size; size = align(size, 64); - size *= align(pt->height[l], tile_h) * pt->block.size; + size *= align(pt->height[l], tile_h); lvl->image_offset[i] = mt->total_size; @@ -109,7 +116,7 @@ nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp) } ret = nouveau_bo_new_tile(dev, NOUVEAU_BO_VRAM, 256, mt->total_size, - tile_mode, tile_flags, &mt->bo); + mt->level[0].tile_mode, tile_flags, &mt->bo); if (ret) { FREE(mt); return NULL; |