Hi Brian,
I created a smallest possible test case to reproduce the segfault, as
attached. Please see file header on how I compile it. vs and fs both
needs to be checked to avoid the segfault.
If I replace the screen creation part to use swrast or r600, they both
work fine.
Thanks.
Vic
On 03/06/2012 07:44 AM, Brian Paul wrote:
On 03/03/2012 04:17 AM, Vic Lee wrote:
This patch fix segfault if an application clears a render target
before setting any vertex or fragment shaders, which is a legal
situation.
I can't seem to trigger this problem with a test program. Can you post a
test case?
The first part of your patch looks OK but I don't see why the second
part is needed. We already check svga->curr.fs before dereffing the
pointer.
-Brian
/*
put this file under src/gallium and compile with:
gcc -Wall -g -O0 -o test -DDEBUG -I/usr/include/libdrm -I./include -I./auxiliary -I./winsys -I./drivers test.c \
./winsys/svga/drm/libsvgadrm.a ./winsys/sw/wrapper/libwsw.a ./drivers/svga/libsvga.a ./auxiliary/libgallium.a \
`llvm-config --libs` -lstdc++ -lpthread -ldrm -lm -ldl
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <xf86drm.h>
#include "pipe/p_compiler.h"
#include "pipe/p_screen.h"
#include "pipe/p_context.h"
#include "pipe/p_state.h"
#include "util/u_debug.h"
#include "target-helpers/inline_debug_helper.h"
#include "svga/drm/svga_drm_public.h"
#include "svga/svga_public.h"
#define SVGA_PCI_BUSID "PCI:0000:00:0f.0"
int main(int argc, char *argv[])
{
struct pipe_screen *screen;
struct pipe_context *pipe;
struct pipe_framebuffer_state framebuffer;
int fd;
int newlyopened;
struct svga_winsys_screen *sws;
struct pipe_resource resource;
struct pipe_resource *rendertarget;
struct pipe_surface surface;
struct pipe_rasterizer_state rasterizer;
void *rs;
float color[] = { 1.0f, 0.4f, 0.4f, 1.0f };
fd = drmOpenOnce(NULL, SVGA_PCI_BUSID, &newlyopened);
if (fd < 0)
{
printf("drmOpenOnce failed\n");
return 1;
}
sws = svga_drm_winsys_screen_create(fd);
if (!sws)
{
printf("svga_drm_winsys_screen_create failed\n");
return 1;
}
screen = svga_screen_create(sws);
if (!screen)
{
printf("svga_screen_create failed\n");
return 1;
}
pipe = screen->context_create(screen, NULL);
if (!pipe)
{
printf("context_create failed\n");
return 1;
}
memset(&resource, 0, sizeof(resource));
resource.target = PIPE_TEXTURE_2D;
resource.format = PIPE_FORMAT_B8G8R8A8_UNORM;
resource.bind = PIPE_BIND_RENDER_TARGET;
resource.width0 = 300;
resource.height0 = 300;
resource.depth0 = 1;
resource.array_size = 1;
resource.last_level = 0;
resource.nr_samples = 1;
rendertarget = (struct pipe_resource *) screen->resource_create(screen, &resource);
memset(&surface, 0, sizeof(surface));
surface.format = rendertarget->format;
surface.usage = PIPE_BIND_RENDER_TARGET;
memset(&framebuffer, 0, sizeof(framebuffer));
framebuffer.width = rendertarget->width0;
framebuffer.height = rendertarget->height0;
framebuffer.cbufs[0] = pipe->create_surface(pipe, rendertarget, &surface);
framebuffer.nr_cbufs = 1;
pipe->set_framebuffer_state(pipe, &framebuffer);
/* the driver crash if rasterizer state is not set before we call clear! */
memset(&rasterizer, 0, sizeof(rasterizer));
rs = pipe->create_rasterizer_state(pipe, &rasterizer);
pipe->bind_rasterizer_state(pipe, rs);
pipe->clear(pipe, PIPE_CLEAR_COLOR, (const union pipe_color_union *)color, 0, 1);
pipe->flush(pipe, NULL);
debug_dump_surface_bmp(pipe, "result.bmp", framebuffer.cbufs[0]);
return 0;
}
_______________________________________________
mesa-dev mailing list
mesa-dev@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/mesa-dev