Fix aliasing problems.

This commit is contained in:
Ulrich Drepper 1999-07-28 04:34:36 +00:00
parent 3703b10b6f
commit 3068508dba
3 changed files with 333 additions and 224 deletions

View File

@ -110,51 +110,68 @@ __STRING2_COPY_TYPE (8);
# define __memset_gc(s, c, n) \
({ void *__s = (s); \
__uint32_t *__ts = (__uint32_t *) __s; \
union { \
unsigned int __ui; \
unsigned short int __usi; \
unsigned char __uc; \
} *__u = __s; \
__uint8_t __c = (__uint8_t) (c); \
\
\
/* This `switch' statement will be removed at compile-time. */ \
switch (n) \
{ \
case 15: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 11: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 7: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 3: \
*((__uint16_t *) __ts)++ = __c * 0x0101; \
*((__uint8_t *) __ts) = __c; \
__u->__usi = (unsigned short int) __c * 0x0101; \
__u = (void *) __u + 2; \
__u->__uc = (unsigned char) __c; \
break; \
\
case 14: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 10: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 6: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 2: \
*((__uint16_t *) __ts) = __c * 0x0101; \
__u->__usi = (unsigned short int) __c * 0x0101; \
break; \
\
case 13: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 9: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 5: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 1: \
*((__uint8_t *) __ts) = __c; \
__u->__uc = (unsigned char) __c; \
break; \
\
case 16: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 12: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 8: \
*__ts++ = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
__u = (void *) __u + 4; \
case 4: \
*__ts = __c * 0x01010101; \
__u->__ui = __c * 0x01010101; \
case 0: \
break; \
} \
@ -167,9 +184,9 @@ __STRING2_COPY_TYPE (8);
: memset (s, c, n)))
# endif
/* GCC optimizes memset(s, 0, n) but not bzero(s, n). */
#if defined __GNUC__ \
&& (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ > 90))
/* GCC optimizes memset(s, 0, n) but not bzero(s, n).
The optimization is broken before EGCS 1.1. */
# if __GNUC_PREREQ (2, 91)
# define __bzero(s, n) __builtin_memset (s, '\0', n)
# endif
@ -207,48 +224,60 @@ __mempcpy_small (void *__dest1,
__uint32_t __src0_4, __uint32_t __src4_4,
size_t __srclen)
{
char *__dest = (char *) __dest1;
union {
__uint32_t __ui;
__uint16_t __usi;
unsigned char __uc;
unsigned char __c;
} *__u = __dest1;
switch (__srclen)
{
case 1:
*__dest++ = __src0_1;
__u->__c = __src0_1;
__u = (void *) __u + 1;
break;
case 2:
*((__uint16_t *) __dest) = __src0_2;
__dest += 2;
__u->__usi = __src0_2;
__u = (void *) __u + 2;
break;
case 3:
*((__uint16_t *) __dest) = __src0_2;
__dest += 2;
*__dest++ = __src2_1;
__u->__usi = __src0_2;
__u = (void *) __u + 2;
__u->__c = __src2_1;
__u = (void *) __u + 1;
break;
case 4:
*((__uint32_t *) __dest) = __src0_4;
__dest += 4;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
break;
case 5:
*((__uint32_t *) __dest) = __src0_4;
__dest += 4;
*__dest++ = __src4_1;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__c = __src4_1;
__u = (void *) __u + 1;
break;
case 6:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
__dest += 6;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
__u = (void *) __u + 2;
break;
case 7:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
__dest += 6;
*__dest++ = __src6_1;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
__u = (void *) __u + 2;
__u->__c = __src6_1;
__u = (void *) __u + 1;
break;
case 8:
*((__uint32_t *) __dest) = __src0_4;
*((__uint32_t *) (__dest + 4)) = __src4_4;
__dest += 8;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__ui = __src4_4;
__u = (void *) __u + 4;
break;
}
return (void *) __dest;
return (void *) __u;
}
# else
# define __mempcpy_args(src) \
@ -287,41 +316,50 @@ __STRING_INLINE void *__mempcpy_small (void *, char, __STRING2_COPY_ARR2,
__STRING2_COPY_ARR7,
__STRING2_COPY_ARR8, size_t);
__STRING_INLINE void *
__mempcpy_small (void *__dest1, char __src1,
__mempcpy_small (void *__dest, char __src1,
__STRING2_COPY_ARR2 __src2, __STRING2_COPY_ARR3 __src3,
__STRING2_COPY_ARR4 __src4, __STRING2_COPY_ARR5 __src5,
__STRING2_COPY_ARR6 __src6, __STRING2_COPY_ARR7 __src7,
__STRING2_COPY_ARR8 __src8, size_t __srclen)
{
char *__dest = (char *) __dest1;
union {
char __c;
__STRING2_COPY_ARR2 __sca2;
__STRING2_COPY_ARR3 __sca3;
__STRING2_COPY_ARR4 __sca4;
__STRING2_COPY_ARR5 __sca5;
__STRING2_COPY_ARR6 __sca6;
__STRING2_COPY_ARR7 __sca7;
__STRING2_COPY_ARR8 __sca8;
} *__u = __dest;
switch (__srclen)
{
case 1:
*__dest = __src1;
__u->__c = __src1;
break;
case 2:
__extension__ *((__STRING2_COPY_ARR2 *) __dest) = __src2;
__extension__ __u->__sca2 = __src2;
break;
case 3:
__extension__ *((__STRING2_COPY_ARR3 *) __dest) = __src3;
__extension__ __u->__sca3 = __src3;
break;
case 4:
__extension__ *((__STRING2_COPY_ARR4 *) __dest) = __src4;
__extension__ __u->__sca4 = __src4;
break;
case 5:
__extension__ *((__STRING2_COPY_ARR5 *) __dest) = __src5;
__extension__ __u->__sca5 = __src5;
break;
case 6:
__extension__ *((__STRING2_COPY_ARR6 *) __dest) = __src6;
__extension__ __u->__sca6 = __src6;
break;
case 7:
__extension__ *((__STRING2_COPY_ARR7 *) __dest) = __src7;
__extension__ __u->__sca7 = __src7;
break;
case 8:
__extension__ *((__STRING2_COPY_ARR8 *) __dest) = __src8;
__extension__ __u->__sca8 = __src8;
break;
}
return (void *) (__dest + __srclen);
return __extension__ ((void *) __u + __srclen);
}
# endif
# endif
@ -362,37 +400,48 @@ __strcpy_small (char *__dest,
__uint32_t __src0_4, __uint32_t __src4_4,
size_t __srclen)
{
union {
__uint32_t __ui;
__uint16_t __usi;
unsigned char __uc;
} *__u = (void *) __dest;
switch (__srclen)
{
case 1:
*__dest = '\0';
__u->__uc = '\0';
break;
case 2:
*((__uint16_t *) __dest) = __src0_2;
__u->__usi = __src0_2;
break;
case 3:
*((__uint16_t *) __dest) = __src0_2;
*(__dest + 2) = '\0';
__u->__usi = __src0_2;
__u = (void *) __u + 2;
__u->__uc = '\0';
break;
case 4:
*((__uint32_t *) __dest) = __src0_4;
__u->__ui = __src0_4;
break;
case 5:
*((__uint32_t *) __dest) = __src0_4;
*(__dest + 4) = '\0';
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__uc = '\0';
break;
case 6:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
break;
case 7:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
*(__dest + 6) = '\0';
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
__u = (void *) __u + 2;
__u->__uc = '\0';
break;
case 8:
*((__uint32_t *) __dest) = __src0_4;
*((__uint32_t *) (__dest + 4)) = __src4_4;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_4;
break;
}
return __dest;
@ -439,31 +488,41 @@ __strcpy_small (char *__dest,
__STRING2_COPY_ARR6 __src6, __STRING2_COPY_ARR7 __src7,
__STRING2_COPY_ARR8 __src8, size_t __srclen)
{
union {
char __c;
__STRING2_COPY_ARR2 __sca2;
__STRING2_COPY_ARR3 __sca3;
__STRING2_COPY_ARR4 __sca4;
__STRING2_COPY_ARR5 __sca5;
__STRING2_COPY_ARR6 __sca6;
__STRING2_COPY_ARR7 __sca7;
__STRING2_COPY_ARR8 __sca8;
} *__u = (void *) __dest;
switch (__srclen)
{
case 1:
*__dest = '\0';
__u->__c = '\0';
break;
case 2:
__extension__ *((__STRING2_COPY_ARR2 *) __dest) = __src2;
__extension__ __u->__sca2 = __src2;
break;
case 3:
__extension__ *((__STRING2_COPY_ARR3 *) __dest) = __src3;
__extension__ __u->__sca3 = __src3;
break;
case 4:
__extension__ *((__STRING2_COPY_ARR4 *) __dest) = __src4;
__extension__ __u->__sca4 = __src4;
break;
case 5:
__extension__ *((__STRING2_COPY_ARR5 *) __dest) = __src5;
__extension__ __u->__sca5 = __src5;
break;
case 6:
__extension__ *((__STRING2_COPY_ARR6 *) __dest) = __src6;
__extension__ __u->__sca6 = __src6;
break;
case 7:
__extension__ *((__STRING2_COPY_ARR7 *) __dest) = __src7;
__extension__ __u->__sca7 = __src7;
break;
case 8:
__extension__ *((__STRING2_COPY_ARR8 *) __dest) = __src8;
__extension__ __u->__sca8 = __src8;
break;
}
return __dest;
@ -500,47 +559,55 @@ __stpcpy_small (char *__dest,
__uint32_t __src0_4, __uint32_t __src4_4,
size_t __srclen)
{
union {
unsigned int __ui;
unsigned short int __usi;
unsigned char __uc;
} *__u = (void *) __dest;
switch (__srclen)
{
case 1:
*__dest = '\0';
__u->__uc = '\0';
break;
case 2:
*((__uint16_t *) __dest) = __src0_2;
++__dest;
__u->__usi = __src0_2;
__u = (void *) __u + 1;
break;
case 3:
*((__uint16_t *) __dest) = __src0_2;
__dest += sizeof (__uint16_t);
*__dest = '\0';
__u->__usi = __src0_2;
__u = (void *) __u + 2;
__u->__uc = '\0';
break;
case 4:
*((__uint32_t *) __dest) = __src0_4;
__dest += 3;
__u->__ui = __src0_4;
__u = (void *) __u + 3;
break;
case 5:
*((__uint32_t *) __dest) = __src0_4;
__dest += 4;
*__dest = '\0';
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__uc = '\0';
break;
case 6:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
__dest += 5;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
__u = (void *) __u + 1;
break;
case 7:
*((__uint32_t *) __dest) = __src0_4;
*((__uint16_t *) (__dest + 4)) = __src4_2;
__dest += 6;
*__dest = '\0';
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__usi = __src4_2;
__u = (void *) __u + 2;
__u->__uc = '\0';
break;
case 8:
*((__uint32_t *) __dest) = __src0_4;
*((__uint32_t *) (__dest + 4)) = __src4_4;
__dest += 7;
__u->__ui = __src0_4;
__u = (void *) __u + 4;
__u->__ui = __src4_4;
__u = (void *) __u + 3;
break;
}
return __dest;
return &__u->__uc;
}
# else
# define __stpcpy_args(src) \
@ -584,31 +651,41 @@ __stpcpy_small (char *__dest,
__STRING2_COPY_ARR6 __src6, __STRING2_COPY_ARR7 __src7,
__STRING2_COPY_ARR8 __src8, size_t __srclen)
{
union {
char __c;
__STRING2_COPY_ARR2 __sca2;
__STRING2_COPY_ARR3 __sca3;
__STRING2_COPY_ARR4 __sca4;
__STRING2_COPY_ARR5 __sca5;
__STRING2_COPY_ARR6 __sca6;
__STRING2_COPY_ARR7 __sca7;
__STRING2_COPY_ARR8 __sca8;
} *__u = (void *) __dest;
switch (__srclen)
{
case 1:
*__dest = '\0';
__u->__c = '\0';
break;
case 2:
__extension__ *((__STRING2_COPY_ARR2 *) __dest) = __src2;
__extension__ __u->__sca2 = __src2;
break;
case 3:
__extension__ *((__STRING2_COPY_ARR3 *) __dest) = __src3;
__extension__ __u->__sca3 = __src3;
break;
case 4:
__extension__ *((__STRING2_COPY_ARR4 *) __dest) = __src4;
__extension__ __u->__sca4 = __src4;
break;
case 5:
__extension__ *((__STRING2_COPY_ARR5 *) __dest) = __src5;
__extension__ __u->__sca5 = __src5;
break;
case 6:
__extension__ *((__STRING2_COPY_ARR6 *) __dest) = __src6;
__extension__ __u->__sca6 = __src6;
break;
case 7:
__extension__ *((__STRING2_COPY_ARR7 *) __dest) = __src7;
__extension__ __u->__sca7 = __src7;
break;
case 8:
__extension__ *((__STRING2_COPY_ARR8 *) __dest) = __src8;
__extension__ __u->__sca8 = __src8;
break;
}
return __dest + __srclen - 1;

View File

@ -54,59 +54,65 @@ __STRING_INLINE void *
__memcpy_c (void *__dest, __const void *__src, size_t __n)
{
register unsigned long int __d0, __d1, __d2;
union {
unsigned int __ui;
unsigned short int __usi;
unsigned char __uc;
} *__u = __dest;
switch (__n)
{
case 0:
return __dest;
case 1:
*(unsigned char *) __dest = *(const unsigned char *) __src;
__u->__uc = *(const unsigned char *) __src;
return __dest;
case 2:
*(unsigned short int *) __dest = *(const unsigned short int *) __src;
__u->__usi = *(const unsigned short int *) __src;
return __dest;
case 3:
*(unsigned short int *) __dest = *(const unsigned short int *) __src;
*(2 + (unsigned char *) __dest) = *(2 + (const unsigned char *) __src);
__u->__usi = *(const unsigned short int *) __src;
__u = (void *) __u + 2;
__u->__uc = *(2 + (const unsigned char *) __src);
return __dest;
case 4:
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
__u->__ui = *(const unsigned int *) __src;
return __dest;
case 6: /* for ethernet addresses */
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
*(2 + (unsigned short int *) __dest) =
*(2 + (const unsigned short int *) __src);
case 6:
__u->__ui = *(const unsigned int *) __src;
__u = (void *) __u + 4;
__u->__usi = *(2 + (const unsigned short int *) __src);
return __dest;
case 8:
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
*(1 + (unsigned long int *) __dest) =
*(1 + (const unsigned long int *) __src);
__u->__ui = *(const unsigned int *) __src;
__u = (void *) __u + 4;
__u->__ui = *(1 + (const unsigned int *) __src);
return __dest;
case 12:
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
*(1 + (unsigned long int *) __dest) =
*(1 + (const unsigned long int *) __src);
*(2 + (unsigned long int *) __dest) =
*(2 + (const unsigned long int *) __src);
__u->__ui = *(const unsigned int *) __src;
__u = (void *) __u + 4;
__u->__ui = *(1 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(2 + (const unsigned int *) __src);
return __dest;
case 16:
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
*(1 + (unsigned long int *) __dest) =
*(1 + (const unsigned long int *) __src);
*(2 + (unsigned long int *) __dest) =
*(2 + (const unsigned long int *) __src);
*(3 + (unsigned long int *) __dest) =
*(3 + (const unsigned long int *) __src);
__u->__ui = *(const unsigned int *) __src;
__u = (void *) __u + 4;
__u->__ui = *(1 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(2 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(3 + (const unsigned int *) __src);
return __dest;
case 20:
*(unsigned long int *) __dest = *(const unsigned long int *) __src;
*(1 + (unsigned long int *) __dest) =
*(1 + (const unsigned long int *) __src);
*(2 + (unsigned long int *) __dest) =
*(2 + (const unsigned long int *) __src);
*(3 + (unsigned long int *) __dest) =
*(3 + (const unsigned long int *) __src);
*(4 + (unsigned long int *) __dest) =
*(4 + (const unsigned long int *) __src);
__u->__ui = *(const unsigned int *) __src;
__u = (void *) __u + 4;
__u->__ui = *(1 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(2 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(3 + (const unsigned int *) __src);
__u = (void *) __u + 4;
__u->__ui = *(4 + (const unsigned int *) __src);
return __dest;
}
#define __COMMON_CODE(x) \
@ -115,7 +121,7 @@ __memcpy_c (void *__dest, __const void *__src, size_t __n)
"rep; movsl" \
x \
: "=&c" (__d0), "=&D" (__d1), "=&S" (__d2) \
: "0" (__n / 4), "1" (__dest), "2" (__src) \
: "0" (__n / 4), "1" (&__u->__uc), "2" (__src) \
: "memory");
switch (__n % 4)
@ -184,22 +190,28 @@ __STRING_INLINE void *
__memset_cc (void *__s, unsigned long int __pattern, size_t __n)
{
register unsigned long int __d0, __d1;
union {
unsigned int __ui;
unsigned short int __usi;
unsigned char __uc;
} *__u = __s;
switch (__n)
{
case 0:
return __s;
case 1:
*(unsigned char *) __s = __pattern;
__u->__uc = __pattern;
return __s;
case 2:
*(unsigned short int *) __s = __pattern;
__u->__usi = __pattern;
return __s;
case 3:
*(unsigned short int *) __s = __pattern;
*(2 + (unsigned char *) __s) = __pattern;
__u->__usi = __pattern;
__u = __extension__ ((void *) __u + 1);
__u->__uc = __pattern;
return __s;
case 4:
*(unsigned long *) __s = __pattern;
__u->__ui = __pattern;
return __s;
}
#define __COMMON_CODE(x) \
@ -208,7 +220,7 @@ __memset_cc (void *__s, unsigned long int __pattern, size_t __n)
"rep; stosl" \
x \
: "=&c" (__d0), "=&D" (__d1) \
: "a" (__pattern), "0" (__n / 4), "1" (__s) \
: "a" (__pattern), "0" (__n / 4), "1" (&__u->__uc) \
: "memory")
switch (__n % 4)

View File

@ -211,12 +211,17 @@ memcmp (__const void *__s1, __const void *__s2, size_t __n)
#define __memset_gc(s, c, n) \
({ void *__s = (s); \
unsigned int *__ts = (unsigned int *) __s; \
union { \
unsigned int __ui; \
unsigned short int __usi; \
unsigned char __uc; \
} *__u = __s; \
unsigned int __c = ((unsigned int) ((unsigned char) (c))) * 0x01010101; \
\
/* We apply a trick here. `gcc' would implement the following \
assignments using absolute operands. But this uses to much \
memory (7, instead of 4 bytes). */ \
assignments using immediate operands. But this uses to much \
memory (7, instead of 4 bytes). So we force the value in a \
registers. */ \
if (n == 3 || n >= 5) \
__asm__ __volatile__ ("" : "=r" (__c) : "0" (__c)); \
\
@ -224,44 +229,57 @@ memcmp (__const void *__s1, __const void *__s2, size_t __n)
switch (n) \
{ \
case 15: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 11: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 7: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 3: \
*((unsigned short int *) __ts)++ = (unsigned short int) __c; \
*((unsigned char *) __ts) = (unsigned char) __c; \
__u->__usi = (unsigned short int) __c; \
__u = (void *) __u + 2; \
__u->__uc = (unsigned char) __c; \
break; \
\
case 14: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 10: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 6: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 2: \
*((unsigned short int *) __ts) = (unsigned short int) __c; \
__u->__usi = (unsigned short int) __c; \
break; \
\
case 13: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 9: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 5: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 1: \
*((unsigned char *) __ts) = (unsigned char) __c; \
__u->__uc = (unsigned char) __c; \
break; \
\
case 16: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 12: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 8: \
*__ts++ = __c; \
__u->__ui = __c; \
__u = (void *) __u + 4; \
case 4: \
*__ts = __c; \
__u->__ui = __c; \
case 0: \
break; \
} \
@ -494,48 +512,50 @@ __strlen_g (__const char *__str)
: __strcpy_g (dest, src)))
#define __strcpy_small(dest, src, srclen) \
(__extension__ ({ unsigned char *__dest = (unsigned char *) (dest); \
(__extension__ ({ char *__dest = (dest); \
union { \
unsigned int __ui; \
unsigned short int __usi; \
unsigned char __uc; \
char __c; \
} *__u = (void *) __dest; \
switch (srclen) \
{ \
case 1: \
*__dest = '\0'; \
__u->__uc = '\0'; \
break; \
case 2: \
*((unsigned short int *) __dest) = \
__STRING_SMALL_GET16 (src, 0); \
__u->__usi = __STRING_SMALL_GET16 (src, 0); \
break; \
case 3: \
*((unsigned short int *) __dest) = \
__STRING_SMALL_GET16 (src, 0); \
*(__dest + 2) = '\0'; \
__u->__usi = __STRING_SMALL_GET16 (src, 0); \
__u = (void *) __u + 2; \
__u->__uc = '\0'; \
break; \
case 4: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
break; \
case 5: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*(__dest + 4) = '\0'; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__uc = '\0'; \
break; \
case 6: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned short int *) (__dest + 4)) = \
__STRING_SMALL_GET16 (src, 4); \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__usi = __STRING_SMALL_GET16 (src, 4); \
break; \
case 7: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned short int *) (__dest + 4)) = \
__STRING_SMALL_GET16 (src, 4); \
*(__dest + 6) = '\0'; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__usi = __STRING_SMALL_GET16 (src, 4); \
__u = (void *) __u + 2; \
__u->__uc = '\0'; \
break; \
case 8: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned int *) (__dest + 4)) = \
__STRING_SMALL_GET32 (src, 4); \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__ui = __STRING_SMALL_GET32 (src, 4); \
break; \
} \
(char *) __dest; }))
@ -583,56 +603,56 @@ __strcpy_g (char *__dest, __const char *__src)
# define stpcpy(dest, src) __stpcpy (dest, src)
# define __stpcpy_small(dest, src, srclen) \
(__extension__ ({ unsigned char *__dest = (unsigned char *) (dest); \
(__extension__ ({ union { \
unsigned int __ui; \
unsigned short int __usi; \
unsigned char __uc; \
char __c; \
} *__u = (void *) (dest); \
switch (srclen) \
{ \
case 1: \
*__dest = '\0'; \
__u->__uc = '\0'; \
break; \
case 2: \
*((unsigned short int *) __dest) = \
__STRING_SMALL_GET16 (src, 0); \
++__dest; \
__u->__usi = __STRING_SMALL_GET16 (src, 0); \
__u = (void *) __u + 1; \
break; \
case 3: \
*((unsigned short int *) __dest)++ = \
__STRING_SMALL_GET16 (src, 0); \
*__dest = '\0'; \
__u->__usi = __STRING_SMALL_GET16 (src, 0); \
__u = (void *) __u + 2; \
__u->__uc = '\0'; \
break; \
case 4: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
__dest += 3; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 3; \
break; \
case 5: \
*((unsigned int *) __dest)++ = \
__STRING_SMALL_GET32 (src, 0); \
*__dest = '\0'; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__uc = '\0'; \
break; \
case 6: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned short int *) (__dest + 4)) = \
__STRING_SMALL_GET16 (src, 4); \
__dest += 5; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__usi = __STRING_SMALL_GET16 (src, 4); \
__u = (void *) __u + 1; \
break; \
case 7: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned short int *) (__dest + 4)) = \
__STRING_SMALL_GET16 (src, 4); \
__dest += 6; \
*__dest = '\0'; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__usi = __STRING_SMALL_GET16 (src, 4); \
__u = (void *) __u + 2; \
__u->__uc = '\0'; \
break; \
case 8: \
*((unsigned int *) __dest) = \
__STRING_SMALL_GET32 (src, 0); \
*((unsigned int *) (__dest + 4)) = \
__STRING_SMALL_GET32 (src, 4); \
__dest += 7; \
__u->__ui = __STRING_SMALL_GET32 (src, 0); \
__u = (void *) __u + 4; \
__u->__ui = __STRING_SMALL_GET32 (src, 4); \
__u = (void *) __u + 3; \
break; \
} \
(char *) __dest; }))
(char *) __u; }))
__STRING_INLINE char *__mempcpy_by4 (char *__dest, __const char *__src,
size_t __srclen);