Rev 519 | Rev 750 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 519 | Rev 593 | ||
---|---|---|---|
1 | $Revision: 431 $ |
- | |
2 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
3 | ;; ;; |
2 | ;; ;; |
4 | ;; Copyright (C) KolibriOS team 2004-2007. All rights reserved. ;; |
3 | ;; Copyright (C) KolibriOS team 2004-2007. All rights reserved. ;; |
5 | ;; Distributed under terms of the GNU General Public License ;; |
4 | ;; Distributed under terms of the GNU General Public License ;; |
6 | ;; Author: Kees J. Bot 1 Jan 1994 ;; |
5 | ;; Author: Kees J. Bot 1 Jan 1994 ;; |
7 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
6 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
- | 7 | ||
- | 8 | $Revision: 431 $ |
|
8 | 9 | ||
9 | 10 | ||
10 | ; size_t strncat(char *s1, const char *s2, size_t n) |
11 | ; size_t strncat(char *s1, const char *s2, size_t n) |
11 | ; Append string s2 to s1. |
12 | ; Append string s2 to s1. |
12 | 13 | ||
13 | ; char *strchr(const char *s, int c) |
14 | ; char *strchr(const char *s, int c) |
14 | 15 | ||
15 | 16 | ||
16 | ; int strncmp(const char *s1, const char *s2, size_t n) |
17 | ; int strncmp(const char *s1, const char *s2, size_t n) |
17 | ; Compare two strings. |
18 | ; Compare two strings. |
18 | 19 | ||
19 | ; char *strncpy(char *s1, const char *s2, size_t n) |
20 | ; char *strncpy(char *s1, const char *s2, size_t n) |
20 | ; Copy string s2 to s1. |
21 | ; Copy string s2 to s1. |
21 | 22 | ||
22 | ; size_t strnlen(const char *s, size_t n) |
23 | ; size_t strnlen(const char *s, size_t n) |
23 | ; Return the length of a string. |
24 | ; Return the length of a string. |
24 | 25 | ||
25 | ; proc strrchr stdcall, s:dword, c:dword |
26 | ; proc strrchr stdcall, s:dword, c:dword |
26 | ; Look for the last occurrence a character in a string. |
27 | ; Look for the last occurrence a character in a string. |
27 | 28 | ||
28 | proc strncat stdcall, s1:dword, s2:dword, n:dword |
29 | proc strncat stdcall, s1:dword, s2:dword, n:dword |
29 | push esi |
30 | push esi |
30 | push edi |
31 | push edi |
31 | mov edi, [s1] ; String s1 |
32 | mov edi, [s1] ; String s1 |
32 | mov edx, [n] ; Maximum length |
33 | mov edx, [n] ; Maximum length |
33 | 34 | ||
34 | mov ecx, -1 |
35 | mov ecx, -1 |
35 | xor al, al ; Null byte |
36 | xor al, al ; Null byte |
36 | cld |
37 | cld |
37 | repne scasb ; Look for the zero byte in s1 |
38 | repne scasb ; Look for the zero byte in s1 |
38 | dec edi ; Back one up (and clear 'Z' flag) |
39 | dec edi ; Back one up (and clear 'Z' flag) |
39 | push edi ; Save end of s1 |
40 | push edi ; Save end of s1 |
40 | mov edi, [s2] ; edi = string s2 |
41 | mov edi, [s2] ; edi = string s2 |
41 | mov ecx, edx ; Maximum count |
42 | mov ecx, edx ; Maximum count |
42 | repne scasb ; Look for the end of s2 |
43 | repne scasb ; Look for the end of s2 |
43 | jne @F |
44 | jne @F |
44 | inc ecx ; Exclude null byte |
45 | inc ecx ; Exclude null byte |
45 | @@: |
46 | @@: |
46 | sub edx, ecx ; Number of bytes in s2 |
47 | sub edx, ecx ; Number of bytes in s2 |
47 | mov ecx, edx |
48 | mov ecx, edx |
48 | mov esi, [s2] ; esi = string s2 |
49 | mov esi, [s2] ; esi = string s2 |
49 | pop edi ; edi = end of string s1 |
50 | pop edi ; edi = end of string s1 |
50 | rep movsb ; Copy bytes |
51 | rep movsb ; Copy bytes |
51 | stosb ; Add a terminating null |
52 | stosb ; Add a terminating null |
52 | mov eax, [s1] ; Return s1 |
53 | mov eax, [s1] ; Return s1 |
53 | pop edi |
54 | pop edi |
54 | pop esi |
55 | pop esi |
55 | ret |
56 | ret |
56 | endp |
57 | endp |
57 | 58 | ||
58 | align 4 |
59 | align 4 |
59 | proc strncmp stdcall, s1:dword, s2:dword, n:dword |
60 | proc strncmp stdcall, s1:dword, s2:dword, n:dword |
60 | 61 | ||
61 | push esi |
62 | push esi |
62 | push edi |
63 | push edi |
63 | mov ecx, [n] |
64 | mov ecx, [n] |
64 | test ecx, ecx ; Max length is zero? |
65 | test ecx, ecx ; Max length is zero? |
65 | je .done |
66 | je .done |
66 | 67 | ||
67 | mov esi, [s1] ; esi = string s1 |
68 | mov esi, [s1] ; esi = string s1 |
68 | mov edi, [s2] ; edi = string s2 |
69 | mov edi, [s2] ; edi = string s2 |
69 | cld |
70 | cld |
70 | .compare: |
71 | .compare: |
71 | cmpsb ; Compare two bytes |
72 | cmpsb ; Compare two bytes |
72 | jne .done |
73 | jne .done |
73 | cmp byte [esi-1], 0 ; End of string? |
74 | cmp byte [esi-1], 0 ; End of string? |
74 | je .done |
75 | je .done |
75 | dec ecx ; Length limit reached? |
76 | dec ecx ; Length limit reached? |
76 | jne .compare |
77 | jne .compare |
77 | .done: |
78 | .done: |
78 | seta al ; al = (s1 > s2) |
79 | seta al ; al = (s1 > s2) |
79 | setb ah ; ah = (s1 < s2) |
80 | setb ah ; ah = (s1 < s2) |
80 | sub al, ah |
81 | sub al, ah |
81 | movsx eax, al ; eax = (s1 > s2) - (s1 < s2), i.e. -1, 0, 1 |
82 | movsx eax, al ; eax = (s1 > s2) - (s1 < s2), i.e. -1, 0, 1 |
82 | pop edi |
83 | pop edi |
83 | pop esi |
84 | pop esi |
84 | ret |
85 | ret |
85 | endp |
86 | endp |
86 | 87 | ||
87 | align 4 |
88 | align 4 |
88 | proc strncpy stdcall, s1:dword, s2:dword, n:dword |
89 | proc strncpy stdcall, s1:dword, s2:dword, n:dword |
89 | 90 | ||
90 | push esi |
91 | push esi |
91 | push edi |
92 | push edi |
92 | 93 | ||
93 | mov ecx, [n] ; Maximum length |
94 | mov ecx, [n] ; Maximum length |
94 | mov edi, [s2] ; edi = string s2 |
95 | mov edi, [s2] ; edi = string s2 |
95 | xor al, al ; Look for a zero byte |
96 | xor al, al ; Look for a zero byte |
96 | mov edx, ecx ; Save maximum count |
97 | mov edx, ecx ; Save maximum count |
97 | cld |
98 | cld |
98 | repne scasb ; Look for end of s2 |
99 | repne scasb ; Look for end of s2 |
99 | sub edx, ecx ; Number of bytes in s2 including null |
100 | sub edx, ecx ; Number of bytes in s2 including null |
100 | xchg ecx, edx |
101 | xchg ecx, edx |
101 | mov esi, [s2] ; esi = string s2 |
102 | mov esi, [s2] ; esi = string s2 |
102 | mov edi, [s1] ; edi = string s1 |
103 | mov edi, [s1] ; edi = string s1 |
103 | rep movsb ; Copy bytes |
104 | rep movsb ; Copy bytes |
104 | 105 | ||
105 | mov ecx, edx ; Number of bytes not copied |
106 | mov ecx, edx ; Number of bytes not copied |
106 | rep stosb ; strncpy always copies n bytes by null padding |
107 | rep stosb ; strncpy always copies n bytes by null padding |
107 | mov eax, [s1] ; Return s1 |
108 | mov eax, [s1] ; Return s1 |
108 | pop edi |
109 | pop edi |
109 | pop esi |
110 | pop esi |
110 | ret |
111 | ret |
111 | endp |
112 | endp |
112 | 113 | ||
113 | align 4 |
114 | align 4 |
114 | proc strnlen stdcall, s:dword, n:dword |
115 | proc strnlen stdcall, s:dword, n:dword |
115 | 116 | ||
116 | push edi |
117 | push edi |
117 | mov edi, [s] ; edi = string |
118 | mov edi, [s] ; edi = string |
118 | xor al, al ; Look for a zero byte |
119 | xor al, al ; Look for a zero byte |
119 | mov edx, ecx ; Save maximum count |
120 | mov edx, ecx ; Save maximum count |
120 | cmp cl, 1 ; 'Z' bit must be clear if ecx = 0 |
121 | cmp cl, 1 ; 'Z' bit must be clear if ecx = 0 |
121 | cld |
122 | cld |
122 | repne scasb ; Look for zero |
123 | repne scasb ; Look for zero |
123 | jne @F |
124 | jne @F |
124 | inc ecx ; Don't count zero byte |
125 | inc ecx ; Don't count zero byte |
125 | @@: |
126 | @@: |
126 | mov eax, edx |
127 | mov eax, edx |
127 | sub eax, ecx ; Compute bytes scanned |
128 | sub eax, ecx ; Compute bytes scanned |
128 | pop edi |
129 | pop edi |
129 | ret |
130 | ret |
130 | endp |
131 | endp |
131 | 132 | ||
132 | align 4 |
133 | align 4 |
133 | proc strchr stdcall, s:dword, c:dword |
134 | proc strchr stdcall, s:dword, c:dword |
134 | push edi |
135 | push edi |
135 | cld |
136 | cld |
136 | mov edi, [s] ; edi = string |
137 | mov edi, [s] ; edi = string |
137 | mov edx, 16 ; Look at small chunks of the string |
138 | mov edx, 16 ; Look at small chunks of the string |
138 | .next: |
139 | .next: |
139 | shl edx, 1 ; Chunks become bigger each time |
140 | shl edx, 1 ; Chunks become bigger each time |
140 | mov ecx, edx |
141 | mov ecx, edx |
141 | xor al, al ; Look for the zero at the end |
142 | xor al, al ; Look for the zero at the end |
142 | repne scasb |
143 | repne scasb |
143 | pushf ; Remember the flags |
144 | pushf ; Remember the flags |
144 | sub ecx, edx |
145 | sub ecx, edx |
145 | neg ecx ; Some or all of the chunk |
146 | neg ecx ; Some or all of the chunk |
146 | sub edi, ecx ; Step back |
147 | sub edi, ecx ; Step back |
147 | mov eax, [c] ; The character to look for |
148 | mov eax, [c] ; The character to look for |
148 | repne scasb |
149 | repne scasb |
149 | je .found |
150 | je .found |
150 | popf ; Did we find the end of string earlier? |
151 | popf ; Did we find the end of string earlier? |
151 | jne .next ; No, try again |
152 | jne .next ; No, try again |
152 | xor eax, eax ; Return NULL |
153 | xor eax, eax ; Return NULL |
153 | pop edi |
154 | pop edi |
154 | ret |
155 | ret |
155 | .found: |
156 | .found: |
156 | pop eax ; Get rid of those flags |
157 | pop eax ; Get rid of those flags |
157 | lea eax, [edi-1] ; Address of byte found |
158 | lea eax, [edi-1] ; Address of byte found |
158 | pop edi |
159 | pop edi |
159 | ret |
160 | ret |
160 | 161 | ||
161 | endp |
162 | endp |
162 | 163 | ||
163 | 164 | ||
164 | proc strrchr stdcall, s:dword, c:dword |
165 | proc strrchr stdcall, s:dword, c:dword |
165 | push edi |
166 | push edi |
166 | mov edi, [s] ; edi = string |
167 | mov edi, [s] ; edi = string |
167 | mov ecx, -1 |
168 | mov ecx, -1 |
168 | xor al, al |
169 | xor al, al |
169 | cld |
170 | cld |
170 | repne scasb ; Look for the end of the string |
171 | repne scasb ; Look for the end of the string |
171 | not ecx ; -1 - ecx = Length of the string + null |
172 | not ecx ; -1 - ecx = Length of the string + null |
172 | dec edi ; Put edi back on the zero byte |
173 | dec edi ; Put edi back on the zero byte |
173 | mov eax, [c] ; The character to look for |
174 | mov eax, [c] ; The character to look for |
174 | std ; Downwards search |
175 | std ; Downwards search |
175 | repne scasb |
176 | repne scasb |
176 | cld ; Direction bit back to default |
177 | cld ; Direction bit back to default |
177 | jne .fail |
178 | jne .fail |
178 | lea eax, [edi+1] ; Found it |
179 | lea eax, [edi+1] ; Found it |
179 | pop edi |
180 | pop edi |
180 | ret |
181 | ret |
181 | .fail: |
182 | .fail: |
182 | xor eax, eax ; Not there |
183 | xor eax, eax ; Not there |
183 | pop edi |
184 | pop edi |
184 | ret |
185 | ret |
185 | endp>> |
186 | endp>> |