diff options
| -rw-r--r-- | src/gallium/drivers/nv50/nv50_miptree.c | 35 | ||||
| -rw-r--r-- | src/gallium/drivers/nv50/nv50_transfer.c | 50 | 
2 files changed, 48 insertions, 37 deletions
| diff --git a/src/gallium/drivers/nv50/nv50_miptree.c b/src/gallium/drivers/nv50/nv50_miptree.c index 93479a0314..229a59cb74 100644 --- a/src/gallium/drivers/nv50/nv50_miptree.c +++ b/src/gallium/drivers/nv50/nv50_miptree.c @@ -26,6 +26,16 @@  #include "nv50_context.h" +static INLINE uint32_t +get_tile_mode(unsigned ny) +{ +	if (ny > 32) return 4; +	if (ny > 16) return 3; +	if (ny >  8) return 2; +	if (ny >  4) return 1; +	return 0; +} +  static struct pipe_texture *  nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp)  { @@ -34,7 +44,7 @@ nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp)  	struct pipe_texture *pt = &mt->base.base;  	unsigned width = tmp->width[0], height = tmp->height[0];  	unsigned depth = tmp->depth[0]; -	uint32_t tile_mode, tile_flags, tile_h; +	uint32_t tile_flags;  	int ret, i, l;  	*pt = *tmp; @@ -57,13 +67,6 @@ nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp)  		break;  	} -	if      (pt->height[0] > 32) tile_mode = 4; -	else if (pt->height[0] > 16) tile_mode = 3; -	else if (pt->height[0] >  8) tile_mode = 2; -	else if (pt->height[0] >  4) tile_mode = 1; -	else                         tile_mode = 0; -	tile_h = 1 << (tile_mode + 2); -  	switch (pt->target) {  	case PIPE_TEXTURE_3D:  		mt->image_nr = pt->depth[0]; @@ -86,28 +89,22 @@ nv50_miptree_create(struct pipe_screen *pscreen, const struct pipe_texture *tmp)  		pt->nblocksy[l] = pf_get_nblocksy(&pt->block, height);  		lvl->image_offset = CALLOC(mt->image_nr, sizeof(int)); -		lvl->pitch = align(pt->width[l] * pt->block.size, 64); -		lvl->tile_mode = tile_mode; +		lvl->pitch = align(pt->nblocksx[l] * pt->block.size, 64); +		lvl->tile_mode = get_tile_mode(pt->nblocksy[l]);  		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); +			unsigned tile_ny = 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); +			size  = align(pt->nblocksx[l] * pt->block.size, 64); +			size *= align(pt->nblocksy[l], tile_ny);  			lvl->image_offset[i] = mt->total_size; diff --git a/src/gallium/drivers/nv50/nv50_transfer.c b/src/gallium/drivers/nv50/nv50_transfer.c index f1eb672336..9c008090b8 100644 --- a/src/gallium/drivers/nv50/nv50_transfer.c +++ b/src/gallium/drivers/nv50/nv50_transfer.c @@ -124,7 +124,7 @@ nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,  	struct nv50_miptree *mt = nv50_miptree(pt);  	struct nv50_miptree_level *lvl = &mt->level[level];  	struct nv50_transfer *tx; -	unsigned image = 0; +	unsigned nx, ny, image = 0;  	int ret;  	if (pt->target == PIPE_TEXTURE_CUBE) @@ -142,9 +142,16 @@ nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,  	tx->base.width = w;  	tx->base.height = h;  	tx->base.block = pt->block; -	tx->base.nblocksx = pt->nblocksx[level]; -	tx->base.nblocksy = pt->nblocksy[level]; -	tx->base.stride = (w * pt->block.size); +	if (!pt->nblocksx[level]) { +		tx->base.nblocksx = pf_get_nblocksx(&pt->block, +						    pt->width[level]); +		tx->base.nblocksy = pf_get_nblocksy(&pt->block, +						    pt->height[level]); +	} else { +		tx->base.nblocksx = pt->nblocksx[level]; +		tx->base.nblocksy = pt->nblocksy[level]; +	} +	tx->base.stride = tx->base.nblocksx * pt->block.size;  	tx->base.usage = usage;  	tx->level_pitch = lvl->pitch; @@ -152,24 +159,28 @@ nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,  	tx->level_height = mt->base.base.height[level];  	tx->level_offset = lvl->image_offset[image];  	tx->level_tiling = lvl->tile_mode; -	tx->level_x = x; -	tx->level_y = y; +	tx->level_x = pf_get_nblocksx(&tx->base.block, x); +	tx->level_y = pf_get_nblocksy(&tx->base.block, y);  	ret = nouveau_bo_new(dev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP, 0, -			     w * pt->block.size * h, &tx->bo); +			     tx->base.nblocksy * tx->base.stride, &tx->bo);  	if (ret) {  		FREE(tx);  		return NULL;  	}  	if (usage & PIPE_TRANSFER_READ) { +		nx = pf_get_nblocksx(&tx->base.block, tx->base.width); +		ny = pf_get_nblocksy(&tx->base.block, tx->base.height); +  		nv50_transfer_rect_m2mf(pscreen, mt->base.bo, tx->level_offset,  					tx->level_pitch, tx->level_tiling,  					x, y, -					tx->level_width, tx->level_height, -					tx->bo, 0, tx->base.stride, -					tx->bo->tile_mode, 0, 0, -					tx->base.width, tx->base.height, -					tx->base.block.size, w, h, +					tx->base.nblocksx, tx->base.nblocksy, +					tx->bo, 0, +					tx->base.stride, tx->bo->tile_mode, +					0, 0, +					tx->base.nblocksx, tx->base.nblocksy, +					tx->base.block.size, nx, ny,  					NOUVEAU_BO_VRAM | NOUVEAU_BO_GART,  					NOUVEAU_BO_GART);  	} @@ -183,17 +194,20 @@ nv50_transfer_del(struct pipe_transfer *ptx)  	struct nv50_transfer *tx = (struct nv50_transfer *)ptx;  	struct nv50_miptree *mt = nv50_miptree(ptx->texture); +	unsigned nx = pf_get_nblocksx(&tx->base.block, tx->base.width); +	unsigned ny = pf_get_nblocksy(&tx->base.block, tx->base.height); +  	if (ptx->usage & PIPE_TRANSFER_WRITE) {  		struct pipe_screen *pscreen = ptx->texture->screen; -		nv50_transfer_rect_m2mf(pscreen, tx->bo, 0, tx->base.stride, -					tx->bo->tile_mode, 0, 0, -					tx->base.width, tx->base.height, +		nv50_transfer_rect_m2mf(pscreen, tx->bo, 0, +					tx->base.stride, tx->bo->tile_mode, +					0, 0, +					tx->base.nblocksx, tx->base.nblocksy,  					mt->base.bo, tx->level_offset,  					tx->level_pitch, tx->level_tiling,  					tx->level_x, tx->level_y, -					tx->level_width, tx->level_height, -					tx->base.block.size, tx->base.width, -					tx->base.height, +					tx->base.nblocksx, tx->base.nblocksy, +					tx->base.block.size, nx, ny,  					NOUVEAU_BO_GART, NOUVEAU_BO_VRAM |  					NOUVEAU_BO_GART);  	} | 
