msvcp71: Added basic_string::append(iterator, iterator) implementation.
[wine/multimedia.git] / dlls / msvcp71 / msvcp71.c
blob07590515fb53e7d9b891a4d082229b10457fd1f3
1 /*
2 * msvcp71 specific functions
4 * Copyright 2010 Piotr Caban for CodeWeavers
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 #include "config.h"
23 #include <stdarg.h>
25 #include "windef.h"
26 #include "winbase.h"
27 #include "wine/unicode.h"
29 /* Copied from dlls/msvcrt/cpp.c */
30 #ifdef __i386__ /* thiscall functions are i386-specific */
32 #define THISCALL(func) __thiscall_ ## func
33 #define THISCALL_NAME(func) __ASM_NAME("__thiscall_" #func)
34 #define __thiscall __stdcall
35 #define DEFINE_THISCALL_WRAPPER(func,args) \
36 extern void THISCALL(func)(void); \
37 __ASM_GLOBAL_FUNC(__thiscall_ ## func, \
38 "popl %eax\n\t" \
39 "pushl %ecx\n\t" \
40 "pushl %eax\n\t" \
41 "jmp " __ASM_NAME(#func) __ASM_STDCALL(args) )
42 #else /* __i386__ */
44 #define THISCALL(func) func
45 #define THISCALL_NAME(func) __ASM_NAME(#func)
46 #define __thiscall __cdecl
47 #define DEFINE_THISCALL_WRAPPER(func,args) /* nothing */
49 #endif /* __i386__ */
51 /* Copied from dlls/msvcp90/msvcp90.h */
52 typedef SIZE_T MSVCP_size_t;
53 typedef unsigned short MSVCP_wchar_t;
55 #define BUF_SIZE_CHAR 16
56 typedef struct
58 void *allocator;
59 union {
60 char buf[BUF_SIZE_CHAR];
61 char *ptr;
62 } data;
63 MSVCP_size_t size;
64 MSVCP_size_t res;
65 } basic_string_char;
67 #define BUF_SIZE_WCHAR 8
68 typedef struct
70 void *allocator;
71 union {
72 MSVCP_wchar_t buf[BUF_SIZE_WCHAR];
73 MSVCP_wchar_t *ptr;
74 } data;
75 MSVCP_size_t size;
76 MSVCP_size_t res;
77 } basic_string_wchar;
79 basic_string_char* (__stdcall *pbasic_string_char_replace)(basic_string_char*,
80 MSVCP_size_t, MSVCP_size_t, const char*, MSVCP_size_t);
81 basic_string_wchar* (__stdcall *pbasic_string_wchar_replace)(basic_string_wchar*,
82 MSVCP_size_t, MSVCP_size_t, const MSVCP_wchar_t*, MSVCP_size_t);
84 typedef struct {
85 const char *pos;
86 } basic_string_char_iterator;
88 typedef struct {
89 const MSVCP_wchar_t *pos;
90 } basic_string_wchar_iterator;
92 static char* basic_string_char_ptr(basic_string_char *this)
94 if(this->res == BUF_SIZE_CHAR-1)
95 return this->data.buf;
96 return this->data.ptr;
99 static MSVCP_wchar_t* basic_string_wchar_ptr(basic_string_wchar *this)
101 if(this->res == BUF_SIZE_WCHAR-1)
102 return this->data.buf;
103 return this->data.ptr;
106 /* ?begin@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE?AViterator@12@XZ */
107 /* ?begin@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBE?AVconst_iterator@12@XZ */
108 /* ?rend@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@XZ */
109 /* ?rend@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@XZ */
110 DEFINE_THISCALL_WRAPPER(basic_string_char_begin, 8)
111 basic_string_char_iterator* __thiscall basic_string_char_begin(
112 basic_string_char *this, basic_string_char_iterator *ret)
114 ret->pos = basic_string_char_ptr(this);
115 return ret;
118 /* ?end@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE?AViterator@12@XZ */
119 /* ?end@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBE?AVconst_iterator@12@XZ */
120 /* ?rbegin@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@XZ */
121 /* ?rbegin@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@@2@XZ */
122 DEFINE_THISCALL_WRAPPER(basic_string_char_end, 8)
123 basic_string_char_iterator* __thiscall basic_string_char_end(
124 basic_string_char *this, basic_string_char_iterator *ret)
126 ret->pos = basic_string_char_ptr(this)+this->size;
127 return ret;
130 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0ABV12@@Z */
131 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_bstr, 16)
132 basic_string_char* __thiscall basic_string_char_replace_iter_bstr(basic_string_char *this,
133 basic_string_char_iterator beg, basic_string_char_iterator end, basic_string_char *str)
135 return pbasic_string_char_replace(this, beg.pos-basic_string_char_ptr(this),
136 end.pos-beg.pos, basic_string_char_ptr(str), str->size);
139 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0ID@Z */
140 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_ch, 20)
141 basic_string_char* __thiscall basic_string_char_replace_iter_ch(basic_string_char *this,
142 basic_string_char_iterator beg, basic_string_char_iterator end, MSVCP_size_t count, char ch)
144 /* TODO: add more efficient implementation */
145 MSVCP_size_t off = beg.pos-basic_string_char_ptr(this);
147 pbasic_string_char_replace(this, off, end.pos-beg.pos, NULL, 0);
148 while(count--)
149 pbasic_string_char_replace(this, off, 0, &ch, 1);
150 return this;
153 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0PBD1@Z */
154 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_beg_end, 20)
155 basic_string_char* __thiscall basic_string_char_replace_iter_beg_end(basic_string_char *this,
156 basic_string_char_iterator beg, basic_string_char_iterator end, const char *rbeg, const char *rend)
158 return pbasic_string_char_replace(this, beg.pos-basic_string_char_ptr(this),
159 end.pos-beg.pos, rbeg, rend-rbeg);
162 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0PBD@Z */
163 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_cstr, 16)
164 basic_string_char* __thiscall basic_string_char_replace_iter_cstr(basic_string_char *this,
165 basic_string_char_iterator beg, basic_string_char_iterator end, const char *str)
167 return pbasic_string_char_replace(this, beg.pos-basic_string_char_ptr(this),
168 end.pos-beg.pos, str, strlen(str));
171 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0PBDI@Z */
172 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_cstr_len, 20)
173 basic_string_char* __thiscall basic_string_char_replace_iter_cstr_len(basic_string_char *this,
174 basic_string_char_iterator beg, basic_string_char_iterator end, const char *str, MSVCP_size_t len)
176 return pbasic_string_char_replace(this, beg.pos-basic_string_char_ptr(this),
177 end.pos-beg.pos, str, len);
180 /* ?replace@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Viterator@12@0Vconst_iterator@12@1@Z */
181 DEFINE_THISCALL_WRAPPER(basic_string_char_replace_iter_iter, 20)
182 basic_string_char* __thiscall basic_string_char_replace_iter_iter(basic_string_char *this,
183 basic_string_char_iterator beg, basic_string_char_iterator end,
184 basic_string_char_iterator rbeg, basic_string_char_iterator rend)
186 return pbasic_string_char_replace(this, beg.pos-basic_string_char_ptr(this),
187 end.pos-beg.pos, rbeg.pos, rend.pos-rbeg.pos);
190 /* ?append@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@Vconst_iterator@12@0@Z */
191 DEFINE_THISCALL_WRAPPER(basic_string_char_append_iter, 12)
192 basic_string_char* __thiscall basic_string_char_append_iter(basic_string_char *this,
193 basic_string_char_iterator beg, basic_string_char_iterator end)
195 return pbasic_string_char_replace(this, this->size, 0, beg.pos, end.pos-beg.pos);
198 /* ?begin@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAE?AViterator@12@XZ */
199 /* ?begin@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QBE?AVconst_iterator@12@XZ */
200 /* ?begin@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAE?AViterator@12@XZ */
201 /* ?begin@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QBE?AVconst_iterator@12@XZ */
202 /* ?rend@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@@2@XZ */
203 /* ?rend@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@@2@XZ */
204 /* ?rend@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@@2@XZ */
205 /* ?rend@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@@2@XZ */
206 DEFINE_THISCALL_WRAPPER(basic_string_wchar_begin, 8)
207 basic_string_wchar_iterator* __thiscall basic_string_wchar_begin(
208 basic_string_wchar *this, basic_string_wchar_iterator *ret)
210 ret->pos = basic_string_wchar_ptr(this);
211 return ret;
214 /* ?end@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAE?AViterator@12@XZ */
215 /* ?end@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QBE?AVconst_iterator@12@XZ */
216 /* ?end@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAE?AViterator@12@XZ */
217 /* ?end@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QBE?AVconst_iterator@12@XZ */
218 /* ?rbegin@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@@2@XZ */
219 /* ?rbegin@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@@2@XZ */
220 /* ?rbegin@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAE?AV?$reverse_iterator@Viterator@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@@2@XZ */
221 /* ?rbegin@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QBE?AV?$reverse_iterator@Vconst_iterator@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@@2@XZ */
222 DEFINE_THISCALL_WRAPPER(basic_string_wchar_end, 8)
223 basic_string_wchar_iterator* __thiscall basic_string_wchar_end(
224 basic_string_wchar *this, basic_string_wchar_iterator *ret)
226 ret->pos = basic_string_wchar_ptr(this)+this->size;
227 return ret;
230 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0ABV12@@Z */
231 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0ABV12@@Z */
232 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_bstr, 16)
233 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_bstr(basic_string_wchar *this,
234 basic_string_wchar_iterator beg, basic_string_wchar_iterator end, basic_string_wchar *str)
236 return pbasic_string_wchar_replace(this, beg.pos-basic_string_wchar_ptr(this),
237 end.pos-beg.pos, basic_string_wchar_ptr(str), str->size);
240 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0IG@Z */
241 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0I_W@Z */
242 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_ch, 20)
243 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_ch(basic_string_wchar *this,
244 basic_string_wchar_iterator beg, basic_string_wchar_iterator end, MSVCP_size_t count, MSVCP_wchar_t ch)
246 /* TODO: add more efficient implementation */
247 MSVCP_size_t off = beg.pos-basic_string_wchar_ptr(this);
249 pbasic_string_wchar_replace(this, off, end.pos-beg.pos, NULL, 0);
250 while(count--)
251 pbasic_string_wchar_replace(this, off, 0, &ch, 1);
252 return this;
255 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0PBG1@Z */
256 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0PB_W1@Z */
257 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_beg_end, 20)
258 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_beg_end(basic_string_wchar *this,
259 basic_string_wchar_iterator beg, basic_string_wchar_iterator end,
260 const MSVCP_wchar_t *rbeg, const MSVCP_wchar_t *rend)
262 return pbasic_string_wchar_replace(this, beg.pos-basic_string_wchar_ptr(this),
263 end.pos-beg.pos, rbeg, rend-rbeg);
266 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0PBG@Z */
267 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0PB_W@Z */
268 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_cstr, 16)
269 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_cstr(basic_string_wchar *this,
270 basic_string_wchar_iterator beg, basic_string_wchar_iterator end, const MSVCP_wchar_t *str)
272 return pbasic_string_wchar_replace(this, beg.pos-basic_string_wchar_ptr(this),
273 end.pos-beg.pos, str, strlenW(str));
276 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0PBGI@Z */
277 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0PB_WI@Z */
278 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_cstr_len, 20)
279 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_cstr_len(basic_string_wchar *this,
280 basic_string_wchar_iterator beg, basic_string_wchar_iterator end,
281 const MSVCP_wchar_t *str, MSVCP_size_t len)
283 return pbasic_string_wchar_replace(this, beg.pos-basic_string_wchar_ptr(this),
284 end.pos-beg.pos, str, len);
287 /* ?replace@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Viterator@12@0Vconst_iterator@12@1@Z */
288 /* ?replace@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Viterator@12@0Vconst_iterator@12@1@Z */
289 DEFINE_THISCALL_WRAPPER(basic_string_wchar_replace_iter_iter, 20)
290 basic_string_wchar* __thiscall basic_string_wchar_replace_iter_iter(basic_string_wchar *this,
291 basic_string_wchar_iterator beg, basic_string_wchar_iterator end,
292 basic_string_wchar_iterator rbeg, basic_string_wchar_iterator rend)
294 return pbasic_string_wchar_replace(this, beg.pos-basic_string_wchar_ptr(this),
295 end.pos-beg.pos, rbeg.pos, rend.pos-rbeg.pos);
298 /* ?append@?$basic_string@GU?$char_traits@G@std@@V?$allocator@G@2@@std@@QAEAAV12@Vconst_iterator@12@0@Z */
299 /* ?append@?$basic_string@_WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@QAEAAV12@Vconst_iterator@12@0@Z */
300 DEFINE_THISCALL_WRAPPER(basic_string_wchar_append_iter, 12)
301 basic_string_wchar* __thiscall basic_string_wchar_append_iter(basic_string_wchar *this,
302 basic_string_wchar_iterator beg, basic_string_wchar_iterator end)
304 return pbasic_string_wchar_replace(this, this->size, 0, beg.pos, end.pos-beg.pos);
307 static BOOL init_funcs(void)
309 HMODULE hmod = GetModuleHandleA("msvcp90.dll");
310 if(!hmod)
311 return FALSE;
313 pbasic_string_char_replace = (void*)GetProcAddress(hmod, "basic_string_char_replace_helper");
314 pbasic_string_wchar_replace = (void*)GetProcAddress(hmod, "basic_string_wchar_replace_helper");
316 return pbasic_string_char_replace && pbasic_string_wchar_replace;
319 BOOL WINAPI DllMain(HINSTANCE hdll, DWORD reason, LPVOID reserved)
321 switch (reason)
323 case DLL_WINE_PREATTACH:
324 return FALSE; /* prefer native version */
326 case DLL_PROCESS_ATTACH:
327 DisableThreadLibraryCalls(hdll);
328 if(!init_funcs())
329 return FALSE;
331 return TRUE;