mirror of
https://sourceware.org/git/glibc.git
synced 2025-07-29 11:41:21 +03:00
Fix BZ #14602: strstr and strcasestr return wrong result.
This commit is contained in:
13
ChangeLog
13
ChangeLog
@ -1,3 +1,16 @@
|
|||||||
|
2012-10-08 Maxim Kuvyrkov <maxim@codesourcery.com>
|
||||||
|
|
||||||
|
[BZ #14602]
|
||||||
|
* string/str-two-way.h (AVAILABLE1, AVAILABLE2, AVAILABLE1_USES_J):
|
||||||
|
Replace with ...
|
||||||
|
(CHECK_EOL): New macro.
|
||||||
|
(two_way_short_needle): Check beginning of haystack for EOL. Use
|
||||||
|
CHECK_EOL.
|
||||||
|
* string/strcasestr.c (AVAILABLE1, AVAILABLE2, AVAILABLE1_USES_J):
|
||||||
|
Replace with CHECK_EOL.
|
||||||
|
* string/strstr.c (AVAILABLE1, AVAILABLE2, AVAILABLE1_USES_J):
|
||||||
|
Replace with CHECK_EOL.
|
||||||
|
|
||||||
2012-10-08 Joseph Myers <joseph@codesourcery.com>
|
2012-10-08 Joseph Myers <joseph@codesourcery.com>
|
||||||
|
|
||||||
* math/gen-libm-test.pl (parse_args): Handle isinf and isnan as
|
* math/gen-libm-test.pl (parse_args): Handle isinf and isnan as
|
||||||
|
@ -75,18 +75,17 @@
|
|||||||
# define CMP_FUNC memcmp
|
# define CMP_FUNC memcmp
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef AVAILABLE1
|
/* Check for end-of-line in strstr and strcasestr routines.
|
||||||
# define AVAILABLE1(h, h_l, j, n_l) AVAILABLE (h, h_l, j, n_l)
|
We piggy-back matching procedure for detecting EOL where possible,
|
||||||
#endif
|
and use AVAILABLE macro otherwise. */
|
||||||
#ifndef AVAILABLE2
|
#ifndef CHECK_EOL
|
||||||
# define AVAILABLE2(h, h_l, j, n_l) (1)
|
# define CHECK_EOL (0)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Return NULL if argument is '\0'. */
|
||||||
#ifndef RET0_IF_0
|
#ifndef RET0_IF_0
|
||||||
# define RET0_IF_0(a) /* nothing */
|
# define RET0_IF_0(a) /* nothing */
|
||||||
#endif
|
#endif
|
||||||
#ifndef AVAILABLE1_USES_J
|
|
||||||
# define AVAILABLE1_USES_J (1)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Perform a critical factorization of NEEDLE, of length NEEDLE_LEN.
|
/* Perform a critical factorization of NEEDLE, of length NEEDLE_LEN.
|
||||||
Return the index of the first byte in the right half, and set
|
Return the index of the first byte in the right half, and set
|
||||||
@ -283,11 +282,23 @@ two_way_short_needle (const unsigned char *haystack, size_t haystack_len,
|
|||||||
and use an optimized first-character loop. */
|
and use an optimized first-character loop. */
|
||||||
unsigned char needle_suffix = CANON_ELEMENT (needle[suffix]);
|
unsigned char needle_suffix = CANON_ELEMENT (needle[suffix]);
|
||||||
|
|
||||||
|
#if CHECK_EOL
|
||||||
|
/* We start matching from the SUFFIX'th element, so make sure we
|
||||||
|
don't hit '\0' before that. */
|
||||||
|
if (haystack_len < suffix + 1
|
||||||
|
&& !AVAILABLE (haystack, haystack_len, 0, suffix + 1))
|
||||||
|
return NULL;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* The two halves of needle are distinct; no extra memory is
|
/* The two halves of needle are distinct; no extra memory is
|
||||||
required, and any mismatch results in a maximal shift. */
|
required, and any mismatch results in a maximal shift. */
|
||||||
period = MAX (suffix, needle_len - suffix) + 1;
|
period = MAX (suffix, needle_len - suffix) + 1;
|
||||||
j = 0;
|
j = 0;
|
||||||
while (AVAILABLE1 (haystack, haystack_len, j, needle_len))
|
while (1
|
||||||
|
#if !CHECK_EOL
|
||||||
|
&& AVAILABLE (haystack, haystack_len, j, needle_len)
|
||||||
|
#endif
|
||||||
|
)
|
||||||
{
|
{
|
||||||
unsigned char haystack_char;
|
unsigned char haystack_char;
|
||||||
const unsigned char *pneedle;
|
const unsigned char *pneedle;
|
||||||
@ -298,13 +309,13 @@ two_way_short_needle (const unsigned char *haystack, size_t haystack_len,
|
|||||||
!= (haystack_char = CANON_ELEMENT (*phaystack++)))
|
!= (haystack_char = CANON_ELEMENT (*phaystack++)))
|
||||||
{
|
{
|
||||||
RET0_IF_0 (haystack_char);
|
RET0_IF_0 (haystack_char);
|
||||||
#if AVAILABLE1_USES_J
|
#if CHECK_EOL
|
||||||
++j;
|
++j;
|
||||||
#endif
|
#endif
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if !AVAILABLE1_USES_J
|
#if !CHECK_EOL
|
||||||
/* Calculate J if it wasn't kept up-to-date in the first-character
|
/* Calculate J if it wasn't kept up-to-date in the first-character
|
||||||
loop. */
|
loop. */
|
||||||
j = phaystack - &haystack[suffix] - 1;
|
j = phaystack - &haystack[suffix] - 1;
|
||||||
@ -346,8 +357,10 @@ two_way_short_needle (const unsigned char *haystack, size_t haystack_len,
|
|||||||
else
|
else
|
||||||
j += i - suffix + 1;
|
j += i - suffix + 1;
|
||||||
|
|
||||||
if (!AVAILABLE2 (haystack, haystack_len, j, needle_len))
|
#if CHECK_EOL
|
||||||
|
if (!AVAILABLE (haystack, haystack_len, j, needle_len))
|
||||||
break;
|
break;
|
||||||
|
#endif
|
||||||
|
|
||||||
phaystack = &haystack[suffix + j];
|
phaystack = &haystack[suffix + j];
|
||||||
}
|
}
|
||||||
|
@ -43,10 +43,8 @@
|
|||||||
#define AVAILABLE(h, h_l, j, n_l) \
|
#define AVAILABLE(h, h_l, j, n_l) \
|
||||||
(!memchr ((h) + (h_l), '\0', (j) + (n_l) - (h_l)) \
|
(!memchr ((h) + (h_l), '\0', (j) + (n_l) - (h_l)) \
|
||||||
&& ((h_l) = (j) + (n_l)))
|
&& ((h_l) = (j) + (n_l)))
|
||||||
#define AVAILABLE1(h, h_l, j, n_l) (true)
|
#define CHECK_EOL (1)
|
||||||
#define AVAILABLE2(h, h_l, j, n_l) AVAILABLE (h, h_l, j, n_l)
|
|
||||||
#define RET0_IF_0(a) if (!a) goto ret0
|
#define RET0_IF_0(a) if (!a) goto ret0
|
||||||
#define AVAILABLE1_USES_J (0)
|
|
||||||
#define CANON_ELEMENT(c) TOLOWER (c)
|
#define CANON_ELEMENT(c) TOLOWER (c)
|
||||||
#define CMP_FUNC(p1, p2, l) \
|
#define CMP_FUNC(p1, p2, l) \
|
||||||
__strncasecmp ((const char *) (p1), (const char *) (p2), l)
|
__strncasecmp ((const char *) (p1), (const char *) (p2), l)
|
||||||
|
@ -35,10 +35,8 @@
|
|||||||
#define AVAILABLE(h, h_l, j, n_l) \
|
#define AVAILABLE(h, h_l, j, n_l) \
|
||||||
(!memchr ((h) + (h_l), '\0', (j) + (n_l) - (h_l)) \
|
(!memchr ((h) + (h_l), '\0', (j) + (n_l) - (h_l)) \
|
||||||
&& ((h_l) = (j) + (n_l)))
|
&& ((h_l) = (j) + (n_l)))
|
||||||
#define AVAILABLE1(h, h_l, j, n_l) (true)
|
#define CHECK_EOL (1)
|
||||||
#define AVAILABLE2(h, h_l, j, n_l) AVAILABLE (h, h_l, j, n_l)
|
|
||||||
#define RET0_IF_0(a) if (!a) goto ret0
|
#define RET0_IF_0(a) if (!a) goto ret0
|
||||||
#define AVAILABLE1_USES_J (0)
|
|
||||||
#include "str-two-way.h"
|
#include "str-two-way.h"
|
||||||
|
|
||||||
#undef strstr
|
#undef strstr
|
||||||
|
Reference in New Issue
Block a user