]> git.sur5r.net Git - openldap/blob - libraries/libldap_r/rq.c
8aa9b0b76a72c5dbb82c1609e7201d88999adbcc
[openldap] / libraries / libldap_r / rq.c
1 /* $OpenLDAP$ */
2 #include "portable.h"
3
4 #include <stdio.h>
5
6 #include <ac/stdarg.h>
7 #include <ac/stdlib.h>
8 #include <ac/string.h>
9 #include <ac/time.h>
10 #include <ac/errno.h>
11
12 #include "ldap-int.h"
13 #include "ldap_pvt_thread.h"
14 #include "ldap_queue.h"
15 #include "ldap_rq.h"
16
17 #ifdef LDAP_SYNCREPL
18
19 void
20 ldap_pvt_runqueue_insert(
21         struct runqueue_s* rq,
22         time_t interval,
23         ldap_pvt_thread_start_t *routine,
24         void *arg
25 )
26 {
27         struct re_s* entry;
28
29         entry = (struct re_s *) LDAP_CALLOC( 1, sizeof( struct re_s ));
30         entry->interval.tv_sec = interval;
31         entry->interval.tv_usec = 0;
32         entry->next_sched.tv_sec = time( NULL );
33         entry->next_sched.tv_usec = 0;
34         entry->routine = routine;
35         entry->arg = arg;
36         LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
37 }
38
39 void
40 ldap_pvt_runqueue_remove(
41         struct runqueue_s* rq,
42         struct re_s* entry
43 )
44 {
45         struct re_s* e;
46
47         LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
48                 if ( e == entry)
49                         break;
50         }
51
52         assert ( e == entry );
53
54         LDAP_STAILQ_REMOVE( &rq->task_list, entry, re_s, tnext );
55
56         LDAP_FREE( entry );
57
58 }
59
60 struct re_s*
61 ldap_pvt_runqueue_next_sched(
62         struct runqueue_s* rq,
63         struct timeval** next_run
64 )
65 {
66         struct re_s* entry;
67
68         entry = LDAP_STAILQ_FIRST( &rq->task_list );
69         if ( entry == NULL ) {
70                 *next_run = NULL;
71                 return NULL;
72         } else if ( entry->next_sched.tv_sec == 0 ) {
73                 *next_run = NULL;
74                 return NULL;
75         } else {
76                 *next_run = &entry->next_sched;
77                 return entry;
78         }
79 }
80
81 void
82 ldap_pvt_runqueue_runtask(
83         struct runqueue_s* rq,
84         struct re_s* entry
85 )
86 {
87         LDAP_STAILQ_INSERT_HEAD( &rq->run_list, entry, rnext );
88 }
89
90 void
91 ldap_pvt_runqueue_stoptask(
92         struct runqueue_s* rq,
93         struct re_s* entry
94 )
95 {
96         LDAP_STAILQ_REMOVE( &rq->run_list, entry, re_s, rnext );
97 }
98
99 int
100 ldap_pvt_runqueue_isrunning(
101         struct runqueue_s* rq,
102         struct re_s* entry
103 )
104 {
105         struct re_s* e;
106
107         LDAP_STAILQ_FOREACH( e, &rq->run_list, rnext ) {
108                 if ( e == entry ) {
109                         return 1;
110                 }
111         }
112         return 0;
113 }
114
115 void 
116 ldap_pvt_runqueue_resched(
117         struct runqueue_s* rq,
118         struct re_s* entry
119 )
120 {
121         struct re_s* prev;
122         struct re_s* e;
123
124         LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
125                 if ( e == entry )
126                         break;
127         }
128
129         assert ( e == entry );
130
131         LDAP_STAILQ_REMOVE( &rq->task_list, entry, re_s, tnext );
132
133         if ( entry->interval.tv_sec ) {
134                 entry->next_sched.tv_sec = time( NULL ) + entry->interval.tv_sec;
135         } else {
136                 entry->next_sched.tv_sec = 0;
137         }
138
139         if ( LDAP_STAILQ_EMPTY( &rq->task_list )) {
140                 LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
141         } else if ( entry->next_sched.tv_sec == 0 ) {
142                 LDAP_STAILQ_INSERT_TAIL( &rq->task_list, entry, tnext );
143         } else {
144                 prev = NULL;
145                 LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
146                         if ( e->next_sched.tv_sec == 0 ) {
147                                 if ( prev == NULL ) {
148                                         LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
149                                 } else {
150                                         LDAP_STAILQ_INSERT_AFTER( &rq->task_list, prev, entry, tnext );
151                                 }
152                                 break;
153                         } else if ( e->next_sched.tv_sec > entry->next_sched.tv_sec ) {
154                                 if ( prev == NULL ) {
155                                         LDAP_STAILQ_INSERT_HEAD( &rq->task_list, entry, tnext );
156                                 } else {
157                                         LDAP_STAILQ_INSERT_AFTER( &rq->task_list, prev, entry, tnext );
158                                 }
159                                 break;
160                         }
161                         prev = e;
162                 }
163         }
164 }
165
166 int
167 ldap_pvt_runqueue_persistent_backload(
168         struct runqueue_s* rq
169 )
170 {
171         struct re_s* e;
172         int count = 0;
173
174         if ( !LDAP_STAILQ_EMPTY( &rq->task_list )) {
175                 LDAP_STAILQ_FOREACH( e, &rq->task_list, tnext ) {
176                         if ( e->next_sched.tv_sec == 0 )
177                                 count++;
178                 }
179         }
180         return count;
181 }
182
183 #endif