Bug 57114 - regression on FcFontMatch with namelang
After 7587d1c99d
applied, family,
style, and fullname is localized against current locale or lang
if any though, the string in other languages were dropped from
the pattern. this caused unexpected mismatch on the target="font"
rules.
This fix adds other strings at the end of the list.
This commit is contained in:
parent
bdaef0b80d
commit
c20ac78b01
22
src/fcint.h
22
src/fcint.h
|
@ -923,15 +923,37 @@ FcObjectFini (void);
|
||||||
FcPrivate FcValue
|
FcPrivate FcValue
|
||||||
FcValueCanonicalize (const FcValue *v);
|
FcValueCanonicalize (const FcValue *v);
|
||||||
|
|
||||||
|
FcPrivate FcValueListPtr
|
||||||
|
FcValueListCreate (void);
|
||||||
|
|
||||||
FcPrivate void
|
FcPrivate void
|
||||||
FcValueListDestroy (FcValueListPtr l);
|
FcValueListDestroy (FcValueListPtr l);
|
||||||
|
|
||||||
|
FcPrivate FcValueListPtr
|
||||||
|
FcValueListPrepend (FcValueListPtr vallist,
|
||||||
|
FcValue value,
|
||||||
|
FcValueBinding binding);
|
||||||
|
|
||||||
|
FcPrivate FcValueListPtr
|
||||||
|
FcValueListAppend (FcValueListPtr vallist,
|
||||||
|
FcValue value,
|
||||||
|
FcValueBinding binding);
|
||||||
|
|
||||||
|
FcPrivate FcValueListPtr
|
||||||
|
FcValueListDuplicate(FcValueListPtr orig);
|
||||||
|
|
||||||
FcPrivate FcPatternElt *
|
FcPrivate FcPatternElt *
|
||||||
FcPatternObjectFindElt (const FcPattern *p, FcObject object);
|
FcPatternObjectFindElt (const FcPattern *p, FcObject object);
|
||||||
|
|
||||||
FcPrivate FcPatternElt *
|
FcPrivate FcPatternElt *
|
||||||
FcPatternObjectInsertElt (FcPattern *p, FcObject object);
|
FcPatternObjectInsertElt (FcPattern *p, FcObject object);
|
||||||
|
|
||||||
|
FcPrivate FcBool
|
||||||
|
FcPatternObjectListAdd (FcPattern *p,
|
||||||
|
FcObject object,
|
||||||
|
FcValueListPtr list,
|
||||||
|
FcBool append);
|
||||||
|
|
||||||
FcPrivate FcBool
|
FcPrivate FcBool
|
||||||
FcPatternObjectAddWithBinding (FcPattern *p,
|
FcPatternObjectAddWithBinding (FcPattern *p,
|
||||||
FcObject object,
|
FcObject object,
|
||||||
|
|
|
@ -432,7 +432,7 @@ FcFontRenderPrepare (FcConfig *config,
|
||||||
FcPattern *new;
|
FcPattern *new;
|
||||||
int i;
|
int i;
|
||||||
FcPatternElt *fe, *pe, *fel, *pel;
|
FcPatternElt *fe, *pe, *fel, *pel;
|
||||||
FcValue v, vl;
|
FcValue v;
|
||||||
FcResult result;
|
FcResult result;
|
||||||
|
|
||||||
assert (pat != NULL);
|
assert (pat != NULL);
|
||||||
|
@ -440,7 +440,7 @@ FcFontRenderPrepare (FcConfig *config,
|
||||||
|
|
||||||
new = FcPatternCreate ();
|
new = FcPatternCreate ();
|
||||||
if (!new)
|
if (!new)
|
||||||
return 0;
|
return NULL;
|
||||||
for (i = 0; i < font->num; i++)
|
for (i = 0; i < font->num; i++)
|
||||||
{
|
{
|
||||||
fe = &FcPatternElts(font)[i];
|
fe = &FcPatternElts(font)[i];
|
||||||
|
@ -478,47 +478,74 @@ FcFontRenderPrepare (FcConfig *config,
|
||||||
FcPatternEltValues(fe), &v, NULL, NULL, &result))
|
FcPatternEltValues(fe), &v, NULL, NULL, &result))
|
||||||
{
|
{
|
||||||
FcPatternDestroy (new);
|
FcPatternDestroy (new);
|
||||||
return 0;
|
return NULL;
|
||||||
}
|
}
|
||||||
if (fel && pel)
|
if (fel && pel)
|
||||||
{
|
{
|
||||||
int n = 1, j;
|
int n = 1, j;
|
||||||
|
FcValueListPtr l1, l2, ln = NULL, ll = NULL;
|
||||||
|
|
||||||
match = FcObjectToMatcher (pel->object, FcTrue);
|
match = FcObjectToMatcher (pel->object, FcTrue);
|
||||||
if (!FcCompareValueList (pel->object, match,
|
if (!FcCompareValueList (pel->object, match,
|
||||||
FcPatternEltValues (pel),
|
FcPatternEltValues (pel),
|
||||||
FcPatternEltValues (fel), &vl, NULL, &n, &result))
|
FcPatternEltValues (fel), NULL, NULL, &n, &result))
|
||||||
{
|
{
|
||||||
FcPatternDestroy (new);
|
FcPatternDestroy (new);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
FcValueListPtr l;
|
|
||||||
|
|
||||||
for (j = 0, l = FcPatternEltValues (fe);
|
for (j = 0, l1 = FcPatternEltValues (fe), l2 = FcPatternEltValues (fel);
|
||||||
j < n && l != NULL;
|
l1 != NULL || l2 != NULL;
|
||||||
j++, l = FcValueListNext (l));
|
j++, l1 = l1 ? FcValueListNext (l1) : NULL, l2 = l2 ? FcValueListNext (l2) : NULL)
|
||||||
if (l)
|
{
|
||||||
v = FcValueCanonicalize (&l->value);
|
if (j == n)
|
||||||
|
{
|
||||||
|
if (l1)
|
||||||
|
ln = FcValueListPrepend (ln,
|
||||||
|
FcValueCanonicalize (&l1->value),
|
||||||
|
FcValueBindingStrong);
|
||||||
|
if (l2)
|
||||||
|
ll = FcValueListPrepend (ll,
|
||||||
|
FcValueCanonicalize (&l2->value),
|
||||||
|
FcValueBindingStrong);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
v = FcValueCanonicalize (&FcPatternEltValues (fe)->value);
|
{
|
||||||
|
if (l1)
|
||||||
|
ln = FcValueListAppend (ln,
|
||||||
|
FcValueCanonicalize (&l1->value),
|
||||||
|
FcValueBindingStrong);
|
||||||
|
if (l2)
|
||||||
|
ll = FcValueListAppend (ll,
|
||||||
|
FcValueCanonicalize (&l2->value),
|
||||||
|
FcValueBindingStrong);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
FcPatternObjectListAdd (new, fe->object, ln, FcFalse);
|
||||||
|
FcPatternObjectListAdd (new, fel->object, ll, FcFalse);
|
||||||
|
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
else if (fel)
|
else if (fel)
|
||||||
{
|
{
|
||||||
vl = FcValueCanonicalize (&FcPatternEltValues (fel)->value);
|
FcValueListPtr l1, l2;
|
||||||
|
|
||||||
|
copy_lang:
|
||||||
|
l1 = FcValueListDuplicate (FcPatternEltValues (fe));
|
||||||
|
l2 = FcValueListDuplicate (FcPatternEltValues (fel));
|
||||||
|
FcPatternObjectListAdd (new, fe->object, l1, FcFalse);
|
||||||
|
FcPatternObjectListAdd (new, fel->object, l2, FcFalse);
|
||||||
|
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
v = FcValueCanonicalize(&FcPatternEltValues (fe)->value);
|
|
||||||
if (fel)
|
if (fel)
|
||||||
vl = FcValueCanonicalize (&FcPatternEltValues (fel)->value);
|
goto copy_lang;
|
||||||
|
v = FcValueCanonicalize(&FcPatternEltValues (fe)->value);
|
||||||
}
|
}
|
||||||
FcPatternObjectAdd (new, fe->object, v, FcFalse);
|
FcPatternObjectAdd (new, fe->object, v, FcFalse);
|
||||||
if (fel)
|
|
||||||
FcPatternObjectAdd (new, fel->object, vl, FcFalse);
|
|
||||||
}
|
}
|
||||||
for (i = 0; i < pat->num; i++)
|
for (i = 0; i < pat->num; i++)
|
||||||
{
|
{
|
||||||
|
|
146
src/fcpat.c
146
src/fcpat.c
|
@ -120,6 +120,20 @@ FcValueSave (FcValue v)
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FcValueListPtr
|
||||||
|
FcValueListCreate (void)
|
||||||
|
{
|
||||||
|
FcValueListPtr ret;
|
||||||
|
|
||||||
|
ret = calloc (1, sizeof (FcValueList));
|
||||||
|
if (ret)
|
||||||
|
{
|
||||||
|
FcMemAlloc(FC_MEM_VALLIST, sizeof (FcValueList));
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
FcValueListDestroy (FcValueListPtr l)
|
FcValueListDestroy (FcValueListPtr l)
|
||||||
{
|
{
|
||||||
|
@ -151,6 +165,81 @@ FcValueListDestroy (FcValueListPtr l)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FcValueListPtr
|
||||||
|
FcValueListPrepend (FcValueListPtr vallist,
|
||||||
|
FcValue value,
|
||||||
|
FcValueBinding binding)
|
||||||
|
{
|
||||||
|
FcValueListPtr new;
|
||||||
|
|
||||||
|
if (value.type == FcTypeVoid)
|
||||||
|
return vallist;
|
||||||
|
new = FcValueListCreate ();
|
||||||
|
if (!new)
|
||||||
|
return vallist;
|
||||||
|
|
||||||
|
new->value = FcValueSave (value);
|
||||||
|
new->binding = binding;
|
||||||
|
new->next = vallist;
|
||||||
|
|
||||||
|
return new;
|
||||||
|
}
|
||||||
|
|
||||||
|
FcValueListPtr
|
||||||
|
FcValueListAppend (FcValueListPtr vallist,
|
||||||
|
FcValue value,
|
||||||
|
FcValueBinding binding)
|
||||||
|
{
|
||||||
|
FcValueListPtr new, last;
|
||||||
|
|
||||||
|
if (value.type == FcTypeVoid)
|
||||||
|
return vallist;
|
||||||
|
new = FcValueListCreate ();
|
||||||
|
if (!new)
|
||||||
|
return vallist;
|
||||||
|
|
||||||
|
new->value = FcValueSave (value);
|
||||||
|
new->binding = binding;
|
||||||
|
new->next = NULL;
|
||||||
|
|
||||||
|
if (vallist)
|
||||||
|
{
|
||||||
|
for (last = vallist; FcValueListNext (last); last = FcValueListNext (last));
|
||||||
|
|
||||||
|
last->next = new;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
vallist = new;
|
||||||
|
|
||||||
|
return vallist;
|
||||||
|
}
|
||||||
|
|
||||||
|
FcValueListPtr
|
||||||
|
FcValueListDuplicate(FcValueListPtr orig)
|
||||||
|
{
|
||||||
|
FcValueListPtr new = NULL, l, t = NULL;
|
||||||
|
FcValue v;
|
||||||
|
|
||||||
|
for (l = orig; l != NULL; l = FcValueListNext (l))
|
||||||
|
{
|
||||||
|
if (!new)
|
||||||
|
{
|
||||||
|
t = new = FcValueListCreate();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
t->next = FcValueListCreate();
|
||||||
|
t = FcValueListNext (t);
|
||||||
|
}
|
||||||
|
v = FcValueCanonicalize (&l->value);
|
||||||
|
t->value = FcValueSave (v);
|
||||||
|
t->binding = l->binding;
|
||||||
|
t->next = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new;
|
||||||
|
}
|
||||||
|
|
||||||
FcBool
|
FcBool
|
||||||
FcValueEqual (FcValue va, FcValue vb)
|
FcValueEqual (FcValue va, FcValue vb)
|
||||||
{
|
{
|
||||||
|
@ -460,6 +549,59 @@ FcPatternEqualSubset (const FcPattern *pai, const FcPattern *pbi, const FcObject
|
||||||
return FcTrue;
|
return FcTrue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FcBool
|
||||||
|
FcPatternObjectListAdd (FcPattern *p,
|
||||||
|
FcObject object,
|
||||||
|
FcValueListPtr list,
|
||||||
|
FcBool append)
|
||||||
|
{
|
||||||
|
FcPatternElt *e;
|
||||||
|
FcValueListPtr l, *prev;
|
||||||
|
|
||||||
|
if (p->ref == FC_REF_CONSTANT)
|
||||||
|
goto bail0;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Make sure the stored type is valid for built-in objects
|
||||||
|
*/
|
||||||
|
for (l = list; l != NULL; l = FcValueListNext (l))
|
||||||
|
{
|
||||||
|
if (!FcObjectValidType (object, l->value.type))
|
||||||
|
{
|
||||||
|
if (FcDebug() & FC_DBG_OBJTYPES)
|
||||||
|
{
|
||||||
|
printf ("FcPattern object %s does not accept value ",
|
||||||
|
FcObjectName (object));
|
||||||
|
FcValuePrint (l->value);
|
||||||
|
}
|
||||||
|
goto bail0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
e = FcPatternObjectInsertElt (p, object);
|
||||||
|
if (!e)
|
||||||
|
goto bail0;
|
||||||
|
|
||||||
|
if (append)
|
||||||
|
{
|
||||||
|
for (prev = &e->values; *prev; prev = &(*prev)->next)
|
||||||
|
;
|
||||||
|
*prev = list;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for (prev = &list; *prev; prev = &(*prev)->next)
|
||||||
|
;
|
||||||
|
*prev = e->values;
|
||||||
|
e->values = list;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FcTrue;
|
||||||
|
|
||||||
|
bail0:
|
||||||
|
return FcFalse;
|
||||||
|
}
|
||||||
|
|
||||||
FcBool
|
FcBool
|
||||||
FcPatternObjectAddWithBinding (FcPattern *p,
|
FcPatternObjectAddWithBinding (FcPattern *p,
|
||||||
FcObject object,
|
FcObject object,
|
||||||
|
@ -473,12 +615,10 @@ FcPatternObjectAddWithBinding (FcPattern *p,
|
||||||
if (p->ref == FC_REF_CONSTANT)
|
if (p->ref == FC_REF_CONSTANT)
|
||||||
goto bail0;
|
goto bail0;
|
||||||
|
|
||||||
new = malloc (sizeof (FcValueList));
|
new = FcValueListCreate ();
|
||||||
if (!new)
|
if (!new)
|
||||||
goto bail0;
|
goto bail0;
|
||||||
|
|
||||||
memset(new, 0, sizeof (FcValueList));
|
|
||||||
FcMemAlloc (FC_MEM_VALLIST, sizeof (FcValueList));
|
|
||||||
value = FcValueSave (value);
|
value = FcValueSave (value);
|
||||||
if (value.type == FcTypeVoid)
|
if (value.type == FcTypeVoid)
|
||||||
goto bail1;
|
goto bail1;
|
||||||
|
|
Loading…
Reference in New Issue