Commit 81b6a1fb authored by Alexandre Julliard's avatar Alexandre Julliard

Convert the APC queues to use standard lists.

parent 9abbc913
...@@ -62,8 +62,7 @@ struct thread_wait ...@@ -62,8 +62,7 @@ struct thread_wait
struct thread_apc struct thread_apc
{ {
struct thread_apc *next; /* queue linked list */ struct list entry; /* queue linked list */
struct thread_apc *prev;
struct object *owner; /* object that queued this apc */ struct object *owner; /* object that queued this apc */
void *func; /* function to call in client */ void *func; /* function to call in client */
enum apc_type type; /* type of apc function */ enum apc_type type; /* type of apc function */
...@@ -121,10 +120,6 @@ inline static void init_thread_structure( struct thread *thread ) ...@@ -121,10 +120,6 @@ inline static void init_thread_structure( struct thread *thread )
thread->debug_event = NULL; thread->debug_event = NULL;
thread->queue = NULL; thread->queue = NULL;
thread->wait = NULL; thread->wait = NULL;
thread->system_apc.head = NULL;
thread->system_apc.tail = NULL;
thread->user_apc.head = NULL;
thread->user_apc.tail = NULL;
thread->error = 0; thread->error = 0;
thread->req_data = NULL; thread->req_data = NULL;
thread->req_toread = 0; thread->req_toread = 0;
...@@ -144,6 +139,9 @@ inline static void init_thread_structure( struct thread *thread ) ...@@ -144,6 +139,9 @@ inline static void init_thread_structure( struct thread *thread )
thread->creation_time = time(NULL); thread->creation_time = time(NULL);
thread->exit_time = 0; thread->exit_time = 0;
list_init( &thread->system_apc );
list_init( &thread->user_apc );
for (i = 0; i < MAX_INFLIGHT_FDS; i++) for (i = 0; i < MAX_INFLIGHT_FDS; i++)
thread->inflight[i].server = thread->inflight[i].client = -1; thread->inflight[i].server = thread->inflight[i].client = -1;
} }
...@@ -451,8 +449,8 @@ static int check_wait( struct thread *thread ) ...@@ -451,8 +449,8 @@ static int check_wait( struct thread *thread )
} }
other_checks: other_checks:
if ((wait->flags & SELECT_INTERRUPTIBLE) && thread->system_apc.head) return STATUS_USER_APC; if ((wait->flags & SELECT_INTERRUPTIBLE) && !list_empty(&thread->system_apc)) return STATUS_USER_APC;
if ((wait->flags & SELECT_ALERTABLE) && thread->user_apc.head) return STATUS_USER_APC; if ((wait->flags & SELECT_ALERTABLE) && !list_empty(&thread->user_apc)) return STATUS_USER_APC;
if (wait->flags & SELECT_TIMEOUT) if (wait->flags & SELECT_TIMEOUT)
{ {
struct timeval now; struct timeval now;
...@@ -588,28 +586,22 @@ int thread_queue_apc( struct thread *thread, struct object *owner, void *func, ...@@ -588,28 +586,22 @@ int thread_queue_apc( struct thread *thread, struct object *owner, void *func,
enum apc_type type, int system, void *arg1, void *arg2, void *arg3 ) enum apc_type type, int system, void *arg1, void *arg2, void *arg3 )
{ {
struct thread_apc *apc; struct thread_apc *apc;
struct apc_queue *queue = system ? &thread->system_apc : &thread->user_apc; struct list *queue = system ? &thread->system_apc : &thread->user_apc;
/* cancel a possible previous APC with the same owner */ /* cancel a possible previous APC with the same owner */
if (owner) thread_cancel_apc( thread, owner, system ); if (owner) thread_cancel_apc( thread, owner, system );
if (thread->state == TERMINATED) return 0; if (thread->state == TERMINATED) return 0;
if (!(apc = mem_alloc( sizeof(*apc) ))) return 0; if (!(apc = mem_alloc( sizeof(*apc) ))) return 0;
apc->prev = queue->tail;
apc->next = NULL;
apc->owner = owner; apc->owner = owner;
apc->func = func; apc->func = func;
apc->type = type; apc->type = type;
apc->arg1 = arg1; apc->arg1 = arg1;
apc->arg2 = arg2; apc->arg2 = arg2;
apc->arg3 = arg3; apc->arg3 = arg3;
queue->tail = apc; list_add_tail( queue, &apc->entry );
if (!apc->prev) /* first one */ if (!list_prev( queue, &apc->entry )) /* first one */
{
queue->head = apc;
wake_thread( thread ); wake_thread( thread );
}
else apc->prev->next = apc;
return 1; return 1;
} }
...@@ -618,14 +610,11 @@ int thread_queue_apc( struct thread *thread, struct object *owner, void *func, ...@@ -618,14 +610,11 @@ int thread_queue_apc( struct thread *thread, struct object *owner, void *func,
void thread_cancel_apc( struct thread *thread, struct object *owner, int system ) void thread_cancel_apc( struct thread *thread, struct object *owner, int system )
{ {
struct thread_apc *apc; struct thread_apc *apc;
struct apc_queue *queue = system ? &thread->system_apc : &thread->user_apc; struct list *queue = system ? &thread->system_apc : &thread->user_apc;
for (apc = queue->head; apc; apc = apc->next) LIST_FOR_EACH_ENTRY( apc, queue, struct thread_apc, entry )
{ {
if (apc->owner != owner) continue; if (apc->owner != owner) continue;
if (apc->next) apc->next->prev = apc->prev; list_remove( &apc->entry );
else queue->tail = apc->prev;
if (apc->prev) apc->prev->next = apc->next;
else queue->head = apc->next;
free( apc ); free( apc );
return; return;
} }
...@@ -634,15 +623,14 @@ void thread_cancel_apc( struct thread *thread, struct object *owner, int system ...@@ -634,15 +623,14 @@ void thread_cancel_apc( struct thread *thread, struct object *owner, int system
/* remove the head apc from the queue; the returned pointer must be freed by the caller */ /* remove the head apc from the queue; the returned pointer must be freed by the caller */
static struct thread_apc *thread_dequeue_apc( struct thread *thread, int system_only ) static struct thread_apc *thread_dequeue_apc( struct thread *thread, int system_only )
{ {
struct thread_apc *apc; struct thread_apc *apc = NULL;
struct apc_queue *queue = &thread->system_apc; struct list *ptr = list_head( &thread->system_apc );
if (!queue->head && !system_only) queue = &thread->user_apc; if (!ptr && !system_only) ptr = list_head( &thread->user_apc );
if ((apc = queue->head)) if (ptr)
{ {
if (apc->next) apc->next->prev = NULL; apc = LIST_ENTRY( ptr, struct thread_apc, entry );
else queue->tail = NULL; list_remove( ptr );
queue->head = apc->next;
} }
return apc; return apc;
} }
......
...@@ -40,12 +40,6 @@ enum run_state ...@@ -40,12 +40,6 @@ enum run_state
TERMINATED /* terminated */ TERMINATED /* terminated */
}; };
struct apc_queue
{
struct thread_apc *head;
struct thread_apc *tail;
};
/* descriptor for fds currently in flight from client to server */ /* descriptor for fds currently in flight from client to server */
struct inflight_fd struct inflight_fd
{ {
...@@ -68,8 +62,8 @@ struct thread ...@@ -68,8 +62,8 @@ struct thread
struct debug_event *debug_event; /* debug event being sent to debugger */ struct debug_event *debug_event; /* debug event being sent to debugger */
struct msg_queue *queue; /* message queue */ struct msg_queue *queue; /* message queue */
struct thread_wait *wait; /* current wait condition if sleeping */ struct thread_wait *wait; /* current wait condition if sleeping */
struct apc_queue system_apc; /* queue of system async procedure calls */ struct list system_apc; /* queue of system async procedure calls */
struct apc_queue user_apc; /* queue of user async procedure calls */ struct list user_apc; /* queue of user async procedure calls */
struct inflight_fd inflight[MAX_INFLIGHT_FDS]; /* fds currently in flight */ struct inflight_fd inflight[MAX_INFLIGHT_FDS]; /* fds currently in flight */
unsigned int error; /* current error code */ unsigned int error; /* current error code */
union generic_request req; /* current request */ union generic_request req; /* current request */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment