]> git.sur5r.net Git - openldap/blob - libraries/libldap_r/rq.c
Remove broken MSVC build from REL_ENG branch.
[openldap] / libraries / libldap_r / rq.c
1 /* $OpenLDAP$ */
2 /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
3  *
4  * Copyright 2003 The OpenLDAP Foundation.
5  * Portions Copyright 2003 IBM Corporation.
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted only as authorized by the OpenLDAP
10  * Public License.
11  *
12  * A copy of this license is available in file LICENSE in the
13  * top-level directory of the distribution or, alternatively, at
14  * <http://www.OpenLDAP.org/license.html>.
15  */
16 /* This work was initially developed by Jong Hyuk Choi for inclusion
17  * in OpenLDAP Software.
18  */
19
20 #include "portable.h"
21
22 #include <stdio.h>
23
24 #include <ac/stdarg.h>
25 #include <ac/stdlib.h>
26 #include <ac/errno.h>
27 #include <ac/socket.h>
28 #include <ac/string.h>
29 #include <ac/time.h>
30
31 #include "ldap-int.h"
32 #include "ldap_pvt_thread.h"
33 #include "ldap_queue.h"
34 #include "ldap_rq.h"
35
36 void
37 ldap_pvt_runqueue_insert(
38         struct runqueue_s* rq,
39         time_t interval,
40         ldap_pvt_thread_start_t *routine,
41         void *arg
42 )
43 {
44         struct re_s* entry;
45
46         entry = (struct re_s *) LDAP_CALLOC( 1, sizeof( struct re_s ));
47         entry->interval.tv_sec = interval;
48         entry->interval.tv_usec = 0;
49         entry->next_sched.tv_sec = time( NULL );
50         entry->next_sched.tv_usec = 0;
51         entry->routine = routine;
52         entry->arg = arg;
53         LDAP_STAILQ_INSERT_TAIL( &rq->task_list, entry, tnext );
54 }
55
56 void
57 ldap_pvt_runqueue_remove(
58         struct runqueue_s* rq,
59         struct re_s* entry
60 )
61 {
62         struct re_s* e;
63
64         LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
65                 if ( e == entry)
66                         break;
67         }
68
69         assert ( e == entry );
70
71         LDAP_STAILQ_REMOVE( &rq->task_list, entry, re_s, tnext );
72
73         LDAP_FREE( entry );
74
75 }
76
77 struct re_s*
78 ldap_pvt_runqueue_next_sched(
79         struct runqueue_s* rq,
80         struct timeval** next_run
81 )
82 {
83         struct re_s* entry;
84
85         entry = LDAP_STAILQ_FIRST( &rq->task_list );
86         if ( entry == NULL ) {
87                 *next_run = NULL;
88                 return NULL;
89         } else if ( entry->next_sched.tv_sec == 0 ) {
90                 *next_run = NULL;
91                 return NULL;
92         } else {
93                 *next_run = &entry->next_sched;
94                 return entry;
95         }
96 }
97
98 void
99 ldap_pvt_runqueue_runtask(
100         struct runqueue_s* rq,
101         struct re_s* entry
102 )
103 {
104         LDAP_STAILQ_INSERT_TAIL( &rq->run_list, entry, rnext );
105 }
106
107 void
108 ldap_pvt_runqueue_stoptask(
109         struct runqueue_s* rq,
110         struct re_s* entry
111 )
112 {
113         LDAP_STAILQ_REMOVE( &rq->run_list, entry, re_s, rnext );
114 }
115
116 int
117 ldap_pvt_runqueue_isrunning(
118         struct runqueue_s* rq,
119         struct re_s* entry
120 )
121 {
122         struct re_s* e;
123
124         LDAP_STAILQ_FOREACH( e, &rq->run_list, rnext ) {
125                 if ( e == entry ) {
126                         return 1;
127                 }
128         }
129         return 0;
130 }
131
132 void 
133 ldap_pvt_runqueue_resched(
134         struct runqueue_s* rq,
135         struct re_s* entry,
136         int defer
137 )
138 {
139         struct re_s* prev;
140         struct re_s* e;
141
142         LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
143                 if ( e == entry )
144                         break;
145         }
146
147         assert ( e == entry );
148
149         LDAP_STAILQ_REMOVE( &rq->task_list, entry, re_s, tnext );
150
151         if ( entry->interval.tv_sec && !defer ) {
152                 entry->next_sched.tv_sec = time( NULL ) + entry->interval.tv_sec;
153         } else {
154                 entry->next_sched.tv_sec = 0;
155         }
156
157         if ( LDAP_STAILQ_EMPTY( &rq->task_list )) {
158                 LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
159         } else if ( entry->next_sched.tv_sec == 0 ) {
160                 LDAP_STAILQ_INSERT_TAIL( &rq->task_list, entry, tnext );
161         } else {
162                 prev = NULL;
163                 LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
164                         if ( e->next_sched.tv_sec == 0 ) {
165                                 if ( prev == NULL ) {
166                                         LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
167                                 } else {
168                                         LDAP_STAILQ_INSERT_AFTER( &rq->task_list, prev, entry, tnext );
169                                 }
170                                 return;
171                         } else if ( e->next_sched.tv_sec > entry->next_sched.tv_sec ) {
172                                 if ( prev == NULL ) {
173                                         LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
174                                 } else {
175                                         LDAP_STAILQ_INSERT_AFTER( &rq->task_list, prev, entry, tnext );
176                                 }
177                                 return;
178                         }
179                         prev = e;
180                 }
181                 LDAP_STAILQ_INSERT_TAIL( &rq->task_list, entry, tnext );
182         }
183 }
184
185 int
186 ldap_pvt_runqueue_persistent_backload(
187         struct runqueue_s* rq
188 )
189 {
190         struct re_s* e;
191         int count = 0;
192
193         ldap_pvt_thread_mutex_lock( &rq->rq_mutex );
194         if ( !LDAP_STAILQ_EMPTY( &rq->task_list )) {
195                 LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
196                         if ( e->next_sched.tv_sec == 0 )
197                                 count++;
198                 }
199         }
200         ldap_pvt_thread_mutex_unlock( &rq->rq_mutex );
201         return count;
202 }
203