annotate libphobos/libdruntime/rt/adi.d @ 158:494b0b89df80 default tip

...
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 25 May 2020 18:13:55 +0900
parents 1830386684a0
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
145
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
1 /**
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
2 * Implementation of dynamic array property support routines.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
3 *
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
4 * Copyright: Copyright Digital Mars 2000 - 2015.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
5 * License: Distributed under the
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
6 * $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost Software License 1.0).
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
7 * (See accompanying file LICENSE)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
8 * Authors: Walter Bright
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
9 * Source: $(DRUNTIMESRC src/rt/_adi.d)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
10 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
11
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
12 module rt.adi;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
13
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
14 //debug=adi; // uncomment to turn on debugging printf's
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
15
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
16 private
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
17 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
18 debug(adi) import core.stdc.stdio;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
19 import core.stdc.string;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
20 import core.stdc.stdlib;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
21 import core.memory;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
22 import rt.util.utf;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
23
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
24 extern (C) void[] _adSort(void[] a, TypeInfo ti);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
25 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
26
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
27 private dchar[] mallocUTF32(C)(in C[] s)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
28 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
29 size_t j = 0;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
30 auto p = cast(dchar*)malloc(dchar.sizeof * s.length);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
31 auto r = p[0..s.length]; // r[] will never be longer than s[]
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
32 foreach (dchar c; s)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
33 r[j++] = c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
34 return r[0 .. j];
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
35 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
36
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
37 /**********************************************
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
38 * Sort array of chars.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
39 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
40
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
41 extern (C) char[] _adSortChar(char[] a)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
42 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
43 if (a.length > 1)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
44 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
45 auto da = mallocUTF32(a);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
46 _adSort(*cast(void[]*)&da, typeid(da[0]));
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
47 size_t i = 0;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
48 foreach (dchar d; da)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
49 { char[4] buf;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
50 auto t = toUTF8(buf, d);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
51 a[i .. i + t.length] = t[];
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
52 i += t.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
53 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
54 free(da.ptr);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
55 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
56 return a;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
57 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
58
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
59 /**********************************************
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
60 * Sort array of wchars.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
61 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
62
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
63 extern (C) wchar[] _adSortWchar(wchar[] a)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
64 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
65 if (a.length > 1)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
66 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
67 auto da = mallocUTF32(a);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
68 _adSort(*cast(void[]*)&da, typeid(da[0]));
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
69 size_t i = 0;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
70 foreach (dchar d; da)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
71 { wchar[2] buf;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
72 auto t = toUTF16(buf, d);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
73 a[i .. i + t.length] = t[];
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
74 i += t.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
75 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
76 free(da.ptr);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
77 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
78 return a;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
79 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
80
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
81 /***************************************
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
82 * Support for array equality test.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
83 * Returns:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
84 * 1 equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
85 * 0 not equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
86 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
87
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
88 extern (C) int _adEq(void[] a1, void[] a2, TypeInfo ti)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
89 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
90 debug(adi) printf("_adEq(a1.length = %d, a2.length = %d)\n", a1.length, a2.length);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
91 if (a1.length != a2.length)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
92 return 0; // not equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
93 auto sz = ti.tsize;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
94 auto p1 = a1.ptr;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
95 auto p2 = a2.ptr;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
96
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
97 if (sz == 1)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
98 // We should really have a ti.isPOD() check for this
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
99 return (memcmp(p1, p2, a1.length) == 0);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
100
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
101 for (size_t i = 0; i < a1.length; i++)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
102 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
103 if (!ti.equals(p1 + i * sz, p2 + i * sz))
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
104 return 0; // not equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
105 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
106 return 1; // equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
107 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
108
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
109 extern (C) int _adEq2(void[] a1, void[] a2, TypeInfo ti)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
110 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
111 debug(adi) printf("_adEq2(a1.length = %d, a2.length = %d)\n", a1.length, a2.length);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
112 if (a1.length != a2.length)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
113 return 0; // not equal
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
114 if (!ti.equals(&a1, &a2))
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
115 return 0;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
116 return 1;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
117 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
118 unittest
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
119 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
120 debug(adi) printf("array.Eq unittest\n");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
121
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
122 auto a = "hello"c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
123
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
124 assert(a != "hel");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
125 assert(a != "helloo");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
126 assert(a != "betty");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
127 assert(a == "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
128 assert(a != "hxxxx");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
129
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
130 float[] fa = [float.nan];
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
131 assert(fa != fa);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
132 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
133
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
134 /***************************************
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
135 * Support for array compare test.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
136 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
137
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
138 extern (C) int _adCmp(void[] a1, void[] a2, TypeInfo ti)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
139 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
140 debug(adi) printf("adCmp()\n");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
141 auto len = a1.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
142 if (a2.length < len)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
143 len = a2.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
144 auto sz = ti.tsize;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
145 void *p1 = a1.ptr;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
146 void *p2 = a2.ptr;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
147
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
148 if (sz == 1)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
149 { // We should really have a ti.isPOD() check for this
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
150 auto c = memcmp(p1, p2, len);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
151 if (c)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
152 return c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
153 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
154 else
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
155 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
156 for (size_t i = 0; i < len; i++)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
157 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
158 auto c = ti.compare(p1 + i * sz, p2 + i * sz);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
159 if (c)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
160 return c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
161 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
162 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
163 if (a1.length == a2.length)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
164 return 0;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
165 return (a1.length > a2.length) ? 1 : -1;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
166 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
167
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
168 extern (C) int _adCmp2(void[] a1, void[] a2, TypeInfo ti)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
169 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
170 debug(adi) printf("_adCmp2(a1.length = %d, a2.length = %d)\n", a1.length, a2.length);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
171 return ti.compare(&a1, &a2);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
172 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
173 unittest
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
174 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
175 debug(adi) printf("array.Cmp unittest\n");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
176
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
177 auto a = "hello"c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
178
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
179 assert(a > "hel");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
180 assert(a >= "hel");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
181 assert(a < "helloo");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
182 assert(a <= "helloo");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
183 assert(a > "betty");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
184 assert(a >= "betty");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
185 assert(a == "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
186 assert(a <= "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
187 assert(a >= "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
188 assert(a < "я");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
189 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
190
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
191 /***************************************
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
192 * Support for array compare test.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
193 */
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
194
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
195 extern (C) int _adCmpChar(void[] a1, void[] a2)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
196 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
197 version (D_InlineAsm_X86)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
198 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
199 asm
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
200 { naked ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
201
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
202 push EDI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
203 push ESI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
204
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
205 mov ESI,a1+4[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
206 mov EDI,a2+4[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
207
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
208 mov ECX,a1[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
209 mov EDX,a2[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
210
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
211 cmp ECX,EDX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
212 jb GotLength ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
213
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
214 mov ECX,EDX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
215
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
216 GotLength:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
217 cmp ECX,4 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
218 jb DoBytes ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
219
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
220 // Do alignment if neither is dword aligned
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
221 test ESI,3 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
222 jz Aligned ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
223
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
224 test EDI,3 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
225 jz Aligned ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
226 DoAlign:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
227 mov AL,[ESI] ; //align ESI to dword bounds
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
228 mov DL,[EDI] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
229
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
230 cmp AL,DL ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
231 jnz Unequal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
232
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
233 inc ESI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
234 inc EDI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
235
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
236 test ESI,3 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
237
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
238 lea ECX,[ECX-1] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
239 jnz DoAlign ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
240 Aligned:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
241 mov EAX,ECX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
242
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
243 // do multiple of 4 bytes at a time
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
244
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
245 shr ECX,2 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
246 jz TryOdd ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
247
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
248 repe ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
249 cmpsd ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
250
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
251 jnz UnequalQuad ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
252
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
253 TryOdd:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
254 mov ECX,EAX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
255 DoBytes:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
256 // if still equal and not end of string, do up to 3 bytes slightly
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
257 // slower.
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
258
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
259 and ECX,3 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
260 jz Equal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
261
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
262 repe ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
263 cmpsb ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
264
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
265 jnz Unequal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
266 Equal:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
267 mov EAX,a1[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
268 mov EDX,a2[4+ESP] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
269
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
270 sub EAX,EDX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
271 pop ESI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
272
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
273 pop EDI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
274 ret ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
275
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
276 UnequalQuad:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
277 mov EDX,[EDI-4] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
278 mov EAX,[ESI-4] ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
279
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
280 cmp AL,DL ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
281 jnz Unequal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
282
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
283 cmp AH,DH ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
284 jnz Unequal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
285
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
286 shr EAX,16 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
287
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
288 shr EDX,16 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
289
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
290 cmp AL,DL ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
291 jnz Unequal ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
292
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
293 cmp AH,DH ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
294 Unequal:
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
295 sbb EAX,EAX ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
296 pop ESI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
297
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
298 or EAX,1 ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
299 pop EDI ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
300
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
301 ret ;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
302 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
303 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
304 else
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
305 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
306 debug(adi) printf("adCmpChar()\n");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
307 auto len = a1.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
308 if (a2.length < len)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
309 len = a2.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
310 auto c = memcmp(cast(char *)a1.ptr, cast(char *)a2.ptr, len);
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
311 if (!c)
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
312 c = cast(int)a1.length - cast(int)a2.length;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
313 return c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
314 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
315 }
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
316
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
317 unittest
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
318 {
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
319 debug(adi) printf("array.CmpChar unittest\n");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
320
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
321 auto a = "hello"c;
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
322
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
323 assert(a > "hel");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
324 assert(a >= "hel");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
325 assert(a < "helloo");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
326 assert(a <= "helloo");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
327 assert(a > "betty");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
328 assert(a >= "betty");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
329 assert(a == "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
330 assert(a <= "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
331 assert(a >= "hello");
1830386684a0 gcc-9.2.0
anatofuz
parents:
diff changeset
332 }