Sort directory entries while scanning them from disk; prevents Heisenbugs
due to file ordering in a directory. reviewed by: plam
This commit is contained in:
parent
a7683cafe1
commit
37e3f33c7e
|
@ -1,3 +1,11 @@
|
||||||
|
2006-03-08 Egmont Koblinger <egmont@uhulinux.hu>
|
||||||
|
reviewed by: plam
|
||||||
|
|
||||||
|
* src/fcdir.c (FcDirScanConfig):
|
||||||
|
|
||||||
|
Sort directory entries while scanning them from disk;
|
||||||
|
prevents Heisenbugs due to file ordering in a directory.
|
||||||
|
|
||||||
2005-12-13 Carl Worth <cworth@cworth.org>
|
2005-12-13 Carl Worth <cworth@cworth.org>
|
||||||
reviewed by: keithp
|
reviewed by: keithp
|
||||||
|
|
||||||
|
|
45
src/fcdir.c
45
src/fcdir.c
|
@ -168,6 +168,16 @@ FcFileScan (FcFontSet *set,
|
||||||
return FcFileScanConfig (set, dirs, cache, blanks, file, force, 0);
|
return FcFileScanConfig (set, dirs, cache, blanks, file, force, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Strcmp helper that takes pointers to pointers, copied from qsort(3) manpage
|
||||||
|
*/
|
||||||
|
|
||||||
|
static int
|
||||||
|
cmpstringp(const void *p1, const void *p2)
|
||||||
|
{
|
||||||
|
return strcmp(* (char **) p1, * (char **) p2);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Scan 'dir', adding font files to 'set' and
|
* Scan 'dir', adding font files to 'set' and
|
||||||
* subdirectories to 'dirs'
|
* subdirectories to 'dirs'
|
||||||
|
@ -184,9 +194,12 @@ FcDirScanConfig (FcFontSet *set,
|
||||||
{
|
{
|
||||||
DIR *d;
|
DIR *d;
|
||||||
struct dirent *e;
|
struct dirent *e;
|
||||||
|
FcChar8 **dirlist;
|
||||||
|
int dirlistlen, dirlistalloc;
|
||||||
FcChar8 *file;
|
FcChar8 *file;
|
||||||
FcChar8 *base;
|
FcChar8 *base;
|
||||||
FcBool ret = FcTrue;
|
FcBool ret = FcTrue;
|
||||||
|
int i;
|
||||||
|
|
||||||
if (config && !FcConfigAcceptFilename (config, dir))
|
if (config && !FcConfigAcceptFilename (config, dir))
|
||||||
return FcTrue;
|
return FcTrue;
|
||||||
|
@ -232,14 +245,40 @@ FcDirScanConfig (FcFontSet *set,
|
||||||
return FcTrue;
|
return FcTrue;
|
||||||
return FcFalse;
|
return FcFalse;
|
||||||
}
|
}
|
||||||
while (ret && (e = readdir (d)))
|
dirlistlen = 0;
|
||||||
|
dirlistalloc = 8;
|
||||||
|
dirlist = malloc(dirlistalloc * sizeof(FcChar8 *));
|
||||||
|
if (!dirlist)
|
||||||
|
return FcFalse;
|
||||||
|
while ((e = readdir (d)))
|
||||||
{
|
{
|
||||||
if (e->d_name[0] != '.' && strlen (e->d_name) < FC_MAX_FILE_LEN)
|
if (e->d_name[0] != '.' && strlen (e->d_name) < FC_MAX_FILE_LEN)
|
||||||
{
|
{
|
||||||
strcpy ((char *) base, (char *) e->d_name);
|
if (dirlistlen == dirlistalloc)
|
||||||
ret = FcFileScanConfig (set, dirs, cache, blanks, file, force, config);
|
{
|
||||||
|
dirlistalloc *= 2;
|
||||||
|
dirlist = realloc(dirlist, dirlistalloc * sizeof(FcChar8 *));
|
||||||
|
if (!dirlist)
|
||||||
|
return FcFalse;
|
||||||
|
}
|
||||||
|
dirlist[dirlistlen] = malloc(strlen (e->d_name) + 1);
|
||||||
|
if (!dirlist[dirlistlen])
|
||||||
|
return FcFalse;
|
||||||
|
strcpy(dirlist[dirlistlen], e->d_name);
|
||||||
|
dirlistlen++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
qsort(dirlist, dirlistlen, sizeof(FcChar8 *), cmpstringp);
|
||||||
|
i = 0;
|
||||||
|
while (ret && i < dirlistlen)
|
||||||
|
{
|
||||||
|
strcpy ((char *) base, (char *) dirlist[i]);
|
||||||
|
ret = FcFileScanConfig (set, dirs, cache, blanks, file, force, config);
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
for (i = 0; i < dirlistlen; i++)
|
||||||
|
free(dirlist[i]);
|
||||||
|
free (dirlist);
|
||||||
free (file);
|
free (file);
|
||||||
closedir (d);
|
closedir (d);
|
||||||
/*
|
/*
|
||||||
|
|
Loading…
Reference in New Issue