2 % threads.tex: description of threads interface for VideoLAN client
5 \section{A common thread interface}
7 This document describes how the different threads in the VideoLAN client are
8 organized, their API and functionnment.
13 \subsection{Thread properties}
15 A thread is described by a \csymbol{X\_thread\_t} structure (i.e.
16 \csymbol{vout\_thread\_t}), which is used to reference the thread in calls to
17 its API. This structure includes beside following thread-specific data the
21 typedef struct X_thread_s \{
22 pthread_t thread_id; /* thread id for pthreads */
23 boolean_t b_die; /* `die' flag */
24 boolean_t b_run; /* `run' flag */
25 boolean_t b_error; /* `error' flag */
26 boolean_t b_active; /* `active' flag */
33 % Meaning of common flags
35 \subsection{Meaning of common flags}
39 The \csymbol{die} flag means that the thread received a destruction request
40 from another thread. It must terminate as soon as possible. This field is
41 written (set to 1) by other threads and read by the thread itself. It cannot
42 be reset to 0 once it has been set.
44 Note that when the \csymbol{die} flag is set, no other thread should feed the
45 dying one, and all shared structures should have been freed (i.e. the images
46 and video streams for the video output thread).
49 The \csymbol{run} flag tells the other threads that the concerned thread is
50 ready to receive data. It is set to 1 by the thread itself when the second
51 phase of the initialization has succeeded, and set to 0 again by the thread
54 \item[\csymbol{error}]:
55 The \csymbol{error} flag tells the other threads that a fatal error occured in
56 the concerned thread. It can be set by all threads, and is read by the thread
57 itself and the controlling thread.
59 When a thread is in \csymbol{error} state, it runs in a special loop,
60 accepting feed from other threads, but trashing eveything, waiting for a
63 Therefore, the controlling thread should check periodically if a thread has an
64 \csymbol{error} set and, if yes, set its \csymbol{die} flag after having
65 destroyed all depending threads.
67 This flag is optionnal, but recommanded if an error can be envisaged in a later
70 \item[\csymbol{active}]:
71 This flag's purpose is to avoid using useless resources. An in-\csymbol{active}
72 thread must accept input as if it was inactive, but can treat its input
74 In example: the video output thread will set itself as in-\csymbol{active}
75 when it is unmapped, and continue to sort and trash images, but will not
76 render or display them to avoid consumming useless CPU. When a video decoder
77 thread will detect that its related output thread is inactive, it will set
78 itself inactive and trash everything except I images.
80 The \csymbol{active} flag can be set and read by anyone. Precautions should be
81 taken to avoid too long wake-up times.
83 This flag is optionnal, but recommanded if its use can be envisaged in a later
92 This API is only a recommandation.
95 \subsubsection{Creation}
98 X_thread_t * X_CreateThread( X_cfg_t *p_cfg )
101 This function will allocate thread descriptor, perform basic (and fast)
102 initialization steps, and create the thread itself using
103 \csymbol{pthread\_create}.
105 Once it has been called, all flags are set to 0. It will return the thread
106 descriptor or \csymbol{NULL} on failure.
109 \subsubsection{Termination}
112 void X_TerminateThread( X_thread_t * p_X );
115 This function will set the \csymbol{die} flag of the thread and and return
119 \subsubsection{Destruction}
122 int X_DestroyThread( X_thread_t *p_X );
125 This function will try to destroy the thread descriptor, if it is possible
126 (if the \csymbol{run} flag is not set). It will return 0 if it succeeded,
127 and non 0 if the thread was still active.
130 % Local functions names
132 \subsection{Local functions names}
134 The following functions names are recommanded to implement the different
135 parts of the thread creation and destruction:
138 int InitThread(); /* second phase of initialization */
139 int RunThread(); /* main loop */
140 int RunError(); /* error loop */
141 int DestroyThread(); /* thread destruction */
144 \csymbol{X\_CreateThread()} will spawn a thread using \csymbol{RunThread()}
145 function, which will call \csymbol{InitThread()}, enter its main loop,
146 eventually call \csymbol{RunError()} and finally calls \csymbol{DestroyThread}
147 when \csymbol{die} is received.
150 % Order of operations
152 \subsection{Order of operations}
155 \subsubsection{Creation}
158 Controlling thread & Thread \\
161 \csymbol{p\_X = X\_CreateThread( p\_cfg )}: & \\
162 descriptor allocation and initialization & \\
163 all flags are set to 0 & \\
164 base structures initialization & \\
165 If \csymbol{p\_X == NULL}: error & \\
166 \csymbol{X\_DestroyThread( p\_X )}: & \\
167 destruction of the descriptor & \\
169 Else, continuation.... & \csymbol{pthread\_create()} \\
170 & Second step of initialization \\
172 & \csymbol{b\_error = 1} \\
173 & destruction of structures \\
175 & \csymbol{b\_run = 1} \\
176 & beginning of main loop \\
180 Wait for \csymbol{b\_run} or \csymbol{b\_error}...& main loop... \\
181 If \csymbol{b\_error}: & \\
182 \csymbol{X\_DestroyThread( p\_X )} & \\
184 Else (\csymbol{b\_run == 1}): & \\
185 the thread is ready and can be feeded... & \\
192 \item The configuration structure can have been destroyed just after
193 \csymbol{X\_CreateThread()}. Therefore, it should not be used during second
196 \item When an error occurs during second initialization step, the allocated structures
197 are automatically destroyed (except the thread descriptor). Therefore, a call to
198 \csymbol{X\_TerminateThread} is not required.
202 \subsubsection{Main loop}
205 Controlling thread & Thread \\
208 Periodically check for \csymbol{b\_error} & Periodically check for \\
209 If set, then: & \csymbol{b\_error} and \csymbol{b\_die}\\
210 terminate all dependant threads & \\
211 destroy all dependant threads & \\
212 terminate and destroy thread & \\
218 \subsubsection{Destruction}
221 Controlling thread & Thread \\
224 \csymbol{X\_TerminateThread( p\_X )}: & \\
225 set \csymbol{b\_die} & \\
226 all flags are set to 0 & If \csymbol{DEBUG}, check if \\
227 & all shared structures are ok. \\
228 & Destroy and close everything, but \\
229 & keep descriptor. \\
230 & Set \csymbol{b\_run} to 0. \\
235 Loop until \csymbol{X\_DestroyThread} is 0: & \\
236 check if \csymbol{b\_run == 0} & \\
238 destroy descriptor & \\