Read latest cache in paths
Right now fontconfig uses a cache found first in a path and cachedirs are the order of the system-wide path and then the user path. this is due to avoid writing caches into the user path when running as root. However, changing caches by certain config only, e.g. using <match target="scan"> may not take effect by this behavior, because it may be stored into the user path. Thus, needing to find the latest cache out from paths. Fixes https://gitlab.freedesktop.org/fontconfig/fontconfig/issues/182
This commit is contained in:
parent
cd51cb241a
commit
c9862b6ea7
|
@ -338,7 +338,7 @@ FcDirCacheOpenFile (const FcChar8 *cache_file, struct stat *file_stat)
|
||||||
static FcBool
|
static FcBool
|
||||||
FcDirCacheProcess (FcConfig *config, const FcChar8 *dir,
|
FcDirCacheProcess (FcConfig *config, const FcChar8 *dir,
|
||||||
FcBool (*callback) (FcConfig *config, int fd, struct stat *fd_stat,
|
FcBool (*callback) (FcConfig *config, int fd, struct stat *fd_stat,
|
||||||
struct stat *dir_stat, void *closure),
|
struct stat *dir_stat, struct timeval *cache_mtime, void *closure),
|
||||||
void *closure, FcChar8 **cache_file_ret)
|
void *closure, FcChar8 **cache_file_ret)
|
||||||
{
|
{
|
||||||
int fd = -1;
|
int fd = -1;
|
||||||
|
@ -348,6 +348,7 @@ FcDirCacheProcess (FcConfig *config, const FcChar8 *dir,
|
||||||
struct stat file_stat, dir_stat;
|
struct stat file_stat, dir_stat;
|
||||||
FcBool ret = FcFalse;
|
FcBool ret = FcFalse;
|
||||||
const FcChar8 *sysroot = FcConfigGetSysRoot (config);
|
const FcChar8 *sysroot = FcConfigGetSysRoot (config);
|
||||||
|
struct timeval latest_mtime = (struct timeval){ 0 };
|
||||||
|
|
||||||
if (sysroot)
|
if (sysroot)
|
||||||
d = FcStrBuildFilename (sysroot, dir, NULL);
|
d = FcStrBuildFilename (sysroot, dir, NULL);
|
||||||
|
@ -383,15 +384,18 @@ FcDirCacheProcess (FcConfig *config, const FcChar8 *dir,
|
||||||
#endif
|
#endif
|
||||||
fd = FcDirCacheOpenFile (cache_hashed, &file_stat);
|
fd = FcDirCacheOpenFile (cache_hashed, &file_stat);
|
||||||
if (fd >= 0) {
|
if (fd >= 0) {
|
||||||
ret = (*callback) (config, fd, &file_stat, &dir_stat, closure);
|
ret = (*callback) (config, fd, &file_stat, &dir_stat, &latest_mtime, closure);
|
||||||
close (fd);
|
close (fd);
|
||||||
if (ret)
|
if (ret)
|
||||||
{
|
{
|
||||||
if (cache_file_ret)
|
if (cache_file_ret)
|
||||||
|
{
|
||||||
|
if (*cache_file_ret)
|
||||||
|
FcStrFree (*cache_file_ret);
|
||||||
*cache_file_ret = cache_hashed;
|
*cache_file_ret = cache_hashed;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
FcStrFree (cache_hashed);
|
FcStrFree (cache_hashed);
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#ifndef _WIN32
|
#ifndef _WIN32
|
||||||
|
@ -414,7 +418,8 @@ FcDirCacheProcess (FcConfig *config, const FcChar8 *dir,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
FcStrFree (cache_hashed);
|
else
|
||||||
|
FcStrFree (cache_hashed);
|
||||||
}
|
}
|
||||||
FcStrListDone (list);
|
FcStrListDone (list);
|
||||||
|
|
||||||
|
@ -998,12 +1003,31 @@ FcDirCacheUnload (FcCache *cache)
|
||||||
}
|
}
|
||||||
|
|
||||||
static FcBool
|
static FcBool
|
||||||
FcDirCacheMapHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure)
|
FcDirCacheMapHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, struct timeval *latest_cache_mtime, void *closure)
|
||||||
{
|
{
|
||||||
FcCache *cache = FcDirCacheMapFd (config, fd, fd_stat, dir_stat);
|
FcCache *cache = FcDirCacheMapFd (config, fd, fd_stat, dir_stat);
|
||||||
|
struct timeval cache_mtime;
|
||||||
|
|
||||||
if (!cache)
|
if (!cache)
|
||||||
return FcFalse;
|
return FcFalse;
|
||||||
|
cache_mtime.tv_sec = fd_stat->st_mtime;
|
||||||
|
#ifdef HAVE_STRUCT_STAT_ST_MTIM
|
||||||
|
cache_mtime.tv_usec = fd_stat->st_mtim.tv_nsec / 1000;
|
||||||
|
#else
|
||||||
|
cache_mtime.tv_usec = 0;
|
||||||
|
#endif
|
||||||
|
if (timercmp (latest_cache_mtime, &cache_mtime, <))
|
||||||
|
{
|
||||||
|
if (*((FcCache **) closure))
|
||||||
|
FcDirCacheUnload (*((FcCache **) closure));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
FcDirCacheUnload (cache);
|
||||||
|
return FcFalse;
|
||||||
|
}
|
||||||
|
latest_cache_mtime->tv_sec = cache_mtime.tv_sec;
|
||||||
|
latest_cache_mtime->tv_usec = cache_mtime.tv_usec;
|
||||||
*((FcCache **) closure) = cache;
|
*((FcCache **) closure) = cache;
|
||||||
return FcTrue;
|
return FcTrue;
|
||||||
}
|
}
|
||||||
|
@ -1093,7 +1117,7 @@ FcDirChecksumNano (struct stat *statb)
|
||||||
* the magic number and the size field
|
* the magic number and the size field
|
||||||
*/
|
*/
|
||||||
static FcBool
|
static FcBool
|
||||||
FcDirCacheValidateHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure FC_UNUSED)
|
FcDirCacheValidateHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, struct timeval *latest_cache_mtime, void *closure FC_UNUSED)
|
||||||
{
|
{
|
||||||
FcBool ret = FcTrue;
|
FcBool ret = FcTrue;
|
||||||
FcCache c;
|
FcCache c;
|
||||||
|
|
|
@ -340,6 +340,72 @@ fi
|
||||||
|
|
||||||
rm -rf $MyPWD/sysroot
|
rm -rf $MyPWD/sysroot
|
||||||
|
|
||||||
|
dotest "read newer caches when multiple places are allowed to store"
|
||||||
|
prep
|
||||||
|
cp $FONT1 $FONT2 $FONTDIR
|
||||||
|
if [ -n ${SOURCE_DATE_EPOCH:-} ] && [ ${#SOURCE_DATE_EPOCH} -gt 0 ]; then
|
||||||
|
touch -m -t "`date -d \"@${SOURCE_DATE_EPOCH}\" +%y%m%d%H%M.%S`" $FONTDIR
|
||||||
|
fi
|
||||||
|
MYCACHEBASEDIR=`mktemp -d /tmp/fontconfig.XXXXXXXX`
|
||||||
|
MYCACHEDIR=$MYCACHEBASEDIR/cache.dir
|
||||||
|
MYOWNCACHEDIR=$MYCACHEBASEDIR/owncache.dir
|
||||||
|
MYCONFIG=`mktemp /tmp/fontconfig.XXXXXXXX`
|
||||||
|
|
||||||
|
mkdir -p $MYCACHEDIR
|
||||||
|
mkdir -p $MYOWNCACHEDIR
|
||||||
|
|
||||||
|
sed "s!@FONTDIR@!$FONTDIR!
|
||||||
|
s!@REMAPDIR@!!
|
||||||
|
s!@CACHEDIR@!$MYCACHEDIR!" < $TESTDIR/fonts.conf.in > my-fonts.conf
|
||||||
|
|
||||||
|
FONTCONFIG_FILE=$MyPWD/my-fonts.conf $FCCACHE $FONTDIR
|
||||||
|
|
||||||
|
sleep 1
|
||||||
|
cat<<EOF>$MYCONFIG
|
||||||
|
<fontconfig>
|
||||||
|
<match target="scan">
|
||||||
|
<test name="file"><string>$FONTDIR/4x6.pcf</string></test>
|
||||||
|
<edit name="pixelsize"><int>8</int></edit>
|
||||||
|
</match>
|
||||||
|
</fontconfig>
|
||||||
|
EOF
|
||||||
|
sed "s!@FONTDIR@!$FONTDIR!
|
||||||
|
s!@REMAPDIR@!<include ignore_missing=\"yes\">$MYCONFIG</include>!
|
||||||
|
s!@CACHEDIR@!$MYOWNCACHEDIR!" < $TESTDIR/fonts.conf.in > my-fonts.conf
|
||||||
|
|
||||||
|
if [ -n ${SOURCE_DATE_EPOCH:-} ]; then
|
||||||
|
old_epoch=${SOURCE_DATE_EPOCH}
|
||||||
|
SOURCE_DATE_EPOCH=`expr $SOURCE_DATE_EPOCH + 1`
|
||||||
|
fi
|
||||||
|
FONTCONFIG_FILE=$MyPWD/my-fonts.conf $FCCACHE -f $FONTDIR
|
||||||
|
if [ -n ${SOURCE_DATE_EPOCH:-} ]; then
|
||||||
|
SOURCE_DATE_EPOCH=${old_epoch}
|
||||||
|
fi
|
||||||
|
|
||||||
|
sed "s!@FONTDIR@!$FONTDIR!
|
||||||
|
s!@REMAPDIR@!<include ignore_missing=\"yes\">$MYCONFIG</include>!
|
||||||
|
s!@CACHEDIR@!$MYCACHEDIR</cachedir><cachedir>$MYOWNCACHEDIR!" < $TESTDIR/fonts.conf.in > my-fonts.conf
|
||||||
|
|
||||||
|
FONTCONFIG_FILE=$MyPWD/my-fonts.conf $FCLIST - family pixelsize | sort > my-out
|
||||||
|
echo "=" >> my-out
|
||||||
|
FONTCONFIG_FILE=$MyPWD/my-fonts.conf $FCLIST - family pixelsize | sort >> my-out
|
||||||
|
echo "=" >> my-out
|
||||||
|
FONTCONFIG_FILE=$MyPWD/my-fonts.conf $FCLIST - family pixelsize | sort >> my-out
|
||||||
|
tr -d '\015' <my-out >my-out.tmp; mv my-out.tmp my-out
|
||||||
|
sed -e 's/pixelsize=6/pixelsize=8/g' $BUILDTESTDIR/$EXPECTED > my-out.expected
|
||||||
|
|
||||||
|
if cmp my-out my-out.expected > /dev/null ; then : ; else
|
||||||
|
echo "*** Test failed: $TEST"
|
||||||
|
echo "*** output is in 'my-out', expected output in 'my-out.expected'"
|
||||||
|
echo "Actual Result"
|
||||||
|
cat my-out
|
||||||
|
echo "Expected Result"
|
||||||
|
cat my-out.expected
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
rm -rf $MYCACHEBASEDIR $MYCONFIG my-fonts.conf my-out my-out.expected
|
||||||
|
|
||||||
fi # if [ "x$EXEEXT" = "x" ]
|
fi # if [ "x$EXEEXT" = "x" ]
|
||||||
|
|
||||||
rm -rf $FONTDIR $CACHEFILE $CACHEDIR $BASEDIR $FONTCONFIG_FILE out
|
rm -rf $FONTDIR $CACHEFILE $CACHEDIR $BASEDIR $FONTCONFIG_FILE out
|
||||||
|
|
Loading…
Reference in New Issue