summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/nv50/nv50_transfer.c
diff options
context:
space:
mode:
authorYounes Manton <[email protected]>2010-04-30 20:42:30 -0400
committerYounes Manton <[email protected]>2010-04-30 20:42:30 -0400
commita8ea1dacc63ac567498049e5756c247b9fec6cd9 (patch)
tree4031e2e2b6166bd926b43fa4bbb3aab773a30ee5 /src/gallium/drivers/nv50/nv50_transfer.c
parent404fb63b4649f58fce443615e49337d42b8ddece (diff)
parent35d960cc744c374ccaad48c3d80559b59c74e28a (diff)
Merge branch 'master' of ssh://git.freedesktop.org/git/mesa/mesa into pipe-video
Conflicts: src/gallium/auxiliary/Makefile src/gallium/auxiliary/SConscript src/gallium/auxiliary/util/u_format.csv src/gallium/auxiliary/vl/vl_compositor.c src/gallium/auxiliary/vl/vl_compositor.h src/gallium/auxiliary/vl/vl_mpeg12_mc_renderer.c src/gallium/auxiliary/vl/vl_mpeg12_mc_renderer.h src/gallium/drivers/identity/id_objects.c src/gallium/drivers/identity/id_objects.h src/gallium/drivers/identity/id_screen.c src/gallium/drivers/nv40/Makefile src/gallium/drivers/nv40/nv40_screen.c src/gallium/drivers/softpipe/sp_texture.c src/gallium/drivers/softpipe/sp_texture.h src/gallium/drivers/softpipe/sp_video_context.c src/gallium/drivers/softpipe/sp_video_context.h src/gallium/include/pipe/p_format.h src/gallium/include/pipe/p_screen.h src/gallium/include/pipe/p_video_context.h src/gallium/include/pipe/p_video_state.h src/gallium/include/state_tracker/dri1_api.h src/gallium/include/state_tracker/drm_api.h src/gallium/state_trackers/dri/common/dri_context.c src/gallium/state_trackers/xorg/xvmc/attributes.c src/gallium/state_trackers/xorg/xvmc/block.c src/gallium/state_trackers/xorg/xvmc/context.c src/gallium/state_trackers/xorg/xvmc/subpicture.c src/gallium/state_trackers/xorg/xvmc/surface.c src/gallium/state_trackers/xorg/xvmc/tests/.gitignore src/gallium/state_trackers/xorg/xvmc/tests/Makefile src/gallium/state_trackers/xorg/xvmc/xvmc_private.h src/gallium/winsys/drm/radeon/core/radeon_drm.c src/gallium/winsys/g3dvl/vl_winsys.h src/gallium/winsys/g3dvl/xlib/xsp_winsys.c src/gallium/winsys/sw/Makefile
Diffstat (limited to 'src/gallium/drivers/nv50/nv50_transfer.c')
-rw-r--r--src/gallium/drivers/nv50/nv50_transfer.c99
1 files changed, 56 insertions, 43 deletions
diff --git a/src/gallium/drivers/nv50/nv50_transfer.c b/src/gallium/drivers/nv50/nv50_transfer.c
index 7c360e9e73a..c5581a6f9d0 100644
--- a/src/gallium/drivers/nv50/nv50_transfer.c
+++ b/src/gallium/drivers/nv50/nv50_transfer.c
@@ -5,10 +5,13 @@
#include "util/u_math.h"
#include "nv50_context.h"
+#include "nv50_transfer.h"
+#include "nv50_resource.h"
struct nv50_transfer {
struct pipe_transfer base;
struct nouveau_bo *bo;
+ int map_refcnt;
unsigned level_offset;
unsigned level_tiling;
int level_pitch;
@@ -120,43 +123,51 @@ nv50_transfer_rect_m2mf(struct pipe_screen *pscreen,
}
}
-static struct pipe_transfer *
-nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,
- unsigned face, unsigned level, unsigned zslice,
- enum pipe_transfer_usage usage,
- unsigned x, unsigned y, unsigned w, unsigned h)
+struct pipe_transfer *
+nv50_miptree_transfer_new(struct pipe_context *pcontext,
+ struct pipe_resource *pt,
+ struct pipe_subresource sr,
+ unsigned usage,
+ const struct pipe_box *box)
{
+ struct pipe_screen *pscreen = pcontext->screen;
struct nouveau_device *dev = nouveau_screen(pscreen)->device;
struct nv50_miptree *mt = nv50_miptree(pt);
- struct nv50_miptree_level *lvl = &mt->level[level];
+ struct nv50_miptree_level *lvl = &mt->level[sr.level];
struct nv50_transfer *tx;
unsigned nx, ny, image = 0;
int ret;
if (pt->target == PIPE_TEXTURE_CUBE)
- image = face;
+ image = sr.face;
tx = CALLOC_STRUCT(nv50_transfer);
if (!tx)
return NULL;
- pipe_texture_reference(&tx->base.texture, pt);
- tx->nblocksx = util_format_get_nblocksx(pt->format, u_minify(pt->width0, level));
- tx->nblocksy = util_format_get_nblocksy(pt->format, u_minify(pt->height0, level));
- tx->base.width = w;
- tx->base.height = h;
+ /* Don't handle 3D transfers yet.
+ */
+ assert(box->depth == 1);
+
+
+ pipe_resource_reference(&tx->base.resource, pt);
+ tx->base.sr = sr;
+ tx->base.usage = usage;
+ tx->base.box = *box;
+ tx->nblocksx = util_format_get_nblocksx(pt->format, u_minify(pt->width0, sr.level));
+ tx->nblocksy = util_format_get_nblocksy(pt->format, u_minify(pt->height0, sr.level));
tx->base.stride = tx->nblocksx * util_format_get_blocksize(pt->format);
tx->base.usage = usage;
tx->level_pitch = lvl->pitch;
- tx->level_width = u_minify(mt->base.base.width0, level);
- tx->level_height = u_minify(mt->base.base.height0, level);
- tx->level_depth = u_minify(mt->base.base.depth0, level);
+ tx->level_width = u_minify(mt->base.base.width0, sr.level);
+ tx->level_height = u_minify(mt->base.base.height0, sr.level);
+ tx->level_depth = u_minify(mt->base.base.depth0, sr.level);
tx->level_offset = lvl->image_offset[image];
tx->level_tiling = lvl->tile_mode;
- tx->level_z = zslice;
- tx->level_x = util_format_get_nblocksx(pt->format, x);
- tx->level_y = util_format_get_nblocksy(pt->format, y);
+ tx->level_z = box->z;
+ tx->level_x = util_format_get_nblocksx(pt->format, box->x);
+ tx->level_y = util_format_get_nblocksy(pt->format, box->y);
ret = nouveau_bo_new(dev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP, 0,
tx->nblocksy * tx->base.stride, &tx->bo);
if (ret) {
@@ -165,12 +176,12 @@ nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,
}
if (usage & PIPE_TRANSFER_READ) {
- nx = util_format_get_nblocksx(pt->format, tx->base.width);
- ny = util_format_get_nblocksy(pt->format, tx->base.height);
+ nx = util_format_get_nblocksx(pt->format, box->width);
+ ny = util_format_get_nblocksy(pt->format, box->height);
nv50_transfer_rect_m2mf(pscreen, mt->base.bo, tx->level_offset,
tx->level_pitch, tx->level_tiling,
- x, y, zslice,
+ box->x, box->y, box->z,
tx->nblocksx, tx->nblocksy,
tx->level_depth,
tx->bo, 0,
@@ -185,18 +196,19 @@ nv50_transfer_new(struct pipe_screen *pscreen, struct pipe_texture *pt,
return &tx->base;
}
-static void
-nv50_transfer_del(struct pipe_transfer *ptx)
+void
+nv50_miptree_transfer_del(struct pipe_context *pcontext,
+ struct pipe_transfer *ptx)
{
struct nv50_transfer *tx = (struct nv50_transfer *)ptx;
- struct nv50_miptree *mt = nv50_miptree(ptx->texture);
- struct pipe_texture *pt = ptx->texture;
+ struct nv50_miptree *mt = nv50_miptree(ptx->resource);
+ struct pipe_resource *pt = ptx->resource;
- unsigned nx = util_format_get_nblocksx(pt->format, tx->base.width);
- unsigned ny = util_format_get_nblocksy(pt->format, tx->base.height);
+ unsigned nx = util_format_get_nblocksx(pt->format, tx->base.box.width);
+ unsigned ny = util_format_get_nblocksy(pt->format, tx->base.box.height);
if (ptx->usage & PIPE_TRANSFER_WRITE) {
- struct pipe_screen *pscreen = pt->screen;
+ struct pipe_screen *pscreen = pcontext->screen;
nv50_transfer_rect_m2mf(pscreen, tx->bo, 0,
tx->base.stride, tx->bo->tile_mode,
@@ -213,44 +225,45 @@ nv50_transfer_del(struct pipe_transfer *ptx)
}
nouveau_bo_ref(NULL, &tx->bo);
- pipe_texture_reference(&ptx->texture, NULL);
+ pipe_resource_reference(&ptx->resource, NULL);
FREE(ptx);
}
-static void *
-nv50_transfer_map(struct pipe_screen *pscreen, struct pipe_transfer *ptx)
+void *
+nv50_miptree_transfer_map(struct pipe_context *pcontext,
+ struct pipe_transfer *ptx)
{
struct nv50_transfer *tx = (struct nv50_transfer *)ptx;
unsigned flags = 0;
int ret;
+ if (tx->map_refcnt++)
+ return tx->bo->map;
+
if (ptx->usage & PIPE_TRANSFER_WRITE)
flags |= NOUVEAU_BO_WR;
if (ptx->usage & PIPE_TRANSFER_READ)
flags |= NOUVEAU_BO_RD;
ret = nouveau_bo_map(tx->bo, flags);
- if (ret)
+ if (ret) {
+ tx->map_refcnt = 0;
return NULL;
+ }
return tx->bo->map;
}
-static void
-nv50_transfer_unmap(struct pipe_screen *pscreen, struct pipe_transfer *ptx)
+void
+nv50_miptree_transfer_unmap(struct pipe_context *pcontext,
+ struct pipe_transfer *ptx)
{
struct nv50_transfer *tx = (struct nv50_transfer *)ptx;
+ if (--tx->map_refcnt)
+ return;
nouveau_bo_unmap(tx->bo);
}
-void
-nv50_transfer_init_screen_functions(struct pipe_screen *pscreen)
-{
- pscreen->get_tex_transfer = nv50_transfer_new;
- pscreen->tex_transfer_destroy = nv50_transfer_del;
- pscreen->transfer_map = nv50_transfer_map;
- pscreen->transfer_unmap = nv50_transfer_unmap;
-}
void
nv50_upload_sifc(struct nv50_context *nv50,
@@ -331,7 +344,7 @@ nv50_upload_sifc(struct nv50_context *nv50,
count -= nr;
}
- src += src_pitch;
+ src = (uint8_t *) src + src_pitch;
}
BEGIN_RING(chan, tesla, NV50TCL_CODE_CB_FLUSH, 1);