1 /* Thread management routine header.
2 * Copyright (C) 1998 Kunihiro Ishiguro
4 * This file is part of GNU Zebra.
6 * GNU Zebra is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2, or (at your option) any
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with GNU Zebra; see the file COPYING. If not, write to the Free
18 * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
22 #ifndef _ZEBRA_THREAD_H
23 #define _ZEBRA_THREAD_H
34 #define RUSAGE_T struct rusage_t
36 #define GETRUSAGE(X) thread_getrusage(X)
38 /* Linked list of thread. */
49 * Abstract it so we can use different methodologies to
52 typedef fd_set thread_fd_set;
54 /* Master of the theads. */
58 struct thread **write;
60 struct thread_list event;
61 struct thread_list ready;
62 struct thread_list unuse;
63 struct pqueue *background;
66 thread_fd_set writefd;
67 thread_fd_set exceptfd;
71 typedef unsigned char thread_type;
76 thread_type type; /* thread type */
77 thread_type add_type; /* thread type */
78 struct thread *next; /* next pointer of the thread */
79 struct thread *prev; /* previous pointer of the thread */
80 struct thread_master *master; /* pointer to the struct thread_master. */
81 int (*func) (struct thread *); /* event function */
82 void *arg; /* event argument */
84 int val; /* second argument of the event. */
85 int fd; /* file descriptor in case of read/write. */
86 struct timeval sands; /* rest of time sands value. */
88 int index; /* used for timers to store position in queue */
90 struct cpu_thread_history *hist; /* cache pointer to cpu_history */
92 const char *schedfrom;
96 struct cpu_thread_history
98 int (*func)(struct thread *);
99 unsigned int total_calls;
102 unsigned long total, max;
105 struct time_stats cpu;
108 const char *funcname;
111 /* Clocks supported by Quagga */
113 QUAGGA_CLK_REALTIME = 0, /* ala gettimeofday() */
114 QUAGGA_CLK_MONOTONIC, /* monotonic, against an indeterminate base */
115 QUAGGA_CLK_REALTIME_STABILISED, /* like realtime, but non-decrementing */
119 #define THREAD_READ 0
120 #define THREAD_WRITE 1
121 #define THREAD_TIMER 2
122 #define THREAD_EVENT 3
123 #define THREAD_READY 4
124 #define THREAD_BACKGROUND 5
125 #define THREAD_UNUSED 6
126 #define THREAD_EXECUTE 7
128 /* Thread yield time. */
129 #define THREAD_YIELD_TIME_SLOT 10 * 1000L /* 10ms */
132 #define THREAD_ARG(X) ((X)->arg)
133 #define THREAD_FD(X) ((X)->u.fd)
134 #define THREAD_VAL(X) ((X)->u.val)
136 #define THREAD_READ_ON(master,thread,func,arg,sock) \
139 thread = thread_add_read (master, func, arg, sock); \
142 #define THREAD_WRITE_ON(master,thread,func,arg,sock) \
145 thread = thread_add_write (master, func, arg, sock); \
148 #define THREAD_TIMER_ON(master,thread,func,arg,time) \
151 thread = thread_add_timer (master, func, arg, time); \
154 #define THREAD_TIMER_MSEC_ON(master,thread,func,arg,time) \
157 thread = thread_add_timer_msec (master, func, arg, time); \
160 #define THREAD_OFF(thread) \
164 thread_cancel (thread); \
169 #define THREAD_READ_OFF(thread) THREAD_OFF(thread)
170 #define THREAD_WRITE_OFF(thread) THREAD_OFF(thread)
171 #define THREAD_TIMER_OFF(thread) THREAD_OFF(thread)
173 #define debugargdef const char *funcname, const char *schedfrom, int fromln
175 #define thread_add_read(m,f,a,v) funcname_thread_add_read(m,f,a,v,#f,__FILE__,__LINE__)
176 #define thread_add_write(m,f,a,v) funcname_thread_add_write(m,f,a,v,#f,__FILE__,__LINE__)
177 #define thread_add_timer(m,f,a,v) funcname_thread_add_timer(m,f,a,v,#f,__FILE__,__LINE__)
178 #define thread_add_timer_msec(m,f,a,v) funcname_thread_add_timer_msec(m,f,a,v,#f,__FILE__,__LINE__)
179 #define thread_add_timer_tv(m,f,a,v) funcname_thread_add_timer_tv(m,f,a,v,#f,__FILE__,__LINE__)
180 #define thread_add_event(m,f,a,v) funcname_thread_add_event(m,f,a,v,#f,__FILE__,__LINE__)
181 #define thread_execute(m,f,a,v) funcname_thread_execute(m,f,a,v,#f,__FILE__,__LINE__)
183 /* The 4th arg to thread_add_background is the # of milliseconds to delay. */
184 #define thread_add_background(m,f,a,v) funcname_thread_add_background(m,f,a,v,#f,__FILE__,__LINE__)
187 extern struct thread_master *thread_master_create (void);
188 extern void thread_master_free (struct thread_master *);
190 extern struct thread *funcname_thread_add_read (struct thread_master *,
191 int (*)(struct thread *),
192 void *, int, debugargdef);
193 extern struct thread *funcname_thread_add_write (struct thread_master *,
194 int (*)(struct thread *),
195 void *, int, debugargdef);
196 extern struct thread *funcname_thread_add_timer (struct thread_master *,
197 int (*)(struct thread *),
198 void *, long, debugargdef);
199 extern struct thread *funcname_thread_add_timer_msec (struct thread_master *,
200 int (*)(struct thread *),
201 void *, long, debugargdef);
202 extern struct thread *funcname_thread_add_timer_tv (struct thread_master *,
203 int (*)(struct thread *),
204 void *, struct timeval *,
206 extern struct thread *funcname_thread_add_event (struct thread_master *,
207 int (*)(struct thread *),
208 void *, int, debugargdef);
209 extern struct thread *funcname_thread_add_background (struct thread_master *,
210 int (*func)(struct thread *),
212 long milliseconds_to_delay,
214 extern struct thread *funcname_thread_execute (struct thread_master *,
215 int (*)(struct thread *),
216 void *, int, debugargdef);
219 extern void thread_cancel (struct thread *);
220 extern unsigned int thread_cancel_event (struct thread_master *, void *);
221 extern struct thread *thread_fetch (struct thread_master *, struct thread *);
222 extern void thread_call (struct thread *);
223 extern unsigned long thread_timer_remain_second (struct thread *);
224 extern struct timeval thread_timer_remain(struct thread*);
225 extern int thread_should_yield (struct thread *);
226 extern unsigned long timeval_elapsed (struct timeval a, struct timeval b);
228 /* Internal libzebra exports */
229 extern void thread_getrusage (RUSAGE_T *);
230 extern struct cmd_element show_thread_cpu_cmd;
231 extern struct cmd_element clear_thread_cpu_cmd;
233 /* replacements for the system gettimeofday(), clock_gettime() and
234 * time() functions, providing support for non-decrementing clock on
235 * all systems, and fully monotonic on /some/ systems.
237 extern int quagga_gettime (enum quagga_clkid, struct timeval *);
238 extern time_t quagga_time (time_t *);
240 /* Returns elapsed real (wall clock) time. */
241 extern unsigned long thread_consumed_time(RUSAGE_T *after, RUSAGE_T *before,
242 unsigned long *cpu_time_elapsed);
244 /* Global variable containing a recent result from gettimeofday. This can
245 be used instead of calling gettimeofday if a recent value is sufficient.
246 This is guaranteed to be refreshed before a thread is called. */
247 extern struct timeval recent_time;
248 /* Similar to recent_time, but a monotonically increasing time value */
249 extern struct timeval recent_relative_time (void);
251 /* only for use in logging functions! */
252 extern struct thread *thread_current;
254 #endif /* _ZEBRA_THREAD_H */