Fix memory corruption!
In FcStrListCreate() we were increasing reference count of set, however, if set had a const reference (which is the case for list of languages), and with multiple threads, the const ref (-1) was getting up to 1 and then a decrease was destroying the set. Ouch. Here's the valgrind error, which took me quite a few hours of running to catch: ==4464== Invalid read of size 4 ==4464== at 0x4E58FF3: FcStrListNext (fcstr.c:1256) ==4464== by 0x4E3F11D: FcConfigSubstituteWithPat (fccfg.c:1508) ==4464== by 0x4E3F8F4: FcConfigSubstitute (fccfg.c:1729) ==4464== by 0x4009FA: test_match (simple-pthread-test.c:53) ==4464== by 0x400A6E: run_test_in_thread (simple-pthread-test.c:68) ==4464== by 0x507EE99: start_thread (pthread_create.c:308) ==4464== Address 0x6bc0b44 is 4 bytes inside a block of size 24 free'd ==4464== at 0x4C2A82E: free (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) ==4464== by 0x4E58F84: FcStrSetDestroy (fcstr.c:1236) ==4464== by 0x4E3F0C6: FcConfigSubstituteWithPat (fccfg.c:1507) ==4464== by 0x4E3F8F4: FcConfigSubstitute (fccfg.c:1729) ==4464== by 0x4009FA: test_match (simple-pthread-test.c:53) ==4464== by 0x400A6E: run_test_in_thread (simple-pthread-test.c:68) ==4464== by 0x507EE99: start_thread (pthread_create.c:308) Thread test is running happily now. Will add the test in a moment.
This commit is contained in:
parent
4e6c7d0827
commit
dc21ed28d6
13
src/fcstr.c
13
src/fcstr.c
|
@ -1217,6 +1217,17 @@ FcStrSetDel (FcStrSet *set, const FcChar8 *s)
|
||||||
return FcFalse;
|
return FcFalse;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* TODO Make public */
|
||||||
|
static FcStrSet *
|
||||||
|
FcStrSetReference (FcStrSet *set)
|
||||||
|
{
|
||||||
|
if (FcRefIsConst (&set->ref))
|
||||||
|
return set;
|
||||||
|
|
||||||
|
FcRefInc (&set->ref);
|
||||||
|
return set;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
FcStrSetDestroy (FcStrSet *set)
|
FcStrSetDestroy (FcStrSet *set)
|
||||||
{
|
{
|
||||||
|
@ -1245,7 +1256,7 @@ FcStrListCreate (FcStrSet *set)
|
||||||
if (!list)
|
if (!list)
|
||||||
return 0;
|
return 0;
|
||||||
list->set = set;
|
list->set = set;
|
||||||
FcRefInc (&set->ref);
|
FcStrSetReference (set);
|
||||||
list->n = 0;
|
list->n = 0;
|
||||||
return list;
|
return list;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue