diff options
-rw-r--r-- | ChangeLog | 5 | ||||
-rw-r--r-- | posix/fnmatch_loop.c | 13 | ||||
-rw-r--r-- | posix/regcomp.c | 10 | ||||
-rw-r--r-- | posix/regexec.c | 14 |
4 files changed, 30 insertions, 12 deletions
@@ -1,5 +1,10 @@ 2007-10-12 Ulrich Drepper <drepper@redhat.com> + * posix/fnmatch_loop.c: Take rule index returned as part of + findidx return value into account when accessing weights. + * posix/regcomp.c: Likewise. + * posix/regexec.c: Likewise. + * locale/programs/ld-collate.c (collate_read): Optimize a bit. (skip_to): Fix problems with parameter of elifdef/elifndef. diff --git a/posix/fnmatch_loop.c b/posix/fnmatch_loop.c index 2bdd837184..67c0ee4abb 100644 --- a/posix/fnmatch_loop.c +++ b/posix/fnmatch_loop.c @@ -1,5 +1,5 @@ -/* Copyright (C) 1991,1992,1993,1996,1997,1998,1999,2000,2001,2003,2004,2005, - 2007 Free Software Foundation, Inc. +/* Copyright (C) 1991-1993,1996-2001,2003-2005,2007 + Free Software Foundation, Inc. This file is part of the GNU C Library. The GNU C Library is free software; you can redistribute it and/or @@ -418,15 +418,20 @@ FCT (pattern, string, string_end, no_leading_period, flags, ends) /* We found a table entry. Now see whether the character we are currently at has the same equivalance class value. */ - int len = weights[idx]; + int len = weights[idx & 0xffffff]; int32_t idx2; const UCHAR *np = (const UCHAR *) n; idx2 = findidx (&np); - if (idx2 != 0 && len == weights[idx2]) + if (idx2 != 0 + && (idx >> 24) == (idx2 >> 24) + && len == weights[idx2 & 0xffffff]) { int cnt = 0; + idx &= 0xffffff; + idx2 &= 0xffffff; + while (cnt < len && (weights[idx + 1 + cnt] == weights[idx2 + 1 + cnt])) diff --git a/posix/regcomp.c b/posix/regcomp.c index 129546c32c..4cf168821c 100644 --- a/posix/regcomp.c +++ b/posix/regcomp.c @@ -3378,7 +3378,7 @@ build_equiv_class (bitset_t sbcset, const unsigned char *name) /* Build single byte matcing table for this equivalence class. */ char_buf[1] = (unsigned char) '\0'; - len = weights[idx1]; + len = weights[idx1 & 0xffffff]; for (ch = 0; ch < SBC_MAX; ++ch) { char_buf[0] = ch; @@ -3390,11 +3390,15 @@ build_equiv_class (bitset_t sbcset, const unsigned char *name) if (idx2 == 0) /* This isn't a valid character. */ continue; - if (len == weights[idx2]) + /* Compare only if the length matches and the collation rule + index is the same. */ + if (len == weights[idx2 & 0xffffff] && (idx1 >> 24) == (idx2 >> 24)) { int cnt = 0; + while (cnt <= len && - weights[idx1 + 1 + cnt] == weights[idx2 + 1 + cnt]) + weights[(idx1 & 0xffffff) + 1 + cnt] + == weights[(idx2 & 0xffffff) + 1 + cnt]) ++cnt; if (cnt > len) diff --git a/posix/regexec.c b/posix/regexec.c index bdfa3550a7..135efe7441 100644 --- a/posix/regexec.c +++ b/posix/regexec.c @@ -1,5 +1,5 @@ /* Extended regular expression matching and search library. - Copyright (C) 2002, 2003, 2004, 2005 Free Software Foundation, Inc. + Copyright (C) 2002, 2003, 2004, 2005, 2007 Free Software Foundation, Inc. This file is part of the GNU C Library. Contributed by Isamu Hasegawa <isamu@yamato.ibm.com>. @@ -3825,7 +3825,6 @@ check_node_accept_bytes (const re_dfa_t *dfa, int node_idx, const int32_t *table, *indirect; const unsigned char *weights, *extra; const char *collseqwc; - int32_t idx; /* This #include defines a local function! */ # include <locale/weight.h> @@ -3883,15 +3882,20 @@ check_node_accept_bytes (const re_dfa_t *dfa, int node_idx, _NL_CURRENT (LC_COLLATE, _NL_COLLATE_EXTRAMB); indirect = (const int32_t *) _NL_CURRENT (LC_COLLATE, _NL_COLLATE_INDIRECTMB); - idx = findidx (&cp); + int32_t idx = findidx (&cp); if (idx > 0) for (i = 0; i < cset->nequiv_classes; ++i) { int32_t equiv_class_idx = cset->equiv_classes[i]; - size_t weight_len = weights[idx]; - if (weight_len == weights[equiv_class_idx]) + size_t weight_len = weights[idx & 0xffffff]; + if (weight_len == weights[equiv_class_idx & 0xffffff] + && (idx >> 24) == (equiv_class_idx >> 24)) { int cnt = 0; + + idx &= 0xffffff; + equiv_class_idx &= 0xffffff; + while (cnt <= weight_len && (weights[equiv_class_idx + 1 + cnt] == weights[idx + 1 + cnt])) |