]> git.wh0rd.org - fontconfig.git/blobdiff - src/fcmatch.c
Don't do random matching when bad objects are passed into
[fontconfig.git] / src / fcmatch.c
index bc75aa619cfce65c5bfe3f0ce587d26df579d614..26c4124ded61626251505ee42b4874e0febe334e 100644 (file)
@@ -174,6 +174,7 @@ FcCompareSize (FcValue *value1, FcValue *value2)
 
 typedef struct _FcMatcher {
     const char     *object;
+    FcObjectPtr            objectPtr;
     double         (*compare) (FcValue *value1, FcValue *value2);
     int                    strong, weak;
 } FcMatcher;
@@ -184,68 +185,90 @@ typedef struct _FcMatcher {
  * later values
  */
 static FcMatcher _FcMatchers [] = {
-    { FC_FOUNDRY,      FcCompareString,        0, 0 },
+    { FC_FOUNDRY,      0, FcCompareString,     0, 0 },
 #define MATCH_FOUNDRY      0
 #define MATCH_FOUNDRY_INDEX 0
     
-    { FC_CHARSET,      FcCompareCharSet,       1, 1 },
+    { FC_CHARSET,      0, FcCompareCharSet,    1, 1 },
 #define MATCH_CHARSET      1
 #define MATCH_CHARSET_INDEX 1
     
-    { FC_FAMILY,       FcCompareFamily,        2, 4 },
+    { FC_FAMILY,       0, FcCompareFamily,     2, 4 },
 #define MATCH_FAMILY       2
 #define MATCH_FAMILY_STRONG_INDEX   2
 #define MATCH_FAMILY_WEAK_INDEX            4
     
-    { FC_LANG,         FcCompareLang,          3, 3 },
+    { FC_LANG,         0, FcCompareLang,       3, 3 },
 #define MATCH_LANG         3
 #define MATCH_LANG_INDEX    3
     
-    { FC_SPACING,      FcCompareNumber,        5, 5 },
+    { FC_SPACING,      0, FcCompareNumber,     5, 5 },
 #define MATCH_SPACING      4
 #define MATCH_SPACING_INDEX 5
     
-    { FC_PIXEL_SIZE,   FcCompareSize,          6, 6 },
+    { FC_PIXEL_SIZE,   0, FcCompareSize,       6, 6 },
 #define MATCH_PIXEL_SIZE    5
 #define MATCH_PIXEL_SIZE_INDEX 6
     
-    { FC_STYLE,                FcCompareString,        7, 7 },
+    { FC_STYLE,                0, FcCompareString,     7, 7 },
 #define MATCH_STYLE        6
 #define MATCH_STYLE_INDEX   7
     
-    { FC_SLANT,                FcCompareNumber,        8, 8 },
+    { FC_SLANT,                0, FcCompareNumber,     8, 8 },
 #define MATCH_SLANT        7
 #define MATCH_SLANT_INDEX   8
     
-    { FC_WEIGHT,       FcCompareNumber,        9, 9 },
+    { FC_WEIGHT,       0, FcCompareNumber,     9, 9 },
 #define MATCH_WEIGHT       8
 #define MATCH_WEIGHT_INDEX  9
     
-    { FC_WIDTH,                FcCompareNumber,        10, 10 },
+    { FC_WIDTH,                0, FcCompareNumber,     10, 10 },
 #define MATCH_WIDTH        9
 #define MATCH_WIDTH_INDEX   10
     
-    { FC_ANTIALIAS,    FcCompareBool,          11, 11 },
+    { FC_ANTIALIAS,    0, FcCompareBool,       11, 11 },
 #define MATCH_ANTIALIAS            10
 #define MATCH_ANTIALIAS_INDEX      11
     
-    { FC_RASTERIZER,   FcCompareString,        12, 12 },
+    { FC_RASTERIZER,   0, FcCompareString,     12, 12 },
 #define MATCH_RASTERIZER    11
 #define MATCH_RASTERIZER_INDEX    12
 
-    { FC_OUTLINE,      FcCompareBool,          13, 13 },
+    { FC_OUTLINE,      0, FcCompareBool,       13, 13 },
 #define MATCH_OUTLINE      12
 #define MATCH_OUTLINE_INDEX        13
 
-    { FC_FONTVERSION,  FcCompareNumber,        14, 14 },
+    { FC_FONTVERSION,  0, FcCompareNumber,     14, 14 },
 #define MATCH_FONTVERSION   13
 #define MATCH_FONTVERSION_INDEX   14
 };
 
 #define NUM_MATCH_VALUES    15
 
+static FcBool matchObjectPtrsInit = FcFalse;
+
+static void
+FcMatchObjectPtrsInit (void)
+{
+    _FcMatchers[MATCH_FOUNDRY].objectPtr = FcObjectToPtr(FC_FOUNDRY);
+    _FcMatchers[MATCH_CHARSET].objectPtr = FcObjectToPtr(FC_CHARSET);
+    _FcMatchers[MATCH_FAMILY].objectPtr = FcObjectToPtr(FC_FAMILY);
+    _FcMatchers[MATCH_LANG].objectPtr = FcObjectToPtr(FC_LANG);
+    _FcMatchers[MATCH_SPACING].objectPtr = FcObjectToPtr(FC_SPACING);
+    _FcMatchers[MATCH_PIXEL_SIZE].objectPtr = FcObjectToPtr(FC_PIXEL_SIZE);
+    _FcMatchers[MATCH_STYLE].objectPtr = FcObjectToPtr(FC_STYLE);
+    _FcMatchers[MATCH_SLANT].objectPtr = FcObjectToPtr(FC_SLANT);
+    _FcMatchers[MATCH_WEIGHT].objectPtr = FcObjectToPtr(FC_WEIGHT);
+    _FcMatchers[MATCH_WIDTH].objectPtr = FcObjectToPtr(FC_WIDTH);
+    _FcMatchers[MATCH_ANTIALIAS].objectPtr = FcObjectToPtr(FC_ANTIALIAS);
+    _FcMatchers[MATCH_RASTERIZER].objectPtr = FcObjectToPtr(FC_RASTERIZER);
+    _FcMatchers[MATCH_OUTLINE].objectPtr = FcObjectToPtr(FC_OUTLINE);
+    _FcMatchers[MATCH_FONTVERSION].objectPtr = FcObjectToPtr(FC_FONTVERSION);
+    matchObjectPtrsInit = FcTrue;
+}
+
 static FcBool
-FcCompareValueList (const char  *object,
+FcCompareValueList (FcObjectPtr o,
                    FcValueListPtr v1orig,      /* pattern */
                    FcValueListPtr v2orig,      /* target */
                    FcValue     *bestValue,
@@ -257,17 +280,18 @@ FcCompareValueList (const char  *object,
     double         v, best, bestStrong, bestWeak;
     int                    i;
     int                    j;
-    
+    const char     *object = FcObjectPtrU(o);
+
     /*
      * Locate the possible matching entry by examining the
      * first few characters in object
      */
     i = -1;
-    switch (FcToLower (object[0])) {
+    switch (object[0]) {
     case 'f':
-       switch (FcToLower (object[1])) {
+       switch (object[1]) {
        case 'o':
-           switch (FcToLower (object[2])) {
+           switch (object[2]) {
            case 'u':
                i = MATCH_FOUNDRY; break;
            case 'n':
@@ -285,7 +309,7 @@ FcCompareValueList (const char  *object,
     case 'l':
        i = MATCH_LANG; break;
     case 's':
-       switch (FcToLower (object[1])) {
+       switch (object[1]) {
        case 'p':
            i = MATCH_SPACING; break;
        case 't':
@@ -297,7 +321,7 @@ FcCompareValueList (const char  *object,
     case 'p':
        i = MATCH_PIXEL_SIZE; break;
     case 'w':
-       switch (FcToLower (object[1])) {
+       switch (object[1]) {
        case 'i':
            i = MATCH_WIDTH; break;
        case 'e':
@@ -309,6 +333,11 @@ FcCompareValueList (const char  *object,
     case 'o':
        i = MATCH_OUTLINE; break;
     }
+
+    if (!matchObjectPtrsInit)
+        FcMatchObjectPtrsInit();
+    if (_FcMatchers[i].objectPtr != o) i = -1;
+
     if (i == -1 || 
        FcStrCmpIgnoreCase ((FcChar8 *) _FcMatchers[i].object,
                            (FcChar8 *) object) != 0)
@@ -317,20 +346,6 @@ FcCompareValueList (const char  *object,
            *bestValue = FcValueCanonicalize(&FcValueListPtrU(v2orig)->value);
        return FcTrue;
     }
-#if 0
-    for (i = 0; i < NUM_MATCHER; i++)
-    {
-       if (!FcStrCmpIgnoreCase ((FcChar8 *) _FcMatchers[i].object,
-                                (FcChar8 *) object))
-           break;
-    }
-    if (i == NUM_MATCHER)
-    {
-       if (bestValue)
-           *bestValue = v2orig->value;
-       return FcTrue;
-    }
-#endif
     best = 1e99;
     bestStrong = 1e99;
     bestWeak = 1e99;
@@ -348,8 +363,6 @@ FcCompareValueList (const char  *object,
                *result = FcResultTypeMismatch;
                return FcFalse;
            }
-           if (FcDebug () & FC_DBG_MATCHV)
-               printf (" v %g j %d ", v, j);
            v = v * 100 + j;
            if (v < best)
            {
@@ -423,7 +436,7 @@ FcCompare (FcPattern        *pat,
            i1++;
        else
        {
-           if (!FcCompareValueList (FcObjectPtrU(elt_i1->object), 
+           if (!FcCompareValueList (elt_i1->object,
                                     elt_i1->values, elt_i2->values,
                                     0, value, result))
                return FcFalse;
@@ -454,7 +467,7 @@ FcFontRenderPrepare (FcConfig           *config,
        pe = FcPatternFindElt (pat, FcObjectPtrU(fe->object));
        if (pe)
        {
-           if (!FcCompareValueList (FcObjectPtrU(pe->object), pe->values, 
+           if (!FcCompareValueList (pe->object, pe->values, 
                                     fe->values, &v, 0, &result))
            {
                FcPatternDestroy (new);