OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [newlib-1.18.0/] [newlib/] [libc/] [machine/] [microblaze/] [strcmp.c] - Blame information for rev 207

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 207 jeremybenn
/* Copyright (c) 2009 Xilinx, Inc.  All rights reserved.
2
 
3
   Redistribution and use in source and binary forms, with or without
4
   modification, are permitted provided that the following conditions are
5
   met:
6
 
7
   1.  Redistributions source code must retain the above copyright notice,
8
   this list of conditions and the following disclaimer.
9
 
10
   2.  Redistributions in binary form must reproduce the above copyright
11
   notice, this list of conditions and the following disclaimer in the
12
   documentation and/or other materials provided with the distribution.
13
 
14
   3.  Neither the name of Xilinx nor the names of its contributors may be
15
   used to endorse or promote products derived from this software without
16
   specific prior written permission.
17
 
18
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER AND CONTRIBUTORS "AS
19
   IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
20
   TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
21
   PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22
   HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23
   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
24
   TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
25
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
26
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
27
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
28
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
 
30
 
31
FUNCTION
32
        <<strcmp>>---character string compare
33
 
34
INDEX
35
        strcmp
36
 
37
ANSI_SYNOPSIS
38
        #include <string.h>
39
        int strcmp(const char *<[a]>, const char *<[b]>);
40
 
41
TRAD_SYNOPSIS
42
        #include <string.h>
43
        int strcmp(<[a]>, <[b]>)
44
        char *<[a]>;
45
        char *<[b]>;
46
 
47
DESCRIPTION
48
        <<strcmp>> compares the string at <[a]> to
49
        the string at <[b]>.
50
 
51
RETURNS
52
        If <<*<[a]>>> sorts lexicographically after <<*<[b]>>>,
53
        <<strcmp>> returns a number greater than zero.  If the two
54
        strings match, <<strcmp>> returns zero.  If <<*<[a]>>>
55
        sorts lexicographically before <<*<[b]>>>, <<strcmp>> returns a
56
        number less than zero.
57
 
58
PORTABILITY
59
<<strcmp>> is ANSI C.
60
 
61
<<strcmp>> requires no supporting OS subroutines.
62
 
63
QUICKREF
64
        strcmp ansi pure
65
*/
66
 
67
#include <string.h>
68
#include <limits.h>
69
 
70
/* Nonzero if either X or Y is not aligned on a "long" boundary.  */
71
#define UNALIGNED(X, Y) \
72
  (((long)X & (sizeof (long) - 1)) | ((long)Y & (sizeof (long) - 1)))
73
 
74
/* DETECTNULL returns nonzero if (long)X contains a NULL byte. */
75
#if LONG_MAX == 2147483647L
76
#define DETECTNULL(X) (((X) - 0x01010101) & ~(X) & 0x80808080)
77
#else
78
#if LONG_MAX == 9223372036854775807L
79
#define DETECTNULL(X) (((X) - 0x0101010101010101) & ~(X) & 0x8080808080808080)
80
#else
81
#error long int is not a 32bit or 64bit type.
82
#endif
83
#endif
84
 
85
#ifndef DETECTNULL
86
#error long int is not a 32bit or 64bit byte
87
#endif
88
 
89
int
90
_DEFUN (strcmp, (s1, s2),
91
        _CONST char *s1 _AND
92
        _CONST char *s2)
93
{
94
 
95
#ifndef HAVE_HW_PCMP
96
 
97
#if defined(PREFER_SIZE_OVER_SPEED) || defined(__OPTIMIZE_SIZE__)
98
  while (*s1 != '\0' && *s1 == *s2)
99
    {
100
      s1++;
101
      s2++;
102
    }
103
 
104
  return (*(unsigned char *) s1) - (*(unsigned char *) s2);
105
#else
106
  unsigned long *a1;
107
  unsigned long *a2;
108
 
109
  /* If s1 or s2 are unaligned, then compare bytes. */
110
  if (!UNALIGNED (s1, s2))
111
    {
112
      /* If s1 and s2 are word-aligned, compare them a word at a time. */
113
      a1 = (unsigned long*)s1;
114
      a2 = (unsigned long*)s2;
115
      while (*a1 == *a2)
116
        {
117
          /* To get here, *a1 == *a2, thus if we find a null in *a1,
118
             then the strings must be equal, so return zero.  */
119
          if (DETECTNULL (*a1))
120
            return 0;
121
 
122
          a1++;
123
          a2++;
124
        }
125
 
126
      /* A difference was detected in last few bytes of s1, so search bytewise */
127
      s1 = (char*)a1;
128
      s2 = (char*)a2;
129
    }
130
 
131
  while (*s1 != '\0' && *s1 == *s2)
132
    {
133
      s1++;
134
      s2++;
135
    }
136
  return (*(unsigned char *) s1) - (*(unsigned char *) s2);
137
#endif /* not PREFER_SIZE_OVER_SPEED */
138
 
139
#else
140
 
141
    asm volatile ("                                          \n\
142
       or      r9, r0, r0               /* Index register */ \n\
143
check_alignment:                                             \n\
144
        andi    r3, r5, 3                                    \n\
145
        andi    r4, r6, 3                                    \n\
146
        bnei    r3, try_align_args                           \n\
147
        bnei    r4, regular_strcmp     /* At this point we don't have a choice */ \n\
148
cmp_loop:                                                                       \n\
149
        lw      r3, r5, r9                                                      \n\
150
        lw      r4, r6, r9                                                      \n\
151
        pcmpbf  r7, r3, r0              /* See if there is Null byte */                         \n\
152
        bnei    r7, end_cmp_loop        /* IF yes (r7 > 0) use byte compares in end_cmp_loop */ \n\
153
        cmpu    r7, r4, r3              /* ELSE compare whole word */                   \n\
154
        bnei    r7, end_cmp                                                             \n\
155
        brid    cmp_loop                                                                \n\
156
        addik   r9, r9, 4               /* delay slot */                                \n\
157
end_cmp_loop:                                                                           \n\
158
        lbu     r3, r5, r9              /* byte compare loop */                         \n\
159
        lbu     r4, r6, r9                                                              \n\
160
        cmpu    r7, r4, r3              /* Compare bytes */                             \n\
161
        bnei    r7, end_cmp_early                                                       \n\
162
        bneid   r3, end_cmp_loop        /* If reached null on one string, terminate */  \n\
163
        addik   r9, r9, 1               /* delay slot */                        \n\
164
end_cmp_early:                                                                  \n\
165
        rtsd    r15, 8                                                          \n\
166
        or      r3, r0, r7                                                      \n\
167
try_align_args:                                                                 \n\
168
        xor     r7, r4, r3                                                      \n\
169
        bnei    r7, regular_strcmp      /* cannot align args */                 \n\
170
        rsubik  r10, r3, 4              /* Number of initial bytes to align */  \n\
171
align_loop:                                                                     \n\
172
        lbu     r3, r5, r9                                                      \n\
173
        lbu     r4, r6, r9                                                      \n\
174
        cmpu    r7, r4, r3                                                      \n\
175
        bnei    r7, end_cmp                                                     \n\
176
        beqi    r3, end_cmp                                                     \n\
177
        addik   r10, r10, -1                                                    \n\
178
        beqid   r10, cmp_loop                                                   \n\
179
        addik   r9, r9, 1                                                       \n\
180
        bri     align_loop                                                      \n\
181
regular_strcmp:                                                                 \n\
182
        lbu     r3, r5, r9                                                      \n\
183
        lbu     r4, r6, r9                                                      \n\
184
        cmpu    r7, r4, r3                                                      \n\
185
        bnei    r7, end_cmp                                                     \n\
186
        beqi    r3, end_cmp                                                     \n\
187
        brid    regular_strcmp                                                  \n\
188
        addik   r9, r9, 1                                                       \n\
189
end_cmp:                                                                        \n\
190
        rtsd    r15, 8                                                          \n\
191
        or      r3, r0, r7              /* Return strcmp result */");
192
 
193
#endif /* ! HAVE_HW_PCMP */
194
}
195
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.