diff options
author | Richard Li <[email protected]> | 2009-05-08 19:23:45 -0400 |
---|---|---|
committer | Alex Deucher <[email protected]> | 2009-05-08 19:23:45 -0400 |
commit | e2dcebd2e6b2af6269a5ece6d6ced73ec8bb4a47 (patch) | |
tree | d8aa42c0ccdf36c283f548dec293d26ee4af601a /src/mesa/drivers/dri/r600/r600_emit.c | |
parent | 604dd37f66d9c0e83cb3a9012ff1fc35f38b3e37 (diff) |
R6xx/R7xx: WIP r6xx-rewrite code
Diffstat (limited to 'src/mesa/drivers/dri/r600/r600_emit.c')
-rw-r--r-- | src/mesa/drivers/dri/r600/r600_emit.c | 224 |
1 files changed, 215 insertions, 9 deletions
diff --git a/src/mesa/drivers/dri/r600/r600_emit.c b/src/mesa/drivers/dri/r600/r600_emit.c index 9d43873c4d8..fc8f987cabd 100644 --- a/src/mesa/drivers/dri/r600/r600_emit.c +++ b/src/mesa/drivers/dri/r600/r600_emit.c @@ -1,9 +1,8 @@ -/* -Copyright (C) The Weather Channel, Inc. 2002. All Rights Reserved. +/************************************************************************** + +Copyright 2008, 2009 Advanced Micro Devices Inc. (AMD) -The Weather Channel (TM) funded Tungsten Graphics to develop the -initial release of the Radeon 8500 driver under the XFree86 license. -This notice must be preserved. +Copyright (C) Advanced Micro Devices Inc. (AMD) 2009. All Rights Reserved. Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -27,10 +26,10 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. **************************************************************************/ -/** - * \file - * - * \author Keith Whitwell <[email protected]> +/* + * Authors: + * Richard Li <[email protected]>, <[email protected]> + * CooperYuan <[email protected]>, <[email protected]> */ #include "main/glheader.h" @@ -48,6 +47,105 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. #include "r600_context.h" #include "r600_emit.h" +#if defined(USE_X86_ASM) +#define COPY_DWORDS( dst, src, nr ) \ +do { \ + int __tmp; \ + __asm__ __volatile__( "rep ; movsl" \ + : "=%c" (__tmp), "=D" (dst), "=S" (__tmp) \ + : "0" (nr), \ + "D" ((long)dst), \ + "S" ((long)src) ); \ +} while (0) +#else +#define COPY_DWORDS( dst, src, nr ) \ +do { \ + int j; \ + for ( j = 0 ; j < nr ; j++ ) \ + dst[j] = ((int *)src)[j]; \ + dst += nr; \ +} while (0) +#endif + +static void r600EmitVec4(uint32_t *out, GLvoid * data, int stride, int count) +{ + int i; + + if (RADEON_DEBUG & DEBUG_VERTS) + fprintf(stderr, "%s count %d stride %d out %p data %p\n", + __FUNCTION__, count, stride, (void *)out, (void *)data); + + if (stride == 4) + COPY_DWORDS(out, data, count); + else + for (i = 0; i < count; i++) { + out[0] = *(int *)data; + out++; + data += stride; + } +} + +static void r600EmitVec8(uint32_t *out, GLvoid * data, int stride, int count) +{ + int i; + + if (RADEON_DEBUG & DEBUG_VERTS) + fprintf(stderr, "%s count %d stride %d out %p data %p\n", + __FUNCTION__, count, stride, (void *)out, (void *)data); + + if (stride == 8) + COPY_DWORDS(out, data, count * 2); + else + for (i = 0; i < count; i++) { + out[0] = *(int *)data; + out[1] = *(int *)(data + 4); + out += 2; + data += stride; + } +} + +static void r600EmitVec12(uint32_t *out, GLvoid * data, int stride, int count) +{ + int i; + + if (RADEON_DEBUG & DEBUG_VERTS) + fprintf(stderr, "%s count %d stride %d out %p data %p\n", + __FUNCTION__, count, stride, (void *)out, (void *)data); + + if (stride == 12) { + COPY_DWORDS(out, data, count * 3); + } + else + for (i = 0; i < count; i++) { + out[0] = *(int *)data; + out[1] = *(int *)(data + 4); + out[2] = *(int *)(data + 8); + out += 3; + data += stride; + } +} + +static void r600EmitVec16(uint32_t *out, GLvoid * data, int stride, int count) +{ + int i; + + if (RADEON_DEBUG & DEBUG_VERTS) + fprintf(stderr, "%s count %d stride %d out %p data %p\n", + __FUNCTION__, count, stride, (void *)out, (void *)data); + + if (stride == 16) + COPY_DWORDS(out, data, count * 4); + else + for (i = 0; i < count; i++) { + out[0] = *(int *)data; + out[1] = *(int *)(data + 4); + out[2] = *(int *)(data + 8); + out[3] = *(int *)(data + 12); + out += 4; + data += stride; + } +} + /* Emit vertex data to GART memory * Route inputs to the vertex processor * This function should never return R600_FALLBACK_TCL when using software tcl. @@ -73,3 +171,111 @@ void r600EmitCacheFlush(r600ContextPtr rmesa) COMMIT_BATCH(); */ } + +GLboolean r600EmitShader(GLcontext * ctx, + void ** shaderbo, + GLvoid * data, + int sizeinDWORD) +{ + radeonContextPtr radeonctx = RADEON_CONTEXT(ctx); + + struct radeon_bo * pbo; + uint32_t *out; + +shader_again_alloc: + pbo = radeon_bo_open(radeonctx->radeonScreen->bom, + 0, + sizeinDWORD * 4, + 256, + RADEON_GEM_DOMAIN_GTT, + 0); + + if (!pbo) + { + rcommonFlushCmdBuf(radeonctx, __FUNCTION__); + goto shader_again_alloc; + } + + radeon_validate_bo(radeonctx, pbo, RADEON_GEM_DOMAIN_GTT, 0); + + if (radeon_revalidate_bos(radeonctx->glCtx) == GL_FALSE) + { + fprintf(stderr,"failure to revalidate BOs - badness\n"); + } + + radeon_bo_map(pbo, 1); + + radeon_bo_ref(pbo); + + out = (uint32_t*)(pbo->ptr); + + memcpy(out, data, sizeinDWORD * 4); + + *shaderbo = (void*)pbo; + + return GL_TRUE; +} + +GLboolean r600DeleteShader(GLcontext * ctx, + void * shaderbo) +{ + struct radeon_bo * pbo = (struct radeon_bo *)shaderbo; + + radeon_bo_unmap(pbo); + radeon_bo_unref(pbo); /* when bo->cref <= 0, bo will be bo_free */ + + return GL_TRUE; +} + +GLboolean r600EmitVec(GLcontext * ctx, + struct radeon_aos *aos, + GLvoid * data, + int size, + int stride, + int count) +{ + radeonContextPtr rmesa = RADEON_CONTEXT(ctx); + uint32_t *out; + + if (stride == 0) + { + radeonAllocDmaRegion(rmesa, &aos->bo, &aos->offset, size * count * 4, 32); + aos->stride = 0; + } + else + { + radeonAllocDmaRegion(rmesa, &aos->bo, &aos->offset, size * count * 4, 32); + aos->stride = size; + } + + aos->components = size; + aos->count = count; + + out = (uint32_t*)((char*)aos->bo->ptr + aos->offset); + switch (size) { + case 1: r600EmitVec4(out, data, stride, count); break; + case 2: r600EmitVec8(out, data, stride, count); break; + case 3: r600EmitVec12(out, data, stride, count); break; + case 4: r600EmitVec16(out, data, stride, count); break; + default: + assert(0); + break; + } + + return GL_TRUE; +} + +void r600ReleaseVec(GLcontext * ctx) +{ + radeonReleaseArrays(ctx, ~0); +} + +void r600FreeDmaRegion(context_t *context, + void * shaderbo) +{ + struct radeon_bo *pbo = (struct radeon_bo *)shaderbo; + if(pbo) + { + radeon_bo_unref(pbo); + } +} |