summaryrefslogtreecommitdiffstats
path: root/src/gallium
diff options
context:
space:
mode:
Diffstat (limited to 'src/gallium')
-rw-r--r--src/gallium/auxiliary/Makefile1
-rw-r--r--src/gallium/auxiliary/SConscript1
-rw-r--r--src/gallium/auxiliary/gallivm/lp_bld_printf.c109
-rw-r--r--src/gallium/auxiliary/gallivm/lp_bld_printf.h39
-rw-r--r--src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c20
-rw-r--r--src/gallium/auxiliary/util/u_format.csv29
-rw-r--r--src/gallium/auxiliary/util/u_format.h20
-rw-r--r--src/gallium/drivers/i965/brw_screen_texture.c4
-rw-r--r--src/gallium/drivers/llvmpipe/Makefile3
-rw-r--r--src/gallium/drivers/llvmpipe/lp_test_printf.c162
-rw-r--r--src/gallium/drivers/r300/r300_texture.c2
-rw-r--r--src/gallium/drivers/svga/svga_screen_texture.c4
-rw-r--r--src/gallium/include/state_tracker/dri1_api.h8
-rw-r--r--src/gallium/include/state_tracker/drisw_api.h35
-rw-r--r--src/gallium/state_trackers/dri/common/dri_st_api.c2
-rw-r--r--src/gallium/state_trackers/dri/drm/dri1.c30
-rw-r--r--src/gallium/state_trackers/dri/sw/drisw.c100
-rw-r--r--src/gallium/state_trackers/dri/sw/drisw.h2
-rw-r--r--src/gallium/state_trackers/python/SConscript3
-rw-r--r--src/gallium/state_trackers/python/p_context.i287
-rw-r--r--src/gallium/state_trackers/python/p_texture.i226
-rw-r--r--src/gallium/state_trackers/python/st_sample.c30
-rw-r--r--src/gallium/state_trackers/python/st_sample.h7
-rw-r--r--src/gallium/targets/dri-swrast/swrast_drm_api.c17
-rw-r--r--src/gallium/targets/libgl-xlib/xlib.c8
-rw-r--r--src/gallium/winsys/sw/dri/dri_sw_winsys.c176
-rw-r--r--src/gallium/winsys/sw/dri/dri_sw_winsys.h4
27 files changed, 883 insertions, 446 deletions
diff --git a/src/gallium/auxiliary/Makefile b/src/gallium/auxiliary/Makefile
index e1c3bc43a24..452eceb7f4f 100644
--- a/src/gallium/auxiliary/Makefile
+++ b/src/gallium/auxiliary/Makefile
@@ -155,6 +155,7 @@ GALLIVM_SOURCES = \
gallivm/lp_bld_intr.c \
gallivm/lp_bld_logic.c \
gallivm/lp_bld_pack.c \
+ gallivm/lp_bld_printf.c \
gallivm/lp_bld_sample.c \
gallivm/lp_bld_sample_soa.c \
gallivm/lp_bld_struct.c \
diff --git a/src/gallium/auxiliary/SConscript b/src/gallium/auxiliary/SConscript
index 65e1dc8a58d..0a23da47b2a 100644
--- a/src/gallium/auxiliary/SConscript
+++ b/src/gallium/auxiliary/SConscript
@@ -200,6 +200,7 @@ if drawllvm:
'gallivm/lp_bld_logic.c',
'gallivm/lp_bld_init.cpp',
'gallivm/lp_bld_pack.c',
+ 'gallivm/lp_bld_printf.c',
'gallivm/lp_bld_sample.c',
'gallivm/lp_bld_sample_soa.c',
'gallivm/lp_bld_struct.c',
diff --git a/src/gallium/auxiliary/gallivm/lp_bld_printf.c b/src/gallium/auxiliary/gallivm/lp_bld_printf.c
new file mode 100644
index 00000000000..ae4d400af39
--- /dev/null
+++ b/src/gallium/auxiliary/gallivm/lp_bld_printf.c
@@ -0,0 +1,109 @@
+/**************************************************************************
+ *
+ * Copyright 2010 VMware, Inc.
+ * All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sub license, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+ * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
+ * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ **************************************************************************/
+
+#include <stdio.h>
+
+#include "lp_bld_printf.h"
+
+
+static int
+lp_get_printf_arg_count(const char *fmt)
+{
+ int count =0;
+ const char *p = fmt;
+ int c;
+
+ while ((c = *p++)) {
+ if (c != '%')
+ continue;
+ switch (*p) {
+ case '\0':
+ continue;
+ case '%':
+ p++;
+ continue;
+ case '.':
+ if (p[1] == '*' && p[2] == 's') {
+ count += 2;
+ p += 3;
+ continue;
+ }
+ default:
+ count ++;
+ }
+ }
+ return count;
+}
+
+LLVMValueRef
+lp_build_const_string_variable(LLVMModuleRef module, const char *str, int len)
+{
+ LLVMValueRef string = LLVMAddGlobal(module, LLVMArrayType(LLVMInt8Type(), len + 1), "");
+ LLVMSetGlobalConstant(string, TRUE);
+ LLVMSetLinkage(string, LLVMInternalLinkage);
+ LLVMSetInitializer(string, LLVMConstString(str, len + 1, TRUE));
+ return string;
+}
+
+
+/**
+ * lp_build_printf.
+ *
+ * Build printf call in LLVM IR. The output goes to stdout.
+ * The additional variable arguments need to have type
+ * LLVMValueRef.
+ */
+LLVMValueRef
+lp_build_printf(LLVMBuilderRef builder, const char *fmt, ...)
+{
+ va_list arglist;
+ int i = 0;
+ int argcount = lp_get_printf_arg_count(fmt);
+ LLVMModuleRef module = LLVMGetGlobalParent(LLVMGetBasicBlockParent(LLVMGetInsertBlock(builder)));
+ LLVMValueRef params[argcount + 1];
+ LLVMValueRef fmtarg = lp_build_const_string_variable(module, fmt, strlen(fmt) + 1);
+ LLVMValueRef int0 = LLVMConstInt(LLVMInt32Type(), 0, 0);
+ LLVMValueRef index[2];
+ LLVMValueRef func_printf = LLVMGetNamedFunction(module, "printf");
+
+ index[0] = index[1] = int0;
+
+ if (!func_printf) {
+ LLVMTypeRef printf_type = LLVMFunctionType(LLVMIntType(32), NULL, 0, 1);
+ func_printf = LLVMAddFunction(module, "printf", printf_type);
+ }
+
+ params[0] = LLVMBuildGEP(builder, fmtarg, index, 2, "");
+
+ va_start(arglist, fmt);
+ for (i = 1; i <= argcount; i++)
+ params[i] = va_arg(arglist, LLVMValueRef);
+ va_end(arglist);
+
+ return LLVMBuildCall(builder, func_printf, params, argcount + 1, "");
+}
+
diff --git a/src/gallium/auxiliary/gallivm/lp_bld_printf.h b/src/gallium/auxiliary/gallivm/lp_bld_printf.h
new file mode 100644
index 00000000000..83bd8f1d557
--- /dev/null
+++ b/src/gallium/auxiliary/gallivm/lp_bld_printf.h
@@ -0,0 +1,39 @@
+/**************************************************************************
+ *
+ * Copyright 2010 VMware, Inc.
+ * All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sub license, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+ * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
+ * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ **************************************************************************/
+
+#ifndef LP_BLD_PRINTF_H
+#define LP_BLD_PRINTF_H
+
+
+#include "pipe/p_compiler.h"
+#include "lp_bld.h"
+
+LLVMValueRef lp_build_const_string_variable(LLVMModuleRef module, const char *str, int len);
+LLVMValueRef lp_build_printf(LLVMBuilderRef builder, const char *fmt, ...);
+
+#endif
+
diff --git a/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c b/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
index f160be878f8..95cd6a0ecf3 100644
--- a/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
+++ b/src/gallium/auxiliary/gallivm/lp_bld_tgsi_soa.c
@@ -651,6 +651,19 @@ emit_declaration(
unsigned first = decl->Range.First;
unsigned last = decl->Range.Last;
unsigned idx, i;
+ LLVMBasicBlockRef current_block =
+ LLVMGetInsertBlock(bld->base.builder);
+ LLVMBasicBlockRef first_block =
+ LLVMGetEntryBasicBlock(
+ LLVMGetBasicBlockParent(current_block));
+ LLVMValueRef first_inst =
+ LLVMGetFirstInstruction(first_block);
+
+ /* we want alloca's to be the first instruction
+ * in the function so we need to rewind the builder
+ * to the very beginning */
+ LLVMPositionBuilderBefore(bld->base.builder,
+ first_inst);
for (idx = first; idx <= last; ++idx) {
boolean ok;
@@ -673,10 +686,15 @@ emit_declaration(
ok = TRUE;
}
- if (!ok)
+ if (!ok) {
+ LLVMPositionBuilderAtEnd(bld->base.builder,
+ current_block);
return FALSE;
+ }
}
+ LLVMPositionBuilderAtEnd(bld->base.builder,
+ current_block);
return TRUE;
}
diff --git a/src/gallium/auxiliary/util/u_format.csv b/src/gallium/auxiliary/util/u_format.csv
index f55bc3d805b..57e995c03be 100644
--- a/src/gallium/auxiliary/util/u_format.csv
+++ b/src/gallium/auxiliary/util/u_format.csv
@@ -121,18 +121,23 @@ PIPE_FORMAT_R9G9B9E5_FLOAT , compressed, 1, 1, x32 , , , , x
PIPE_FORMAT_R1_UNORM , compressed, 8, 1, x8 , , , , x001, rgb
# Compressed formats
-PIPE_FORMAT_DXT1_RGB , compressed, 4, 4, x64 , , , , xyz1, rgb
-PIPE_FORMAT_DXT1_RGBA , compressed, 4, 4, x64 , , , , xyzw, rgb
-PIPE_FORMAT_DXT3_RGBA , compressed, 4, 4, x128, , , , xyzw, rgb
-PIPE_FORMAT_DXT5_RGBA , compressed, 4, 4, x128, , , , xyzw, rgb
-PIPE_FORMAT_DXT1_SRGB , compressed, 4, 4, x64 , , , , xyz1, srgb
-PIPE_FORMAT_DXT1_SRGBA , compressed, 4, 4, x64 , , , , xyzw, srgb
-PIPE_FORMAT_DXT3_SRGBA , compressed, 4, 4, x128, , , , xyzw, srgb
-PIPE_FORMAT_DXT5_SRGBA , compressed, 4, 4, x128, , , , xyzw, srgb
-PIPE_FORMAT_RGTC1_UNORM , compressed, 4, 4, x64, , , , x001, rgb
-PIPE_FORMAT_RGTC1_SNORM , compressed, 4, 4, x64, , , , x001, rgb
-PIPE_FORMAT_RGTC2_UNORM , compressed, 4, 4, x128, , , , xy01, rgb
-PIPE_FORMAT_RGTC2_SNORM , compressed, 4, 4, x128, , , , xy01, rgb
+# - http://en.wikipedia.org/wiki/S3_Texture_Compression
+# - http://www.opengl.org/registry/specs/EXT/texture_compression_s3tc.txt
+# - http://www.opengl.org/registry/specs/ARB/texture_compression_rgtc.txt
+# - http://msdn.microsoft.com/en-us/library/bb694531.aspx
+PIPE_FORMAT_DXT1_RGB , s3tc, 4, 4, x64 , , , , xyz1, rgb
+PIPE_FORMAT_DXT1_RGBA , s3tc, 4, 4, x64 , , , , xyzw, rgb
+PIPE_FORMAT_DXT3_RGBA , s3tc, 4, 4, x128, , , , xyzw, rgb
+PIPE_FORMAT_DXT5_RGBA , s3tc, 4, 4, x128, , , , xyzw, rgb
+PIPE_FORMAT_DXT1_SRGB , s3tc, 4, 4, x64 , , , , xyz1, srgb
+PIPE_FORMAT_DXT1_SRGBA , s3tc, 4, 4, x64 , , , , xyzw, srgb
+PIPE_FORMAT_DXT3_SRGBA , s3tc, 4, 4, x128, , , , xyzw, srgb
+PIPE_FORMAT_DXT5_SRGBA , s3tc, 4, 4, x128, , , , xyzw, srgb
+
+PIPE_FORMAT_RGTC1_UNORM , rgtc, 4, 4, x64, , , , x001, rgb
+PIPE_FORMAT_RGTC1_SNORM , rgtc, 4, 4, x64, , , , x001, rgb
+PIPE_FORMAT_RGTC2_UNORM , rgtc, 4, 4, x128, , , , xy01, rgb
+PIPE_FORMAT_RGTC2_SNORM , rgtc, 4, 4, x128, , , , xy01, rgb
# Straightforward D3D10-like formats (also used for
# vertex buffer element description)
diff --git a/src/gallium/auxiliary/util/u_format.h b/src/gallium/auxiliary/util/u_format.h
index c08fdcafcc8..98d4b98ebb5 100644
--- a/src/gallium/auxiliary/util/u_format.h
+++ b/src/gallium/auxiliary/util/u_format.h
@@ -56,15 +56,23 @@ enum util_format_layout {
*
* This is for formats like YV12 where there is less than one sample per
* pixel.
- *
- * XXX: This could actually b
*/
UTIL_FORMAT_LAYOUT_SUBSAMPLED = 3,
/**
- * An unspecified compression algorithm.
+ * S3 Texture Compression formats.
+ */
+ UTIL_FORMAT_LAYOUT_S3TC = 4,
+
+ /**
+ * Red-Green Texture Compression formats.
+ */
+ UTIL_FORMAT_LAYOUT_RGTC = 5,
+
+ /**
+ * Everything else that doesn't fit in any of the above layouts.
*/
- UTIL_FORMAT_LAYOUT_COMPRESSED = 4
+ UTIL_FORMAT_LAYOUT_OTHER = 6
};
@@ -210,7 +218,7 @@ util_format_name(enum pipe_format format)
}
static INLINE boolean
-util_format_is_compressed(enum pipe_format format)
+util_format_is_s3tc(enum pipe_format format)
{
const struct util_format_description *desc = util_format_description(format);
@@ -219,7 +227,7 @@ util_format_is_compressed(enum pipe_format format)
return FALSE;
}
- return desc->layout == UTIL_FORMAT_LAYOUT_COMPRESSED ? TRUE : FALSE;
+ return desc->layout == UTIL_FORMAT_LAYOUT_S3TC ? TRUE : FALSE;
}
static INLINE boolean
diff --git a/src/gallium/drivers/i965/brw_screen_texture.c b/src/gallium/drivers/i965/brw_screen_texture.c
index 613ac784207..5825928e28f 100644
--- a/src/gallium/drivers/i965/brw_screen_texture.c
+++ b/src/gallium/drivers/i965/brw_screen_texture.c
@@ -206,7 +206,7 @@ static struct pipe_texture *brw_texture_create( struct pipe_screen *screen,
/* XXX: compressed textures need special treatment here
*/
tex->cpp = util_format_get_blocksize(tex->base.format);
- tex->compressed = util_format_is_compressed(tex->base.format);
+ tex->compressed = util_format_is_s3tc(tex->base.format);
make_empty_list(&tex->views[0]);
make_empty_list(&tex->views[1]);
@@ -321,7 +321,7 @@ brw_texture_from_handle(struct pipe_screen *screen,
templ->depth0 != 1)
return NULL;
- if (util_format_is_compressed(templ->format))
+ if (util_format_is_s3tc(templ->format))
return NULL;
tex = CALLOC_STRUCT(brw_texture);
diff --git a/src/gallium/drivers/llvmpipe/Makefile b/src/gallium/drivers/llvmpipe/Makefile
index 74d728ddb39..b37c6754c08 100644
--- a/src/gallium/drivers/llvmpipe/Makefile
+++ b/src/gallium/drivers/llvmpipe/Makefile
@@ -44,7 +44,8 @@ CPP_SOURCES = \
PROGS := lp_test_format \
lp_test_blend \
- lp_test_conv
+ lp_test_conv \
+ lp_test_printf
include ../../Makefile.template
diff --git a/src/gallium/drivers/llvmpipe/lp_test_printf.c b/src/gallium/drivers/llvmpipe/lp_test_printf.c
new file mode 100644
index 00000000000..e5e5925012a
--- /dev/null
+++ b/src/gallium/drivers/llvmpipe/lp_test_printf.c
@@ -0,0 +1,162 @@
+/**************************************************************************
+ *
+ * Copyright 2010 VMware, Inc.
+ * All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sub license, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
+ * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
+ * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ **************************************************************************/
+
+
+#include <stdlib.h>
+#include <stdio.h>
+
+#include "gallivm/lp_bld.h"
+#include "gallivm/lp_bld_printf.h"
+
+#include <llvm-c/Analysis.h>
+#include <llvm-c/ExecutionEngine.h>
+#include <llvm-c/Target.h>
+#include <llvm-c/Transforms/Scalar.h>
+
+#include "lp_test.h"
+
+
+struct printf_test_case {
+};
+
+void
+write_tsv_header(FILE *fp)
+{
+ fprintf(fp,
+ "result\t"
+ "format\n");
+
+ fflush(fp);
+}
+
+
+
+typedef void (*test_printf_t)(int i);
+
+static LLVMValueRef
+add_printf_test(LLVMModuleRef module)
+{
+ LLVMTypeRef args[1] = { LLVMIntType(32) };
+ LLVMValueRef func = LLVMAddFunction(module, "test_printf", LLVMFunctionType(LLVMVoidType(), args, 1, 0));
+ LLVMBuilderRef builder = LLVMCreateBuilder();
+ LLVMBasicBlockRef block = LLVMAppendBasicBlock(func, "entry");
+
+ LLVMSetFunctionCallConv(func, LLVMCCallConv);
+
+ LLVMPositionBuilderAtEnd(builder, block);
+ lp_build_printf(builder, "hello, world\n");
+ lp_build_printf(builder, "print 5 6: %d %d\n", LLVMConstInt(LLVMInt32Type(), 5, 0),
+ LLVMConstInt(LLVMInt32Type(), 6, 0));
+ LLVMBuildRetVoid(builder);
+ LLVMDisposeBuilder(builder);
+ return func;
+}
+
+
+PIPE_ALIGN_STACK
+static boolean
+test_printf(unsigned verbose, FILE *fp, const struct printf_test_case *testcase)
+{
+ LLVMModuleRef module = NULL;
+ LLVMValueRef test = NULL;
+ LLVMExecutionEngineRef engine = NULL;
+ LLVMModuleProviderRef provider = NULL;
+ LLVMPassManagerRef pass = NULL;
+ char *error = NULL;
+ test_printf_t test_printf;
+ float unpacked[4];
+ unsigned packed;
+ boolean success = TRUE;
+
+ module = LLVMModuleCreateWithName("test");
+
+ test = add_printf_test(module);
+
+ if(LLVMVerifyModule(module, LLVMPrintMessageAction, &error)) {
+ LLVMDumpModule(module);
+ abort();
+ }
+ LLVMDisposeMessage(error);
+
+ provider = LLVMCreateModuleProviderForExistingModule(module);
+ if (LLVMCreateJITCompiler(&engine, provider, 1, &error)) {
+ fprintf(stderr, "%s\n", error);
+ LLVMDisposeMessage(error);
+ abort();
+ }
+
+#if 0
+ pass = LLVMCreatePassManager();
+ LLVMAddTargetData(LLVMGetExecutionEngineTargetData(engine), pass);
+ /* These are the passes currently listed in llvm-c/Transforms/Scalar.h,
+ * but there are more on SVN. */
+ LLVMAddConstantPropagationPass(pass);
+ LLVMAddInstructionCombiningPass(pass);
+ LLVMAddPromoteMemoryToRegisterPass(pass);
+ LLVMAddGVNPass(pass);
+ LLVMAddCFGSimplificationPass(pass);
+ LLVMRunPassManager(pass, module);
+#else
+ (void)pass;
+#endif
+
+ test_printf = (test_printf_t)LLVMGetPointerToGlobal(engine, test);
+
+ memset(unpacked, 0, sizeof unpacked);
+ packed = 0;
+
+
+ // LLVMDumpModule(module);
+
+ test_printf(0);
+
+ LLVMFreeMachineCodeForFunction(engine, test);
+
+ LLVMDisposeExecutionEngine(engine);
+ if(pass)
+ LLVMDisposePassManager(pass);
+
+ return success;
+}
+
+
+boolean
+test_all(unsigned verbose, FILE *fp)
+{
+ bool success = TRUE;
+
+ test_printf(verbose, fp, NULL);
+
+ return success;
+}
+
+
+boolean
+test_some(unsigned verbose, FILE *fp, unsigned long n)
+{
+ return test_all(verbose, fp);
+}
diff --git a/src/gallium/drivers/r300/r300_texture.c b/src/gallium/drivers/r300/r300_texture.c
index bc7e6060636..28cc822b13d 100644
--- a/src/gallium/drivers/r300/r300_texture.c
+++ b/src/gallium/drivers/r300/r300_texture.c
@@ -159,7 +159,7 @@ static uint32_t r300_translate_texformat(enum pipe_format format)
}
/* Compressed formats. */
- if (desc->layout == UTIL_FORMAT_LAYOUT_COMPRESSED) {
+ if (desc->layout == UTIL_FORMAT_LAYOUT_S3TC) {
switch (format) {
case PIPE_FORMAT_DXT1_RGB:
case PIPE_FORMAT_DXT1_RGBA:
diff --git a/src/gallium/drivers/svga/svga_screen_texture.c b/src/gallium/drivers/svga/svga_screen_texture.c
index 41f88eed72c..811c7466956 100644
--- a/src/gallium/drivers/svga/svga_screen_texture.c
+++ b/src/gallium/drivers/svga/svga_screen_texture.c
@@ -330,7 +330,7 @@ svga_texture_create(struct pipe_screen *screen,
*/
#if 0
if((templat->tex_usage & PIPE_TEXTURE_USAGE_RENDER_TARGET) &&
- !util_format_is_compressed(templat->format))
+ !util_format_is_s3tc(templat->format))
tex->key.flags |= SVGA3D_SURFACE_HINT_RENDERTARGET;
#endif
@@ -969,7 +969,7 @@ svga_get_tex_sampler_view(struct pipe_context *pipe, struct pipe_texture *pt,
if (min_lod == 0 && max_lod >= pt->last_level)
view = FALSE;
- if (util_format_is_compressed(pt->format) && view) {
+ if (util_format_is_s3tc(pt->format) && view) {
format = svga_translate_format_render(pt->format);
}
diff --git a/src/gallium/include/state_tracker/dri1_api.h b/src/gallium/include/state_tracker/dri1_api.h
index 27b7a28c467..bb1cd6d1d82 100644
--- a/src/gallium/include/state_tracker/dri1_api.h
+++ b/src/gallium/include/state_tracker/dri1_api.h
@@ -7,14 +7,14 @@
#include "state_tracker/drm_api.h"
-struct drm_clip_rect;
-
struct pipe_screen;
struct pipe_winsys;
struct pipe_buffer;
struct pipe_context;
struct pipe_texture;
+struct drm_clip_rect;
+
struct dri1_api_version
{
int major;
@@ -31,8 +31,8 @@ struct dri1_api_lock_funcs
{
void (*lock) (struct pipe_context * pipe);
void (*unlock) (struct pipe_context * locked_pipe);
- boolean(*is_locked) (struct pipe_context * locked_pipe);
- boolean(*is_lock_lost) (struct pipe_context * locked_pipe);
+ boolean(*is_locked) (struct pipe_context * locked_pipe);
+ boolean(*is_lock_lost) (struct pipe_context * locked_pipe);
void (*clear_lost_lock) (struct pipe_context * locked_pipe);
};
diff --git a/src/gallium/include/state_tracker/drisw_api.h b/src/gallium/include/state_tracker/drisw_api.h
new file mode 100644
index 00000000000..c6adebb4ec5
--- /dev/null
+++ b/src/gallium/include/state_tracker/drisw_api.h
@@ -0,0 +1,35 @@
+#ifndef _DRISW_API_H_
+#define _DRISW_API_H_
+
+#include "pipe/p_compiler.h"
+#include "pipe/p_screen.h"
+#include "pipe/p_format.h"
+
+#include "state_tracker/drm_api.h"
+
+struct pipe_screen;
+struct pipe_winsys;
+struct pipe_buffer;
+struct pipe_context;
+struct pipe_texture;
+
+struct dri_drawable;
+
+/**
+ * This callback struct is intended for the winsys to call the loader.
+ */
+
+struct drisw_loader_funcs
+{
+ void (*put_image) (struct dri_drawable *dri_drawable,
+ void *data, unsigned width, unsigned height);
+};
+
+struct drisw_create_screen_arg
+{
+ struct drm_create_screen_arg base;
+
+ struct drisw_loader_funcs *lf;
+};
+
+#endif
diff --git a/src/gallium/state_trackers/dri/common/dri_st_api.c b/src/gallium/state_trackers/dri/common/dri_st_api.c
index 40b24b18e9f..7ba7ec383d8 100644
--- a/src/gallium/state_trackers/dri/common/dri_st_api.c
+++ b/src/gallium/state_trackers/dri/common/dri_st_api.c
@@ -80,7 +80,7 @@ dri_st_framebuffer_validate(struct st_framebuffer_iface *stfbi,
}
#else
if (new_stamp)
- drisw_update_drawable_info(drawable->dPriv);
+ drisw_update_drawable_info(drawable);
drisw_allocate_textures(drawable, statt_mask);
#endif
diff --git a/src/gallium/state_trackers/dri/drm/dri1.c b/src/gallium/state_trackers/dri/drm/dri1.c
index aad098bb301..9b5842ba2bf 100644
--- a/src/gallium/state_trackers/dri/drm/dri1.c
+++ b/src/gallium/state_trackers/dri/drm/dri1.c
@@ -404,6 +404,19 @@ dri1_allocate_textures(struct dri_drawable *drawable,
drawable->old_h = height;
}
+/*
+ * Backend function for init_screen.
+ */
+
+static const __DRIextension *dri1_screen_extensions[] = {
+ &driReadDrawableExtension,
+ &driCopySubBufferExtension.base,
+ &driSwapControlExtension.base,
+ &driFrameTrackingExtension.base,
+ &driMediaStreamCounterExtension.base,
+ NULL
+};
+
static void
st_dri_lock(struct pipe_context *pipe)
{
@@ -442,21 +455,6 @@ static struct dri1_api_lock_funcs dri1_lf = {
.clear_lost_lock = st_dri_clear_lost_lock
};
-/*
- * Backend function for init_screen.
- */
-
-static const __DRIextension *dri1_screen_extensions[] = {
- &driReadDrawableExtension,
- &driCopySubBufferExtension.base,
- &driSwapControlExtension.base,
- &driFrameTrackingExtension.base,
- &driMediaStreamCounterExtension.base,
- NULL
-};
-
-struct dri1_api *__dri1_api_hooks = NULL;
-
static INLINE void
dri1_copy_version(struct dri1_api_version *dst,
const struct __DRIversionRec *src)
@@ -466,6 +464,8 @@ dri1_copy_version(struct dri1_api_version *dst,
dst->patch_level = src->patch;
}
+struct dri1_api *__dri1_api_hooks = NULL;
+
const __DRIconfig **
dri1_init_screen(__DRIscreen * sPriv)
{
diff --git a/src/gallium/state_trackers/dri/sw/drisw.c b/src/gallium/state_trackers/dri/sw/drisw.c
index b7eba63bcb9..b8256710972 100644
--- a/src/gallium/state_trackers/dri/sw/drisw.c
+++ b/src/gallium/state_trackers/dri/sw/drisw.c
@@ -28,37 +28,17 @@
/* TODO:
*
- * stride:
- *
- * The driver and the loaders (libGL, xserver/glx) compute the stride from the
- * width independently. winsys has a workaround that works for softpipe but may
- * explode for other drivers or platforms, rendering- or performance-wise.
- * Solving this issue properly requires extending the DRISW loader extension,
- * in order to make the stride available to the putImage callback.
- *
- * drisw_api:
- *
- * Define drisw_api similarly to dri1_api and use it to call the loader. This
- * is predicated on support for calling the loader from the winsys, which has
- * to grow for DRI2 as well.
- *
* xshm / texture_from_pixmap / EGLImage:
*
* Allow the loaders to use the XSHM extension. It probably requires callbacks
- * for createImage/destroyImage similar to DRI2 getBuffers. Probably not worth
- * it, given the scope of DRISW, unless it falls naturally from properly
- * solving the other issues.
- *
- * fences:
- *
- * No fences are used, are they needed for llvmpipe / cell ?
+ * for createImage/destroyImage similar to DRI2 getBuffers.
*/
#include "util/u_format.h"
#include "util/u_memory.h"
#include "util/u_inlines.h"
#include "pipe/p_context.h"
-#include "state_tracker/drm_api.h"
+#include "state_tracker/drisw_api.h"
#include "dri_screen.h"
#include "dri_context.h"
@@ -80,60 +60,47 @@ get_drawable_info(__DRIdrawable *dPriv, int *w, int *h)
dPriv->loaderPrivate);
}
-/*
- * Set the width to 'stride / cpp'. PutImage seems to correctly clip the width
- * to the actual width of the dst drawable. Even if this is not specified but
- * an implementation detail, it is the correct thing to do, so rely on it. XXX
- */
static INLINE void
-put_image(__DRIdrawable *dPriv, void *data, unsigned width)
+put_image(__DRIdrawable *dPriv, void *data, unsigned width, unsigned height)
{
__DRIscreen *sPriv = dPriv->driScreenPriv;
const __DRIswrastLoaderExtension *loader = sPriv->swrast_loader;
loader->putImage(dPriv, __DRI_SWRAST_IMAGE_OP_SWAP,
- 0, 0, width, dPriv->h,
+ 0, 0, width, height,
data, dPriv->loaderPrivate);
}
void
-drisw_update_drawable_info(__DRIdrawable *dPriv)
+drisw_update_drawable_info(struct dri_drawable *drawable)
{
+ __DRIdrawable *dPriv = drawable->dPriv;
+
get_drawable_info(dPriv, &dPriv->w, &dPriv->h);
}
+static void
+drisw_put_image(struct dri_drawable *drawable,
+ void *data, unsigned width, unsigned height)
+{
+ __DRIdrawable *dPriv = drawable->dPriv;
+
+ put_image(dPriv, data, width, height);
+}
+
static INLINE void
drisw_present_texture(__DRIdrawable *dPriv,
struct pipe_texture *ptex)
{
struct dri_drawable *drawable = dri_drawable(dPriv);
struct dri_screen *screen = dri_screen(drawable->sPriv);
- struct pipe_context *pipe;
struct pipe_surface *psurf;
- struct pipe_transfer *ptrans;
- void *pmap;
- unsigned width;
- pipe = dri1_get_pipe_context(screen);
psurf = dri1_get_pipe_surface(drawable, ptex);
- if (!pipe || !psurf)
+ if (!psurf)
return;
- ptrans = pipe->get_tex_transfer(pipe, ptex, 0, 0, 0,
- PIPE_TRANSFER_READ,
- 0, 0, dPriv->w, dPriv->h);
-
- width = ptrans->stride / util_format_get_blocksize(ptex->format);
-
- pmap = pipe->transfer_map(pipe, ptrans);
-
- assert(pmap);
-
- put_image(dPriv, pmap, width);
-
- pipe->transfer_unmap(pipe, ptrans);
-
- pipe->tex_transfer_destroy(pipe, ptrans);
+ screen->pipe_screen->flush_frontbuffer(screen->pipe_screen, psurf, drawable);
}
static INLINE void
@@ -163,38 +130,38 @@ drisw_copy_to_front(__DRIdrawable * dPriv,
*/
void
-drisw_flush_frontbuffer(struct dri_drawable *drawable,
- enum st_attachment_type statt)
+drisw_swap_buffers(__DRIdrawable *dPriv)
{
struct dri_context *ctx = dri_get_current();
+ struct dri_drawable *drawable = dri_drawable(dPriv);
struct pipe_texture *ptex;
if (!ctx)
return;
- ptex = drawable->textures[statt];
+ ptex = drawable->textures[ST_ATTACHMENT_BACK_LEFT];
if (ptex) {
- drisw_copy_to_front(ctx->dPriv, ptex);
+ ctx->st->flush(ctx->st, PIPE_FLUSH_RENDER_CACHE, NULL);
+
+ drisw_copy_to_front(dPriv, ptex);
}
}
void
-drisw_swap_buffers(__DRIdrawable *dPriv)
+drisw_flush_frontbuffer(struct dri_drawable *drawable,
+ enum st_attachment_type statt)
{
struct dri_context *ctx = dri_get_current();
- struct dri_drawable *drawable = dri_drawable(dPriv);
struct pipe_texture *ptex;
if (!ctx)
return;
- ptex = drawable->textures[ST_ATTACHMENT_BACK_LEFT];
+ ptex = drawable->textures[statt];
if (ptex) {
- ctx->st->flush(ctx->st, PIPE_FLUSH_RENDER_CACHE, NULL);
-
- drisw_copy_to_front(dPriv, ptex);
+ drisw_copy_to_front(ctx->dPriv, ptex);
}
}
@@ -286,12 +253,16 @@ static const __DRIextension *drisw_screen_extensions[] = {
NULL
};
+static struct drisw_loader_funcs drisw_lf = {
+ .put_image = drisw_put_image
+};
+
const __DRIconfig **
drisw_init_screen(__DRIscreen * sPriv)
{
const __DRIconfig **configs;
struct dri_screen *screen;
- struct drm_create_screen_arg arg;
+ struct drisw_create_screen_arg arg;
screen = CALLOC_STRUCT(dri_screen);
if (!screen)
@@ -304,9 +275,10 @@ drisw_init_screen(__DRIscreen * sPriv)
sPriv->private = (void *)screen;
sPriv->extensions = drisw_screen_extensions;
- arg.mode = DRM_CREATE_DRISW;
+ arg.base.mode = DRM_CREATE_DRISW;
+ arg.lf = &drisw_lf;
- configs = dri_init_screen_helper(screen, &arg, 32);
+ configs = dri_init_screen_helper(screen, &arg.base, 32);
if (!configs)
goto fail;
diff --git a/src/gallium/state_trackers/dri/sw/drisw.h b/src/gallium/state_trackers/dri/sw/drisw.h
index 2c0d5610fac..c0c874f7326 100644
--- a/src/gallium/state_trackers/dri/sw/drisw.h
+++ b/src/gallium/state_trackers/dri/sw/drisw.h
@@ -39,7 +39,7 @@ const __DRIconfig **
drisw_init_screen(__DRIscreen * sPriv);
void
-drisw_update_drawable_info(__DRIdrawable *dPriv);
+drisw_update_drawable_info(struct dri_drawable *drawable);
void
drisw_flush_frontbuffer(struct dri_drawable *drawable,
diff --git a/src/gallium/state_trackers/python/SConscript b/src/gallium/state_trackers/python/SConscript
index d0d141fd249..781f54bf2b9 100644
--- a/src/gallium/state_trackers/python/SConscript
+++ b/src/gallium/state_trackers/python/SConscript
@@ -3,8 +3,7 @@ import os.path
Import('*')
-if 'python' in env['statetrackers'] and 0:
- # FIXME: Disable python state tracker until transfers are done by contexts
+if 'python' in env['statetrackers']:
env = env.Clone()
diff --git a/src/gallium/state_trackers/python/p_context.i b/src/gallium/state_trackers/python/p_context.i
index df700bc663c..bccaeead015 100644
--- a/src/gallium/state_trackers/python/p_context.i
+++ b/src/gallium/state_trackers/python/p_context.i
@@ -280,8 +280,11 @@ struct st_context {
struct pipe_context *pipe = $self->pipe;
struct pipe_screen *screen = pipe->screen;
struct pipe_buffer *vbuf;
+ struct pipe_vertex_element velements[PIPE_MAX_ATTRIBS];
+ struct pipe_vertex_buffer vbuffer;
float *map;
unsigned size;
+ unsigned i;
size = num_verts * num_attribs * 4 * sizeof(float);
@@ -297,9 +300,31 @@ struct st_context {
goto error2;
memcpy(map, vertices, size);
pipe_buffer_unmap(screen, vbuf);
-
- util_draw_vertex_buffer(pipe, vbuf, 0, prim, num_verts, num_attribs);
-
+
+ cso_save_vertex_elements($self->cso);
+
+ /* tell pipe about the vertex attributes */
+ for (i = 0; i < num_attribs; i++) {
+ velements[i].src_offset = i * 4 * sizeof(float);
+ velements[i].instance_divisor = 0;
+ velements[i].vertex_buffer_index = 0;
+ velements[i].src_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
+ }
+ cso_set_vertex_elements($self->cso, num_attribs, velements);
+
+ /* tell pipe about the vertex buffer */
+ memset(&vbuffer, 0, sizeof(vbuffer));
+ vbuffer.buffer = vbuf;
+ vbuffer.stride = num_attribs * 4 * sizeof(float); /* vertex size */
+ vbuffer.buffer_offset = 0;
+ vbuffer.max_index = num_verts - 1;
+ pipe->set_vertex_buffers(pipe, 1, &vbuffer);
+
+ /* draw */
+ pipe->draw_arrays(pipe, prim, 0, num_verts);
+
+ cso_restore_vertex_elements($self->cso);
+
error2:
pipe_buffer_reference(&vbuf, NULL);
error1:
@@ -307,6 +332,13 @@ error1:
}
void
+ clear(unsigned buffers, const float *rgba, double depth = 0.0f,
+ unsigned stencil = 0)
+ {
+ $self->pipe->clear($self->pipe, buffers, rgba, depth, stencil);
+ }
+
+ void
flush(unsigned flags = 0) {
struct pipe_fence_handle *fence = NULL;
$self->pipe->flush($self->pipe, flags | PIPE_FLUSH_RENDER_CACHE, &fence);
@@ -362,10 +394,253 @@ error1:
pipe_surface_reference(&_dst, NULL);
}
- void clear(unsigned buffers, const float *rgba, double depth = 0.0f,
- unsigned stencil = 0)
+ %cstring_output_allocate_size(char **STRING, int *LENGTH, free(*$1));
+ void
+ surface_read_raw(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ char **STRING, int *LENGTH)
{
- $self->pipe->clear($self->pipe, buffers, rgba, depth, stencil);
+ struct pipe_texture *texture = surface->texture;
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ unsigned stride;
+
+ stride = util_format_get_stride(texture->format, w);
+ *LENGTH = util_format_get_nblocksy(texture->format, h) * stride;
+ *STRING = (char *) malloc(*LENGTH);
+ if(!*STRING)
+ return;
+
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_READ,
+ x, y, w, h);
+ if(transfer) {
+ pipe_get_tile_raw(pipe, transfer, 0, 0, w, h, *STRING, stride);
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+ }
+
+ %cstring_input_binary(const char *STRING, unsigned LENGTH);
+ void
+ surface_write_raw(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ const char *STRING, unsigned LENGTH, unsigned stride = 0)
+ {
+ struct pipe_texture *texture = surface->texture;
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+
+ if(stride == 0)
+ stride = util_format_get_stride(texture->format, w);
+
+ if(LENGTH < util_format_get_nblocksy(texture->format, h) * stride)
+ SWIG_exception(SWIG_ValueError, "offset must be smaller than buffer size");
+
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_WRITE,
+ x, y, w, h);
+ if(!transfer)
+ SWIG_exception(SWIG_MemoryError, "couldn't initiate transfer");
+
+ pipe_put_tile_raw(pipe, transfer, 0, 0, w, h, STRING, stride);
+ pipe->tex_transfer_destroy(pipe, transfer);
+
+ fail:
+ return;
+ }
+
+ void
+ surface_read_rgba(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ float *rgba)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_READ,
+ x, y, w, h);
+ if(transfer) {
+ pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+ }
+
+ void
+ surface_write_rgba(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ const float *rgba)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_WRITE,
+ x, y, w, h);
+ if(transfer) {
+ pipe_put_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+ }
+
+ %cstring_output_allocate_size(char **STRING, int *LENGTH, free(*$1));
+ void
+ surface_read_rgba8(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ char **STRING, int *LENGTH)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ float *rgba;
+ unsigned char *rgba8;
+ unsigned i, j, k;
+
+ *LENGTH = 0;
+ *STRING = NULL;
+
+ if (!surface)
+ return;
+
+ *LENGTH = h*w*4;
+ *STRING = (char *) malloc(*LENGTH);
+ if(!*STRING)
+ return;
+
+ rgba = malloc(h*w*4*sizeof(float));
+ if(!rgba)
+ return;
+
+ rgba8 = (unsigned char *) *STRING;
+
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_READ,
+ x, y,
+ w, h);
+ if(transfer) {
+ pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
+ for(j = 0; j < h; ++j) {
+ for(i = 0; i < w; ++i)
+ for(k = 0; k <4; ++k)
+ rgba8[j*w*4 + i*4 + k] = float_to_ubyte(rgba[j*w*4 + i*4 + k]);
+ }
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+
+ free(rgba);
+ }
+
+ void
+ surface_read_z(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ unsigned *z)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_READ,
+ x, y, w, h);
+ if(transfer) {
+ pipe_get_tile_z(pipe, transfer, 0, 0, w, h, z);
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+ }
+
+ void
+ surface_write_z(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ const unsigned *z)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_WRITE,
+ x, y, w, h);
+ if(transfer) {
+ pipe_put_tile_z(pipe, transfer, 0, 0, w, h, z);
+ pipe->tex_transfer_destroy(pipe, transfer);
+ }
+ }
+
+ void
+ surface_sample_rgba(struct st_surface *surface,
+ float *rgba)
+ {
+ st_sample_surface($self->pipe, surface, rgba);
+ }
+
+ unsigned
+ surface_compare_rgba(struct st_surface *surface,
+ unsigned x, unsigned y, unsigned w, unsigned h,
+ const float *rgba, float tol = 0.0)
+ {
+ struct pipe_context *pipe = $self->pipe;
+ struct pipe_transfer *transfer;
+ float *rgba2;
+ const float *p1;
+ const float *p2;
+ unsigned i, j, n;
+
+ rgba2 = MALLOC(h*w*4*sizeof(float));
+ if(!rgba2)
+ return ~0;
+
+ transfer = pipe->get_tex_transfer(pipe,
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_READ,
+ x, y, w, h);
+ if(!transfer) {
+ FREE(rgba2);
+ return ~0;
+ }
+
+ pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba2);
+ pipe->tex_transfer_destroy(pipe, transfer);
+
+ p1 = rgba;
+ p2 = rgba2;
+ n = 0;
+ for(i = h*w; i; --i) {
+ unsigned differs = 0;
+ for(j = 4; j; --j) {
+ float delta = *p2++ - *p1++;
+ if (delta < -tol || delta > tol)
+ differs = 1;
+ }
+ n += differs;
+ }
+
+ FREE(rgba2);
+
+ return n;
}
};
diff --git a/src/gallium/state_trackers/python/p_texture.i b/src/gallium/state_trackers/python/p_texture.i
index 2dd9e5050ea..923a6285289 100644
--- a/src/gallium/state_trackers/python/p_texture.i
+++ b/src/gallium/state_trackers/python/p_texture.i
@@ -124,232 +124,6 @@ struct st_surface
FREE($self);
}
- %cstring_output_allocate_size(char **STRING, int *LENGTH, free(*$1));
- void get_tile_raw(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, char **STRING, int *LENGTH)
- {
- struct pipe_texture *texture = $self->texture;
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- unsigned stride;
-
- stride = util_format_get_stride(texture->format, w);
- *LENGTH = util_format_get_nblocksy(texture->format, h) * stride;
- *STRING = (char *) malloc(*LENGTH);
- if(!*STRING)
- return;
-
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_READ,
- x, y, w, h);
- if(transfer) {
- pipe_get_tile_raw(pipe, transfer, 0, 0, w, h, *STRING, stride);
- pipe->tex_transfer_destroy(pipe, transfer);
- }
- }
-
- %cstring_input_binary(const char *STRING, unsigned LENGTH);
- void put_tile_raw(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, const char *STRING, unsigned LENGTH, unsigned stride = 0)
- {
- struct pipe_texture *texture = $self->texture;
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
-
- if(stride == 0)
- stride = util_format_get_stride(texture->format, w);
-
- if(LENGTH < util_format_get_nblocksy(texture->format, h) * stride)
- SWIG_exception(SWIG_ValueError, "offset must be smaller than buffer size");
-
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_WRITE,
- x, y, w, h);
- if(!transfer)
- SWIG_exception(SWIG_MemoryError, "couldn't initiate transfer");
-
- pipe_put_tile_raw(pipe, transfer, 0, 0, w, h, STRING, stride);
- pipe->tex_transfer_destroy(pipe, transfer);
-
- fail:
- return;
- }
-
- void get_tile_rgba(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, float *rgba)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_READ,
- x, y, w, h);
- if(transfer) {
- pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
- pipe->tex_transfer_destroy(pipe, transfer);
- }
- }
-
- void
- put_tile_rgba(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, const float *rgba)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_WRITE,
- x, y, w, h);
- if(transfer) {
- pipe_put_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
- pipe->tex_transfer_destroy(pipe, transfer);
- }
- }
-
- %cstring_output_allocate_size(char **STRING, int *LENGTH, free(*$1));
- void
- get_tile_rgba8(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, char **STRING, int *LENGTH)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- float *rgba;
- unsigned char *rgba8;
- unsigned i, j, k;
-
- *LENGTH = 0;
- *STRING = NULL;
-
- if (!$self)
- return;
-
- *LENGTH = h*w*4;
- *STRING = (char *) malloc(*LENGTH);
- if(!*STRING)
- return;
-
- rgba = malloc(h*w*4*sizeof(float));
- if(!rgba)
- return;
-
- rgba8 = (unsigned char *) *STRING;
-
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_READ,
- x, y,
- w, h);
- if(transfer) {
- pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba);
- for(j = 0; j < h; ++j) {
- for(i = 0; i < w; ++i)
- for(k = 0; k <4; ++k)
- rgba8[j*w*4 + i*4 + k] = float_to_ubyte(rgba[j*w*4 + i*4 + k]);
- }
- pipe->tex_transfer_destroy(pipe, transfer);
- }
-
- free(rgba);
- }
-
- void get_tile_z(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, unsigned *z)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_READ,
- x, y, w, h);
- if(transfer) {
- pipe_get_tile_z(pipe, transfer, 0, 0, w, h, z);
- pipe->tex_transfer_destroy(pipe, transfer);
- }
- }
-
- void put_tile_z(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, const unsigned *z)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_WRITE,
- x, y, w, h);
- if(transfer) {
- pipe_put_tile_z(pipe, transfer, 0, 0, w, h, z);
- pipe->tex_transfer_destroy(pipe, transfer);
- }
- }
-
-/*
- void
- sample_rgba(float *rgba) {
- st_sample_surface($self, rgba);
- }
-*/
-
- unsigned compare_tile_rgba(struct st_context *ctx, unsigned x, unsigned y, unsigned w, unsigned h, const float *rgba, float tol = 0.0)
- {
- struct pipe_context *pipe = ctx->pipe;
- struct pipe_transfer *transfer;
- float *rgba2;
- const float *p1;
- const float *p2;
- unsigned i, j, n;
-
- rgba2 = MALLOC(h*w*4*sizeof(float));
- if(!rgba2)
- return ~0;
-
- transfer = pipe->get_tex_transfer(pipe,
- $self->texture,
- $self->face,
- $self->level,
- $self->zslice,
- PIPE_TRANSFER_READ,
- x, y, w, h);
- if(!transfer) {
- FREE(rgba2);
- return ~0;
- }
-
- pipe_get_tile_rgba(pipe, transfer, 0, 0, w, h, rgba2);
- pipe->tex_transfer_destroy(pipe, transfer);
-
- p1 = rgba;
- p2 = rgba2;
- n = 0;
- for(i = h*w; i; --i) {
- unsigned differs = 0;
- for(j = 4; j; --j) {
- float delta = *p2++ - *p1++;
- if (delta < -tol || delta > tol)
- differs = 1;
- }
- n += differs;
- }
-
- FREE(rgba2);
-
- return n;
- }
};
diff --git a/src/gallium/state_trackers/python/st_sample.c b/src/gallium/state_trackers/python/st_sample.c
index f9622533fbc..e2c1e060174 100644
--- a/src/gallium/state_trackers/python/st_sample.c
+++ b/src/gallium/state_trackers/python/st_sample.c
@@ -521,12 +521,13 @@ st_sample_pixel_block(enum pipe_format format,
}
}
-#if 0
+
void
-st_sample_surface(struct st_surface *surface, float *rgba)
+st_sample_surface(struct pipe_context *pipe,
+ struct st_surface *surface,
+ float *rgba)
{
struct pipe_texture *texture = surface->texture;
- struct pipe_screen *screen = texture->screen;
unsigned width = u_minify(texture->width0, surface->level);
unsigned height = u_minify(texture->height0, surface->level);
uint rgba_stride = width * 4;
@@ -534,18 +535,18 @@ st_sample_surface(struct st_surface *surface, float *rgba)
void *raw;
transfer = pipe->get_tex_transfer(pipe,
- surface->texture,
- surface->face,
- surface->level,
- surface->zslice,
- PIPE_TRANSFER_WRITE,
- 0, 0,
- width,
- height);
+ surface->texture,
+ surface->face,
+ surface->level,
+ surface->zslice,
+ PIPE_TRANSFER_WRITE,
+ 0, 0,
+ width,
+ height);
if (!transfer)
return;
- raw = screen->transfer_map(screen, transfer);
+ raw = pipe->transfer_map(pipe, transfer);
if (raw) {
enum pipe_format format = texture->format;
uint x, y;
@@ -567,9 +568,8 @@ st_sample_surface(struct st_surface *surface, float *rgba)
}
}
- screen->transfer_unmap(screen, transfer);
+ pipe->transfer_unmap(pipe, transfer);
}
- screen->tex_transfer_destroy(transfer);
+ pipe->tex_transfer_destroy(pipe, transfer);
}
-#endif
diff --git a/src/gallium/state_trackers/python/st_sample.h b/src/gallium/state_trackers/python/st_sample.h
index 888114d3021..6fb8417add8 100644
--- a/src/gallium/state_trackers/python/st_sample.h
+++ b/src/gallium/state_trackers/python/st_sample.h
@@ -32,6 +32,9 @@
#include "pipe/p_format.h"
+struct pipe_context;
+struct st_surface;
+
void
st_sample_pixel_block(enum pipe_format format,
@@ -40,7 +43,9 @@ st_sample_pixel_block(enum pipe_format format,
unsigned w, unsigned h);
void
-st_sample_surface(struct st_surface *surface, float *rgba);
+st_sample_surface(struct pipe_context *pipe,
+ struct st_surface *surface,
+ float *rgba);
#endif /* ST_SAMPLE_H_ */
diff --git a/src/gallium/targets/dri-swrast/swrast_drm_api.c b/src/gallium/targets/dri-swrast/swrast_drm_api.c
index 1f24d7650d7..63b935bb07b 100644
--- a/src/gallium/targets/dri-swrast/swrast_drm_api.c
+++ b/src/gallium/targets/dri-swrast/swrast_drm_api.c
@@ -32,15 +32,7 @@
#include "state_tracker/sw_winsys.h"
#include "dri_sw_winsys.h"
-/* Copied from targets/libgl-xlib.
- *
- * TODO:
- * This function should be put in targets/common or winsys/sw/common and shared
- * with targets/libgl-xlib and winsys/sw/drm.
- *
- * For targets/common, you get layering violations unless all of drm_api's are
- * moved under targets.
- */
+/* Copied from targets/libgl-xlib */
#ifdef GALLIUM_SOFTPIPE
#include "softpipe/sp_public.h"
@@ -98,19 +90,24 @@ swrast_drm_create_screen(struct drm_api *api,
{
struct sw_winsys *winsys = NULL;
struct pipe_screen *screen = NULL;
+ struct drisw_create_screen_arg *drisw;
(void) drmFD;
if (arg != NULL) {
switch(arg->mode) {
case DRM_CREATE_DRISW:
+ drisw = (struct drisw_create_screen_arg *)arg;
break;
default:
return NULL;
}
}
+ else {
+ return NULL;
+ }
- winsys = dri_create_sw_winsys();
+ winsys = dri_create_sw_winsys(drisw->lf);
if (winsys == NULL)
return NULL;
diff --git a/src/gallium/targets/libgl-xlib/xlib.c b/src/gallium/targets/libgl-xlib/xlib.c
index 4a8366280d8..48e5bdff429 100644
--- a/src/gallium/targets/libgl-xlib/xlib.c
+++ b/src/gallium/targets/libgl-xlib/xlib.c
@@ -55,6 +55,14 @@ PUBLIC const struct st_module st_module_OpenGL = {
* GALLIUM_CELL, etc. Scons already eliminates those #defines, so
* things that are painful for it now are likely to be painful for
* other build systems in the future.
+ *
+ * Copies (full or partial):
+ * targets/libgl-xlib
+ * targets/graw-xlib
+ * targets/dri-swrast
+ * winsys/sw/drm
+ * drivers/sw
+ *
*/
#ifdef GALLIUM_SOFTPIPE
diff --git a/src/gallium/winsys/sw/dri/dri_sw_winsys.c b/src/gallium/winsys/sw/dri/dri_sw_winsys.c
index 1c1e5612d28..870c6afc124 100644
--- a/src/gallium/winsys/sw/dri/dri_sw_winsys.c
+++ b/src/gallium/winsys/sw/dri/dri_sw_winsys.c
@@ -37,128 +37,153 @@
#include "dri_sw_winsys.h"
-struct xm_displaytarget
+struct dri_sw_displaytarget
{
+ enum pipe_format format;
+ unsigned width;
+ unsigned height;
+ unsigned stride;
+
void *data;
void *mapped;
};
+struct dri_sw_winsys
+{
+ struct sw_winsys base;
+
+ struct drisw_loader_funcs *lf;
+};
+
+static INLINE struct dri_sw_displaytarget *
+dri_sw_displaytarget( struct sw_displaytarget *dt )
+{
+ return (struct dri_sw_displaytarget *)dt;
+}
-/** Cast wrapper */
-static INLINE struct xm_displaytarget *
-xm_displaytarget( struct sw_displaytarget *dt )
+static INLINE struct dri_sw_winsys *
+dri_sw_winsys( struct sw_winsys *ws )
{
- return (struct xm_displaytarget *)dt;
+ return (struct dri_sw_winsys *)ws;
}
-/* pipe_screen::is_format_supported */
static boolean
-xm_is_displaytarget_format_supported( struct sw_winsys *ws,
- unsigned tex_usage,
- enum pipe_format format )
+dri_sw_is_displaytarget_format_supported( struct sw_winsys *ws,
+ unsigned tex_usage,
+ enum pipe_format format )
{
/* TODO: check visuals or other sensible thing here */
return TRUE;
}
-/* pipe_screen::texture_create DISPLAY_TARGET / SCANOUT / SHARED */
static struct sw_displaytarget *
-xm_displaytarget_create(struct sw_winsys *winsys,
- unsigned tex_usage,
- enum pipe_format format,
- unsigned width, unsigned height,
- unsigned alignment,
- unsigned *stride)
+dri_sw_displaytarget_create(struct sw_winsys *winsys,
+ unsigned tex_usage,
+ enum pipe_format format,
+ unsigned width, unsigned height,
+ unsigned alignment,
+ unsigned *stride)
{
- struct xm_displaytarget *xm_dt;
- unsigned nblocksy, size, xm_stride, format_stride;
+ struct dri_sw_displaytarget *dri_sw_dt;
+ unsigned nblocksy, size, format_stride;
- xm_dt = CALLOC_STRUCT(xm_displaytarget);
- if(!xm_dt)
- goto no_xm_dt;
+ dri_sw_dt = CALLOC_STRUCT(dri_sw_displaytarget);
+ if(!dri_sw_dt)
+ goto no_dt;
+
+ dri_sw_dt->format = format;
+ dri_sw_dt->width = width;
+ dri_sw_dt->height = height;
format_stride = util_format_get_stride(format, width);
- xm_stride = align(format_stride, alignment);
+ dri_sw_dt->stride = align(format_stride, alignment);
nblocksy = util_format_get_nblocksy(format, height);
- size = xm_stride * nblocksy;
+ size = dri_sw_dt->stride * nblocksy;
- xm_dt->data = align_malloc(size, alignment);
- if(!xm_dt->data)
+ dri_sw_dt->data = align_malloc(size, alignment);
+ if(!dri_sw_dt->data)
goto no_data;
- *stride = xm_stride;
- return (struct sw_displaytarget *)xm_dt;
+ *stride = dri_sw_dt->stride;
+ return (struct sw_displaytarget *)dri_sw_dt;
no_data:
- FREE(xm_dt);
-no_xm_dt:
+ FREE(dri_sw_dt);
+no_dt:
return NULL;
}
-/* pipe_screen::texture_destroy */
static void
-xm_displaytarget_destroy(struct sw_winsys *ws,
- struct sw_displaytarget *dt)
+dri_sw_displaytarget_destroy(struct sw_winsys *ws,
+ struct sw_displaytarget *dt)
{
- struct xm_displaytarget *xm_dt = xm_displaytarget(dt);
+ struct dri_sw_displaytarget *dri_sw_dt = dri_sw_displaytarget(dt);
- if (xm_dt->data) {
- FREE(xm_dt->data);
+ if (dri_sw_dt->data) {
+ FREE(dri_sw_dt->data);
}
- FREE(xm_dt);
+ FREE(dri_sw_dt);
}
-/* pipe_context::transfer_map */
static void *
-xm_displaytarget_map(struct sw_winsys *ws,
- struct sw_displaytarget *dt,
- unsigned flags)
+dri_sw_displaytarget_map(struct sw_winsys *ws,
+ struct sw_displaytarget *dt,
+ unsigned flags)
{
- struct xm_displaytarget *xm_dt = xm_displaytarget(dt);
- xm_dt->mapped = xm_dt->data;
- return xm_dt->mapped;
+ struct dri_sw_displaytarget *dri_sw_dt = dri_sw_displaytarget(dt);
+ dri_sw_dt->mapped = dri_sw_dt->data;
+ return dri_sw_dt->mapped;
}
-/* pipe_context::transfer_unmap */
static void
-xm_displaytarget_unmap(struct sw_winsys *ws,
- struct sw_displaytarget *dt)
+dri_sw_displaytarget_unmap(struct sw_winsys *ws,
+ struct sw_displaytarget *dt)
{
- struct xm_displaytarget *xm_dt = xm_displaytarget(dt);
- xm_dt->mapped = NULL;
+ struct dri_sw_displaytarget *dri_sw_dt = dri_sw_displaytarget(dt);
+ dri_sw_dt->mapped = NULL;
}
-/* pipe_screen::texture_from_handle */
static struct sw_displaytarget *
-xm_displaytarget_from_handle(struct sw_winsys *winsys,
- const struct pipe_texture *templ,
- struct winsys_handle *whandle,
- unsigned *stride)
+dri_sw_displaytarget_from_handle(struct sw_winsys *winsys,
+ const struct pipe_texture *templ,
+ struct winsys_handle *whandle,
+ unsigned *stride)
{
assert(0);
return NULL;
}
-/* pipe_screen::texture_get_handle */
static boolean
-xm_displaytarget_get_handle(struct sw_winsys *winsys,
- struct sw_displaytarget *dt,
- struct winsys_handle *whandle)
+dri_sw_displaytarget_get_handle(struct sw_winsys *winsys,
+ struct sw_displaytarget *dt,
+ struct winsys_handle *whandle)
{
assert(0);
return FALSE;
}
-/* pipe_screen::flush_frontbuffer */
static void
-xm_displaytarget_display(struct sw_winsys *ws,
- struct sw_displaytarget *dt,
- void *context_private)
+dri_sw_displaytarget_display(struct sw_winsys *ws,
+ struct sw_displaytarget *dt,
+ void *context_private)
{
- assert(0);
+ struct dri_sw_winsys *dri_sw_ws = dri_sw_winsys(ws);
+ struct dri_sw_displaytarget *dri_sw_dt = dri_sw_displaytarget(dt);
+ struct dri_drawable *dri_drawable = (struct dri_drawable *)context_private;
+ unsigned width, height;
+
+ /* Set the width to 'stride / cpp'.
+ *
+ * PutImage correctly clips to the width of the dst drawable.
+ */
+ width = dri_sw_dt->stride / util_format_get_blocksize(dri_sw_dt->format);
+
+ height = dri_sw_dt->height;
+
+ dri_sw_ws->lf->put_image(dri_drawable, dri_sw_dt->data, width, height);
}
@@ -169,31 +194,32 @@ dri_destroy_sw_winsys(struct sw_winsys *winsys)
}
struct sw_winsys *
-dri_create_sw_winsys(void)
+dri_create_sw_winsys(struct drisw_loader_funcs *lf)
{
- struct sw_winsys *ws;
+ struct dri_sw_winsys *ws;
- ws = CALLOC_STRUCT(sw_winsys);
+ ws = CALLOC_STRUCT(dri_sw_winsys);
if (!ws)
return NULL;
- ws->destroy = dri_destroy_sw_winsys;
+ ws->lf = lf;
+ ws->base.destroy = dri_destroy_sw_winsys;
- ws->is_displaytarget_format_supported = xm_is_displaytarget_format_supported;
+ ws->base.is_displaytarget_format_supported = dri_sw_is_displaytarget_format_supported;
/* screen texture functions */
- ws->displaytarget_create = xm_displaytarget_create;
- ws->displaytarget_destroy = xm_displaytarget_destroy;
- ws->displaytarget_from_handle = xm_displaytarget_from_handle;
- ws->displaytarget_get_handle = xm_displaytarget_get_handle;
+ ws->base.displaytarget_create = dri_sw_displaytarget_create;
+ ws->base.displaytarget_destroy = dri_sw_displaytarget_destroy;
+ ws->base.displaytarget_from_handle = dri_sw_displaytarget_from_handle;
+ ws->base.displaytarget_get_handle = dri_sw_displaytarget_get_handle;
/* texture functions */
- ws->displaytarget_map = xm_displaytarget_map;
- ws->displaytarget_unmap = xm_displaytarget_unmap;
+ ws->base.displaytarget_map = dri_sw_displaytarget_map;
+ ws->base.displaytarget_unmap = dri_sw_displaytarget_unmap;
- ws->displaytarget_display = xm_displaytarget_display;
+ ws->base.displaytarget_display = dri_sw_displaytarget_display;
- return ws;
+ return &ws->base;
}
/* vim: set sw=3 ts=8 sts=3 expandtab: */
diff --git a/src/gallium/winsys/sw/dri/dri_sw_winsys.h b/src/gallium/winsys/sw/dri/dri_sw_winsys.h
index c2382a68d78..329ac06a05b 100644
--- a/src/gallium/winsys/sw/dri/dri_sw_winsys.h
+++ b/src/gallium/winsys/sw/dri/dri_sw_winsys.h
@@ -29,8 +29,10 @@
#ifndef DRI_SW_WINSYS
#define DRI_SW_WINSYS
+#include "state_tracker/drisw_api.h"
+
struct sw_winsys;
-struct sw_winsys *dri_create_sw_winsys(void);
+struct sw_winsys *dri_create_sw_winsys(struct drisw_loader_funcs *lf);
#endif