OpenSlide segmentation faults in Windows
Agelos Pappas
agelos at smartcode.gr
Fri Nov 16 17:05:16 EST 2012
Hi,
as I've reported in another message OpenSlide crashes reporting
segmentation faults when running in a windows multi-threaded
application. The problem occurs with any slide format, but is easier to
reproduce with MIRAX files. I have been able to reproduce the problem in
both x86 and x64 versions of OpenSlide by writing an application that
spawns N threads which read AxA tiles starting from the top level and
walking to the bottom. The application doesn't always crash and when it
does, it is not at the same point.
The following (C++) function, if spawned in multiple threads (4 seem to
be enough for me) will make the application crash reporting access
violation:
DWORD WINAPI SlideWalk(LPVOID lpParam)
{
const int TileSize = 256;
__int64 w, h;
int *osr = openslide_open(PATH_TO_SLIDE);
int numLevels = openslide_get_level_count(osr);
for (int i = numLevels - 1; i >= 0; i--)
{
openslide_get_level_dimensions(osr, i, &w, &h);
double d = openslide_get_level_downsample(osr, i);
for (int y = 0; y < h; y += TileSize)
{
for (int x = 0; x < w; x += TileSize)
{
unsigned int *buffer = new unsigned int[TileSize *
TileSize];
openslide_read_region(osr, buffer, floorl(x * d),
floorl(y * d), i, TileSize, TileSize);
delete []buffer;
}
}
}
openslide_close(osr);
return 0;
}
The above is just a quick test compiled under windows. I ran it using
gdb in Cygwin and I got errors like these:
Program received signal SIGSEGV, Segmentation fault.
[Switching to Thread 7396.0x1e00]
sse2_composite_src_x888_8888 (imp=0x563c08, info=0xbbe22c) at
pixman-sse2.c:2860
in pixman-sse2.c
In all my tests the segmentation fault happens in libpixman, but not
always at the same line.
I've written a similar program in Linux but it doesn't seem to crash,
even though valgrind reported some errors in libpixman too.
Can someone test the attached C program in Linux using a public MRXS
slide to see if they get any seg faults?
Regards
Pappas Agelos
-------------- next part --------------
#include <stdint.h>
#include <math.h>
#include <stdio.h>
#include <glib.h>
#include <openslide.h>
#define NTHREADS 4
#define TILE_SIZE 256
int thread_function(void *data)
{
printf("%x thread started\n", (uint32_t)g_thread_self());
int64_t x, y, w, h;
uint32_t *buffer;
openslide_t *osr = openslide_open((char *)data);
if (osr == NULL) {
printf("%s: Not a file that OpenSlide can recognize", (char *)data);
return -1;
}
int numLevels = openslide_get_level_count(osr);
for (int i = numLevels - 1; i >= 0; i--)
{
openslide_get_level_dimensions(osr, i, &w, &h);
double d = openslide_get_level_downsample(osr, i);
for (int y = 0; y < h; y += TILE_SIZE)
{
for (int x = 0; x < w; x += TILE_SIZE)
{
uint32_t *buffer = g_malloc(TILE_SIZE * TILE_SIZE * 4);
openslide_read_region(osr, buffer, llround (x * d), llround (y * d), i, TILE_SIZE, TILE_SIZE);
g_free(buffer);
}
}
}
openslide_close(osr);
printf("%x thread stopping\n", (uint32_t)g_thread_self());
return 0;
}
int main (int argc, char *argv[])
{
int i;
GThread *thread[NTHREADS];
char *thread_names[NTHREADS];
if (argc != 2) {
printf("Slide file not supplied\n");
return -1;
}
for (i=0; i<NTHREADS; i++) {
thread_names[i] = g_malloc(256);
sprintf(thread_names[i], "Thread %d", i);
thread[i] = g_thread_new(thread_names[i], (GThreadFunc)thread_function, argv[1]);
}
for(i=0; i<NTHREADS; i++) {
g_thread_join(thread[i]);
g_free(thread_names[i]);
}
return 0;
}
More information about the openslide-users
mailing list