VirtualBox

source: vbox/trunk/src/VBox/VMM/VMMGC/EMGCA.asm@ 11347

Last change on this file since 11347 was 9247, checked in by vboxsync, 17 years ago

Fixed broken cmpxchg8b emulation.

  • Property svn:eol-style set to native
File size: 12.7 KB
Line 
1; $Id: EMAllA.asm 20278 2007-04-09 11:56:29Z sandervl $
2;; @file
3; EM Assembly Routines.
4;
5
6;
7; Copyright (C) 2006-2007 Sun Microsystems, Inc.
8;
9; This file is part of VirtualBox Open Source Edition (OSE), as
10; available from http://www.virtualbox.org. This file is free software;
11; you can redistribute it and/or modify it under the terms of the GNU
12; General Public License (GPL) as published by the Free Software
13; Foundation, in version 2 as it comes in the "COPYING" file of the
14; VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15; hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16;
17; Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
18; Clara, CA 95054 USA or visit http://www.sun.com if you need
19; additional information or have any questions.
20;
21
22;*******************************************************************************
23;* Header Files *
24;*******************************************************************************
25%include "VBox/asmdefs.mac"
26%include "VBox/err.mac"
27%include "VBox/x86.mac"
28
29BEGINCODE
30
31;;
32; Emulate LOCK CMPXCHG instruction, CDECL calling conv.
33; EMGCDECL(uint32_t) EMGCEmulateLockCmpXchg(RTGCPTR pu32Param1, uint32_t *pu32Param2, uint32_t u32Param3, size_t cbSize, uint32_t *pEflags);
34;
35; @returns eax=0 if data written, other code - invalid access, #PF was generated.
36; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
37; @param [esp + 08h] Param 2 - Second parameter - pointer to second parameter (eax)
38; @param [esp + 0ch] Param 3 - Third parameter - third parameter
39; @param [esp + 10h] Param 4 - Size of parameters, only 1/2/4 is valid.
40; @param [esp + 14h] Param 4 - Pointer to eflags (out)
41; @uses eax, ecx, edx
42;
43align 16
44BEGINPROC EMGCEmulateLockCmpXchg
45 push ebx
46 mov ecx, [esp + 04h + 4] ; ecx = first parameter
47 mov ebx, [esp + 08h + 4] ; ebx = 2nd parameter (eax)
48 mov edx, [esp + 0ch + 4] ; edx = third parameter
49 mov eax, [esp + 10h + 4] ; eax = size of parameters
50
51 cmp al, 4
52 je short .do_dword ; 4 bytes variant
53 cmp al, 2
54 je short .do_word ; 2 byte variant
55 cmp al, 1
56 je short .do_byte ; 1 bytes variant
57 int3
58
59.do_dword:
60 ; load 2nd parameter's value
61 mov eax, dword [ebx]
62
63 lock cmpxchg dword [ecx], edx ; do 4 bytes CMPXCHG
64 mov dword [ebx], eax
65 jmp short .done
66
67.do_word:
68 ; load 2nd parameter's value
69 mov eax, dword [ebx]
70
71 lock cmpxchg word [ecx], dx ; do 2 bytes CMPXCHG
72 mov word [ebx], ax
73 jmp short .done
74
75.do_byte:
76 ; load 2nd parameter's value
77 mov eax, dword [ebx]
78
79 lock cmpxchg byte [ecx], dl ; do 1 bytes CMPXCHG
80 mov byte [ebx], al
81
82.done:
83 ; collect flags and return.
84 pushf
85 pop eax
86
87 mov edx, [esp + 14h + 4] ; eflags pointer
88 mov dword [edx], eax
89
90 pop ebx
91 mov eax, VINF_SUCCESS
92 retn
93
94; Read error - we will be here after our page fault handler.
95GLOBALNAME EMGCEmulateLockCmpXchg_Error
96 pop ebx
97 mov eax, VERR_ACCESS_DENIED
98 ret
99
100ENDPROC EMGCEmulateLockCmpXchg
101
102;;
103; Emulate CMPXCHG instruction, CDECL calling conv.
104; EMGCDECL(uint32_t) EMGCEmulateCmpXchg(RTGCPTR pu32Param1, uint32_t *pu32Param2, uint32_t u32Param3, size_t cbSize, uint32_t *pEflags);
105;
106; @returns eax=0 if data written, other code - invalid access, #PF was generated.
107; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
108; @param [esp + 08h] Param 2 - Second parameter - pointer to second parameter (eax)
109; @param [esp + 0ch] Param 3 - Third parameter - third parameter
110; @param [esp + 10h] Param 4 - Size of parameters, only 1/2/4 is valid.
111; @param [esp + 14h] Param 4 - Pointer to eflags (out)
112; @uses eax, ecx, edx
113;
114align 16
115BEGINPROC EMGCEmulateCmpXchg
116 push ebx
117 mov ecx, [esp + 04h + 4] ; ecx = first parameter
118 mov ebx, [esp + 08h + 4] ; ebx = 2nd parameter (eax)
119 mov edx, [esp + 0ch + 4] ; edx = third parameter
120 mov eax, [esp + 10h + 4] ; eax = size of parameters
121
122 cmp al, 4
123 je short .do_dword ; 4 bytes variant
124 cmp al, 2
125 je short .do_word ; 2 byte variant
126 cmp al, 1
127 je short .do_byte ; 1 bytes variant
128 int3
129
130.do_dword:
131 ; load 2nd parameter's value
132 mov eax, dword [ebx]
133
134 cmpxchg dword [ecx], edx ; do 4 bytes CMPXCHG
135 mov dword [ebx], eax
136 jmp short .done
137
138.do_word:
139 ; load 2nd parameter's value
140 mov eax, dword [ebx]
141
142 cmpxchg word [ecx], dx ; do 2 bytes CMPXCHG
143 mov word [ebx], ax
144 jmp short .done
145
146.do_byte:
147 ; load 2nd parameter's value
148 mov eax, dword [ebx]
149
150 cmpxchg byte [ecx], dl ; do 1 bytes CMPXCHG
151 mov byte [ebx], al
152
153.done:
154 ; collect flags and return.
155 pushf
156 pop eax
157
158 mov edx, [esp + 14h + 4] ; eflags pointer
159 mov dword [edx], eax
160
161 pop ebx
162 mov eax, VINF_SUCCESS
163 retn
164
165; Read error - we will be here after our page fault handler.
166GLOBALNAME EMGCEmulateCmpXchg_Error
167 pop ebx
168 mov eax, VERR_ACCESS_DENIED
169 ret
170ENDPROC EMGCEmulateCmpXchg
171
172;;
173; Emulate LOCK CMPXCHG8B instruction, CDECL calling conv.
174; EMGCDECL(uint32_t) EMGCEmulateLockCmpXchg8b(RTGCPTR pu32Param1, uint32_t *pEAX, uint32_t *pEDX, uint32_t uEBX, uint32_t uECX, uint32_t *pEflags);
175;
176; @returns eax=0 if data written, other code - invalid access, #PF was generated.
177; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
178; @param [esp + 08h] Param 2 - Address of the eax register
179; @param [esp + 0ch] Param 3 - Address of the edx register
180; @param [esp + 10h] Param 4 - EBX
181; @param [esp + 14h] Param 5 - ECX
182; @param [esp + 18h] Param 6 - Pointer to eflags (out)
183; @uses eax, ecx, edx
184;
185align 16
186BEGINPROC EMGCEmulateLockCmpXchg8b
187 push ebp
188 push ebx
189 mov ebp, [esp + 04h + 8] ; ebp = first parameter
190 mov eax, [esp + 08h + 8] ; &EAX
191 mov eax, dword [eax]
192 mov edx, [esp + 0ch + 8] ; &EDX
193 mov edx, dword [edx]
194 mov ebx, [esp + 10h + 8] ; EBX
195 mov ecx, [esp + 14h + 8] ; ECX
196
197%ifdef RT_OS_OS2
198 lock cmpxchg8b [ebp] ; do CMPXCHG8B
199%else
200 lock cmpxchg8b qword [ebp] ; do CMPXCHG8B
201%endif
202 mov ebx, dword [esp + 08h + 8]
203 mov dword [ebx], eax
204 mov ebx, dword [esp + 0ch + 8]
205 mov dword [ebx], edx
206
207 ; collect flags and return.
208 pushf
209 pop eax
210
211 mov edx, [esp + 18h + 8] ; eflags pointer
212 mov dword [edx], eax
213
214 pop ebx
215 pop ebp
216 mov eax, VINF_SUCCESS
217 retn
218
219; Read error - we will be here after our page fault handler.
220GLOBALNAME EMGCEmulateLockCmpXchg8b_Error
221 pop ebx
222 pop ebp
223 mov eax, VERR_ACCESS_DENIED
224 ret
225
226ENDPROC EMGCEmulateLockCmpXchg8b
227
228;;
229; Emulate CMPXCHG8B instruction, CDECL calling conv.
230; EMGCDECL(uint32_t) EMGCEmulateCmpXchg8b(RTGCPTR pu32Param1, uint32_t *pEAX, uint32_t *pEDX, uint32_t uEBX, uint32_t uECX, uint32_t *pEflags);
231;
232; @returns eax=0 if data written, other code - invalid access, #PF was generated.
233; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
234; @param [esp + 08h] Param 2 - Address of the eax register
235; @param [esp + 0ch] Param 3 - Address of the edx register
236; @param [esp + 10h] Param 4 - EBX
237; @param [esp + 14h] Param 5 - ECX
238; @param [esp + 18h] Param 6 - Pointer to eflags (out)
239; @uses eax, ecx, edx
240;
241align 16
242BEGINPROC EMGCEmulateCmpXchg8b
243 push ebp
244 push ebx
245 mov ebp, [esp + 04h + 8] ; ebp = first parameter
246 mov eax, [esp + 08h + 8] ; &EAX
247 mov eax, dword [eax]
248 mov edx, [esp + 0ch + 8] ; &EDX
249 mov edx, dword [edx]
250 mov ebx, [esp + 10h + 8] ; EBX
251 mov ecx, [esp + 14h + 8] ; ECX
252
253%ifdef RT_OS_OS2
254 cmpxchg8b [ebp] ; do CMPXCHG8B
255%else
256 cmpxchg8b qword [ebp] ; do CMPXCHG8B
257%endif
258 mov ebx, dword [esp + 08h + 8]
259 mov dword [ebx], eax
260 mov ebx, dword [esp + 0ch + 8]
261 mov dword [ebx], edx
262
263 ; collect flags and return.
264 pushf
265 pop eax
266
267 mov edx, [esp + 18h + 8] ; eflags pointer
268 mov dword [edx], eax
269
270 pop ebx
271 pop ebp
272 mov eax, VINF_SUCCESS
273 retn
274
275; Read error - we will be here after our page fault handler.
276GLOBALNAME EMGCEmulateCmpXchg8b_Error
277 pop ebx
278 pop ebp
279 mov eax, VERR_ACCESS_DENIED
280 ret
281ENDPROC EMGCEmulateCmpXchg8b
282
283;;
284; Emulate LOCK XADD instruction, CDECL calling conv.
285; EMGCDECL(uint32_t) EMGCEmulateLockXAdd(RTGCPTR pu32Param1, uint32_t *pu32Param2, uint32_t u32Param3, size_t cbSize, uint32_t *pEflags);
286;
287; @returns eax=0 if data exchanged, other code - invalid access, #PF was generated.
288; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
289; @param [esp + 08h] Param 2 - Second parameter - pointer to second parameter (general register)
290; @param [esp + 0ch] Param 3 - Size of parameters, only 1/2/4 is valid.
291; @param [esp + 10h] Param 4 - Pointer to eflags (out)
292; @uses eax, ecx, edx
293;
294align 16
295BEGINPROC EMGCEmulateLockXAdd
296 mov ecx, [esp + 04h + 0] ; ecx = first parameter
297 mov edx, [esp + 08h + 0] ; edx = 2nd parameter
298 mov eax, [esp + 0ch + 0] ; eax = size of parameters
299
300 cmp al, 4
301 je short .do_dword ; 4 bytes variant
302 cmp al, 2
303 je short .do_word ; 2 byte variant
304 cmp al, 1
305 je short .do_byte ; 1 bytes variant
306 int3
307
308.do_dword:
309 ; load 2nd parameter's value
310 mov eax, dword [edx]
311 lock xadd dword [ecx], eax ; do 4 bytes XADD
312 mov dword [edx], eax
313 jmp short .done
314
315.do_word:
316 ; load 2nd parameter's value
317 mov eax, dword [edx]
318 lock xadd word [ecx], ax ; do 2 bytes XADD
319 mov word [edx], ax
320 jmp short .done
321
322.do_byte:
323 ; load 2nd parameter's value
324 mov eax, dword [edx]
325 lock xadd byte [ecx], al ; do 1 bytes XADD
326 mov byte [edx], al
327
328.done:
329 ; collect flags and return.
330 mov edx, [esp + 10h + 0] ; eflags pointer
331 pushf
332 pop dword [edx]
333
334 mov eax, VINF_SUCCESS
335 retn
336
337; Read error - we will be here after our page fault handler.
338GLOBALNAME EMGCEmulateLockXAdd_Error
339 mov eax, VERR_ACCESS_DENIED
340 ret
341
342ENDPROC EMGCEmulateLockXAdd
343
344;;
345; Emulate XADD instruction, CDECL calling conv.
346; EMGCDECL(uint32_t) EMGCEmulateXAdd(RTGCPTR pu32Param1, uint32_t *pu32Param2, uint32_t u32Param3, size_t cbSize, uint32_t *pEflags);
347;
348; @returns eax=0 if data written, other code - invalid access, #PF was generated.
349; @param [esp + 04h] Param 1 - First parameter - pointer to first parameter
350; @param [esp + 08h] Param 2 - Second parameter - pointer to second parameter (general register)
351; @param [esp + 0ch] Param 3 - Size of parameters, only 1/2/4 is valid.
352; @param [esp + 10h] Param 4 - Pointer to eflags (out)
353; @uses eax, ecx, edx
354;
355align 16
356BEGINPROC EMGCEmulateXAdd
357 mov ecx, [esp + 04h + 0] ; ecx = first parameter
358 mov edx, [esp + 08h + 0] ; edx = 2nd parameter (eax)
359 mov eax, [esp + 0ch + 0] ; eax = size of parameters
360
361 cmp al, 4
362 je short .do_dword ; 4 bytes variant
363 cmp al, 2
364 je short .do_word ; 2 byte variant
365 cmp al, 1
366 je short .do_byte ; 1 bytes variant
367 int3
368
369.do_dword:
370 ; load 2nd parameter's value
371 mov eax, dword [edx]
372 xadd dword [ecx], eax ; do 4 bytes XADD
373 mov dword [edx], eax
374 jmp short .done
375
376.do_word:
377 ; load 2nd parameter's value
378 mov eax, dword [edx]
379 xadd word [ecx], ax ; do 2 bytes XADD
380 mov word [edx], ax
381 jmp short .done
382
383.do_byte:
384 ; load 2nd parameter's value
385 mov eax, dword [edx]
386 xadd byte [ecx], al ; do 1 bytes XADD
387 mov byte [edx], al
388
389.done:
390 ; collect flags and return.
391 mov edx, [esp + 10h + 0] ; eflags pointer
392 pushf
393 pop dword [edx]
394
395 mov eax, VINF_SUCCESS
396 retn
397
398; Read error - we will be here after our page fault handler.
399GLOBALNAME EMGCEmulateXAdd_Error
400 mov eax, VERR_ACCESS_DENIED
401 ret
402ENDPROC EMGCEmulateXAdd
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette