Skip to content
GitLab
Explore
Sign in
Register
Primary navigation
Search or go to…
Project
wine
Manage
Activity
Members
Labels
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Package registry
Container Registry
Model registry
Operate
Terraform modules
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Yoann Laissus
wine
Commits
4eb0bebd
Commit
4eb0bebd
authored
23 years ago
by
Ove Kåven
Committed by
Alexandre Julliard
23 years ago
Browse files
Options
Downloads
Patches
Plain Diff
Fixed vm86_enter race conditions.
parent
fcc148b2
No related branches found
Branches containing commit
No related tags found
Tags containing commit
No related merge requests found
Changes
2
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
dlls/ntdll/signal_i386.c
+42
-19
42 additions, 19 deletions
dlls/ntdll/signal_i386.c
include/thread.h
+1
-2
1 addition, 2 deletions
include/thread.h
with
43 additions
and
21 deletions
dlls/ntdll/signal_i386.c
+
42
−
19
View file @
4eb0bebd
...
...
@@ -115,13 +115,17 @@ static inline int wine_sigaltstack( const struct sigaltstack *new,
}
#endif
int
vm86_enter
(
struct
vm86plus_struct
*
ptr
);
void
vm86_return
();
#define VM86_EAX 0
/* the %eax value while vm86_enter is executing */
int
vm86_enter
(
void
**
vm86_ptr
);
void
vm86_return
(
void
);
void
vm86_return_end
(
void
);
__ASM_GLOBAL_FUNC
(
vm86_enter
,
"pushl %ebp
\n\t
"
"movl %esp, %ebp
\n\t
"
"movl $166,%eax
\n\t
"
/*SYS_vm86*/
"movl 8(%ebp),%ecx
\n\t
"
"movl 8(%ebp),%ecx
\n\t
"
/* vm86_ptr */
"movl (%ecx),%ecx
\n\t
"
"pushl %ebx
\n\t
"
"movl $1,%ebx
\n\t
"
/*VM86_ENTER*/
"pushl %ecx
\n\t
"
/* put vm86plus_struct ptr somewhere we can find it */
...
...
@@ -134,6 +138,16 @@ __ASM_GLOBAL_FUNC(vm86_enter,
"popl %ecx
\n\t
"
"popl %ebx
\n\t
"
"popl %ebp
\n\t
"
"testl %eax,%eax
\n\t
"
"jl 0f
\n\t
"
"cmpb $0,%al
\n\t
"
/* VM86_SIGNAL */
"je "
__ASM_NAME
(
"vm86_enter"
)
"
\n\t
"
"0:
\n\t
"
"movl 4(%esp),%ecx
\n\t
"
/* vm86_ptr */
"movl $0,(%ecx)
\n\t
"
".globl "
__ASM_NAME
(
"vm86_return_end"
)
"
\n\t
"
".type "
__ASM_NAME
(
"vm86_return_end"
)
",@function
\n
"
__ASM_NAME
(
"vm86_return_end"
)
":
\n\t
"
"ret"
);
#define __HAVE_VM86
...
...
@@ -474,14 +488,18 @@ static void save_context( CONTEXT *context, const SIGCONTEXT *sigcontext )
#ifdef __HAVE_VM86
else
if
((
void
*
)
EIP_sig
(
sigcontext
)
==
vm86_return
)
/* vm86 mode */
{
/* retrieve pointer to vm86plus struct that was stored in vm86_enter */
struct
vm86plus_struct
*
vm86
=
*
(
struct
vm86plus_struct
**
)(
ESP_sig
(
sigcontext
)
+
sizeof
(
int
));
/* fetch the saved %fs on the stack */
fs
=
*
(
unsigned
int
*
)
ESP_sig
(
sigcontext
);
__set_fs
(
fs
);
/* get context from vm86 struct */
save_vm86_context
(
context
,
vm86
);
return
;
if
(
EAX_sig
(
sigcontext
)
==
VM86_EAX
)
{
struct
vm86plus_struct
*
vm86
;
__set_fs
(
fs
);
/* retrieve pointer to vm86plus struct that was stored in vm86_enter
* (but we could also get if from teb->vm86_ptr) */
vm86
=
*
(
struct
vm86plus_struct
**
)(
ESP_sig
(
sigcontext
)
+
sizeof
(
int
));
/* get context from vm86 struct */
save_vm86_context
(
context
,
vm86
);
return
;
}
}
#endif
/* __HAVE_VM86 */
...
...
@@ -519,9 +537,11 @@ static void restore_context( const CONTEXT *context, SIGCONTEXT *sigcontext )
#ifdef __HAVE_VM86
/* check if exception occurred in vm86 mode */
if
((
void
*
)
EIP_sig
(
sigcontext
)
==
vm86_return
&&
IS_SELECTOR_SYSTEM
(
CS_sig
(
sigcontext
)))
IS_SELECTOR_SYSTEM
(
CS_sig
(
sigcontext
))
&&
EAX_sig
(
sigcontext
)
==
VM86_EAX
)
{
/* retrieve pointer to vm86plus struct that was stored in vm86_enter */
/* retrieve pointer to vm86plus struct that was stored in vm86_enter
* (but we could also get it from teb->vm86_ptr) */
struct
vm86plus_struct
*
vm86
=
*
(
struct
vm86plus_struct
**
)(
ESP_sig
(
sigcontext
)
+
sizeof
(
int
));
restore_vm86_context
(
context
,
vm86
);
return
;
...
...
@@ -807,8 +827,10 @@ static void set_vm86_pend( CONTEXT *context )
if
(
context
->
EFlags
&
VIF_MASK
)
{
/* VIF is set, throw exception */
teb
->
vm86_pending
=
0
;
teb
->
vm86_ptr
=
NULL
;
rec
.
ExceptionAddress
=
(
LPVOID
)
context
->
Eip
;
EXC_RtlRaiseException
(
&
rec
,
context
);
teb
->
vm86_ptr
=
vm86
;
}
}
else
if
(
vm86
)
...
...
@@ -816,18 +838,22 @@ static void set_vm86_pend( CONTEXT *context )
/* not in VM86, but possibly setting up for it */
if
(
vm86
->
regs
.
eflags
&
VIP_MASK
)
return
;
vm86
->
regs
.
eflags
|=
VIP_MASK
;
if
(((
char
*
)
context
->
Eip
>=
(
char
*
)
vm86_return
)
&&
((
char
*
)
context
->
Eip
<=
(
char
*
)
vm86_return_end
)
&&
(
VM86_TYPE
(
context
->
Eax
)
!=
VM86_SIGNAL
))
{
/* exiting from VM86, can't throw */
return
;
}
if
(
vm86
->
regs
.
eflags
&
VIF_MASK
)
{
/* VIF is set, throw exception */
CONTEXT
vcontext
;
teb
->
vm86_pending
=
0
;
teb
->
vm86_ptr
=
NULL
;
save_vm86_context
(
&
vcontext
,
vm86
);
rec
.
ExceptionAddress
=
(
LPVOID
)
vcontext
.
Eip
;
EXC_RtlRaiseException
(
&
rec
,
&
vcontext
);
teb
->
vm86_ptr
=
vm86
;
restore_vm86_context
(
&
vcontext
,
vm86
);
if
(
teb
->
vm86_ctx
)
{
/* must also save here */
*
(
CONTEXT
*
)(
teb
->
vm86_ctx
)
=
vcontext
;
}
}
}
}
...
...
@@ -1065,7 +1091,7 @@ void __wine_enter_vm86( CONTEXT *context )
do
{
res
=
vm86_enter
(
&
vm86
);
res
=
vm86_enter
(
&
teb
->
vm86_ptr
);
/* uses and clears teb->vm86_ptr */
if
(
res
<
0
)
{
errno
=
-
res
;
...
...
@@ -1073,10 +1099,7 @@ void __wine_enter_vm86( CONTEXT *context )
}
}
while
(
VM86_TYPE
(
res
)
==
VM86_SIGNAL
);
teb
->
vm86_ctx
=
context
;
save_vm86_context
(
context
,
&
vm86
);
teb
->
vm86_ptr
=
NULL
;
teb
->
vm86_ctx
=
NULL
;
context
->
EFlags
|=
teb
->
vm86_pending
;
switch
(
VM86_TYPE
(
res
))
...
...
This diff is collapsed.
Click to expand it.
include/thread.h
+
1
−
2
View file @
4eb0bebd
...
...
@@ -101,11 +101,10 @@ typedef struct _TEB
DWORD
alarms
;
/* --3 22c Data for vm86 mode */
DWORD
vm86_pending
;
/* --3 230 Data for vm86 mode */
void
*
vm86_ptr
;
/* --3 234 Data for vm86 mode */
void
*
vm86_ctx
;
/* --3 238 Data for vm86 mode */
/* here is plenty space for wine specific fields (don't forget to change pad6!!) */
/* the following are nt specific fields */
DWORD
pad6
[
62
3
];
/* --n 23
c
*/
DWORD
pad6
[
62
4
];
/* --n 23
8
*/
UNICODE_STRING
StaticUnicodeString
;
/* -2- bf8 used by advapi32 */
USHORT
StaticUnicodeBuffer
[
261
];
/* -2- c00 used by advapi32 */
DWORD
pad7
;
/* --n e0c */
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment