Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/tcl8.5.2/doc/Notifier.3 @ 25

Last change on this file since 25 was 25, checked in by landauf, 16 years ago

added tcl to libs

File size: 29.1 KB
Line 
1'\"
2'\" Copyright (c) 1998-1999 Scriptics Corporation
3'\" Copyright (c) 1995-1997 Sun Microsystems, Inc.
4'\"
5'\" See the file "license.terms" for information on usage and redistribution
6'\" of this file, and for a DISCLAIMER OF ALL WARRANTIES.
7'\"
8'\" RCS: @(#) $Id: Notifier.3,v 1.21 2007/12/13 15:22:31 dgp Exp $
9'\"
10.so man.macros
11.TH Notifier 3 8.1 Tcl "Tcl Library Procedures"
12.BS
13.SH NAME
14Tcl_CreateEventSource, Tcl_DeleteEventSource, Tcl_SetMaxBlockTime, Tcl_QueueEvent, Tcl_ThreadQueueEvent, Tcl_ThreadAlert, Tcl_GetCurrentThread, Tcl_DeleteEvents, Tcl_InitNotifier, Tcl_FinalizeNotifier, Tcl_WaitForEvent, Tcl_AlertNotifier, Tcl_SetTimer, Tcl_ServiceAll, Tcl_ServiceEvent, Tcl_GetServiceMode, Tcl_SetServiceMode \- the event queue and notifier interfaces
15.SH SYNOPSIS
16.nf
17\fB#include <tcl.h>\fR
18.sp
19void
20\fBTcl_CreateEventSource\fR(\fIsetupProc, checkProc, clientData\fR)
21.sp
22void
23\fBTcl_DeleteEventSource\fR(\fIsetupProc, checkProc, clientData\fR)
24.sp
25void
26\fBTcl_SetMaxBlockTime\fR(\fItimePtr\fR)
27.sp
28void
29\fBTcl_QueueEvent\fR(\fIevPtr, position\fR)
30.sp
31void
32\fBTcl_ThreadQueueEvent\fR(\fIthreadId, evPtr, position\fR)
33.sp
34void
35\fBTcl_ThreadAlert\fR(\fIthreadId\fR)
36.sp
37Tcl_ThreadId
38\fBTcl_GetCurrentThread\fR()
39.sp
40void
41\fBTcl_DeleteEvents\fR(\fIdeleteProc, clientData\fR)
42.sp
43ClientData
44\fBTcl_InitNotifier\fR()
45.sp
46void
47\fBTcl_FinalizeNotifier\fR(\fIclientData\fR)
48.sp
49int
50\fBTcl_WaitForEvent\fR(\fItimePtr\fR)
51.sp
52void
53\fBTcl_AlertNotifier\fR(\fIclientData\fR)
54.sp
55void
56\fBTcl_SetTimer\fR(\fItimePtr\fR)
57.sp
58int
59\fBTcl_ServiceAll\fR()
60.sp
61int
62\fBTcl_ServiceEvent\fR(\fIflags\fR)
63.sp
64int
65\fBTcl_GetServiceMode\fR()
66.sp
67int
68\fBTcl_SetServiceMode\fR(\fImode\fR)
69.sp
70void
71\fBTcl_ServiceModeHook\fR(\fImode\fR)
72.sp
73void
74\fBTcl_SetNotifier\fR(\fInotifierProcPtr\fR)
75.SH ARGUMENTS
76.AS Tcl_EventDeleteProc *notifierProcPtr
77.AP Tcl_EventSetupProc *setupProc in
78Procedure to invoke to prepare for event wait in \fBTcl_DoOneEvent\fR.
79.AP Tcl_EventCheckProc *checkProc in
80Procedure for \fBTcl_DoOneEvent\fR to invoke after waiting for
81events.  Checks to see if any events have occurred and, if so,
82queues them.
83.AP ClientData clientData in
84Arbitrary one-word value to pass to \fIsetupProc\fR, \fIcheckProc\fR, or
85\fIdeleteProc\fR.
86.AP Tcl_Time *timePtr in
87Indicates the maximum amount of time to wait for an event.  This
88is specified as an interval (how long to wait), not an absolute
89time (when to wakeup).  If the pointer passed to \fBTcl_WaitForEvent\fR
90is NULL, it means there is no maximum wait time:  wait forever if
91necessary.
92.AP Tcl_Event *evPtr in
93An event to add to the event queue.  The storage for the event must
94have been allocated by the caller using \fBTcl_Alloc\fR or \fBckalloc\fR.
95.AP Tcl_QueuePosition position in
96Where to add the new event in the queue:  \fBTCL_QUEUE_TAIL\fR,
97\fBTCL_QUEUE_HEAD\fR, or \fBTCL_QUEUE_MARK\fR.
98.AP Tcl_ThreadId threadId in
99A unique identifier for a thread.
100.AP Tcl_EventDeleteProc *deleteProc in
101Procedure to invoke for each queued event in \fBTcl_DeleteEvents\fR.
102.AP int flags in
103What types of events to service.  These flags are the same as those
104passed to \fBTcl_DoOneEvent\fR.
105.AP int mode in
106Indicates whether events should be serviced by \fBTcl_ServiceAll\fR.
107Must be one of \fBTCL_SERVICE_NONE\fR or \fBTCL_SERVICE_ALL\fR.
108.AP Tcl_NotifierProcs* notifierProcPtr in
109Structure of function pointers describing notifier procedures that are
110to replace the ones installed in the executable.  See
111\fBREPLACING THE NOTIFIER\fR for details.
112.BE
113
114.SH INTRODUCTION
115.PP
116The interfaces described here are used to customize the Tcl event
117loop.  The two most common customizations are to add new sources of
118events and to merge Tcl's event loop with some other event loop, such
119as one provided by an application in which Tcl is embedded.  Each of
120these tasks is described in a separate section below.
121.PP
122The procedures in this manual entry are the building blocks out of which
123the Tcl event notifier is constructed.  The event notifier is the lowest
124layer in the Tcl event mechanism.  It consists of three things:
125.IP [1]
126Event sources: these represent the ways in which events can be
127generated.  For example, there is a timer event source that implements
128the \fBTcl_CreateTimerHandler\fR procedure and the \fBafter\fR
129command, and there is a file event source that implements the
130\fBTcl_CreateFileHandler\fR procedure on Unix systems.  An event
131source must work with the notifier to detect events at the right
132times, record them on the event queue, and eventually notify
133higher-level software that they have occurred.  The procedures
134\fBTcl_CreateEventSource\fR, \fBTcl_DeleteEventSource\fR,
135and \fBTcl_SetMaxBlockTime\fR, \fBTcl_QueueEvent\fR, and
136\fBTcl_DeleteEvents\fR are used primarily by event sources.
137.IP [2]
138The event queue: for non-threaded applications,
139there is a single queue for the whole application,
140containing events that have been detected but not yet serviced.  Event
141sources place events onto the queue so that they may be processed in
142order at appropriate times during the event loop. The event queue
143guarantees a fair discipline of event handling, so that no event
144source can starve the others.  It also allows events to be saved for
145servicing at a future time.  Threaded applications work in a
146similar manner, except that there is a separate event queue for
147each thread containing a Tcl interpreter.
148\fBTcl_QueueEvent\fR is used (primarily
149by event sources) to add events to the event queue and
150\fBTcl_DeleteEvents\fR is used to remove events from the queue without
151processing them.  In a threaded application, \fBTcl_QueueEvent\fR adds
152an event to the current thread's queue, and \fBTcl_ThreadQueueEvent\fR
153adds an event to a queue in a specific thread.
154.IP [3]
155The event loop: in order to detect and process events, the application
156enters a loop that waits for events to occur, places them on the event
157queue, and then processes them.  Most applications will do this by
158calling the procedure \fBTcl_DoOneEvent\fR, which is described in a
159separate manual entry.
160.PP
161Most Tcl applications need not worry about any of the internals of
162the Tcl notifier.  However, the notifier now has enough flexibility
163to be retargeted either for a new platform or to use an external event
164loop (such as the Motif event loop, when Tcl is embedded in a Motif
165application).  The procedures \fBTcl_WaitForEvent\fR and
166\fBTcl_SetTimer\fR are normally implemented by Tcl, but may be
167replaced with new versions to retarget the notifier (the
168\fBTcl_InitNotifier\fR, \fBTcl_AlertNotifier\fR,
169\fBTcl_FinalizeNotifier\fR, \fBTcl_Sleep\fR,
170\fBTcl_CreateFileHandler\fR, and \fBTcl_DeleteFileHandler\fR must
171also be replaced; see CREATING A NEW NOTIFIER below for details).
172The procedures \fBTcl_ServiceAll\fR, \fBTcl_ServiceEvent\fR,
173\fBTcl_GetServiceMode\fR, and \fBTcl_SetServiceMode\fR are provided
174to help connect Tcl's event loop to an external event loop such as
175Motif's.
176.SH "NOTIFIER BASICS"
177.PP
178The easiest way to understand how the notifier works is to consider
179what happens when \fBTcl_DoOneEvent\fR is called.
180\fBTcl_DoOneEvent\fR is passed a \fIflags\fR argument that indicates
181what sort of events it is OK to process and also whether or not to
182block if no events are ready.  \fBTcl_DoOneEvent\fR does the following
183things:
184.IP [1]
185Check the event queue to see if it contains any events that can
186be serviced.  If so, service the first possible event, remove it
187from the queue, and return.  It does this by calling
188\fBTcl_ServiceEvent\fR and passing in the \fIflags\fR argument.
189.IP [2]
190Prepare to block for an event.  To do this, \fBTcl_DoOneEvent\fR
191invokes a \fIsetup procedure\fR in each event source.
192The event source will perform event-source specific initialization and
193possibly call \fBTcl_SetMaxBlockTime\fR to limit how long
194\fBTcl_WaitForEvent\fR will block if no new events occur.
195.IP [3]
196Call \fBTcl_WaitForEvent\fR.  This procedure is implemented differently
197on different platforms;  it waits for an event to occur, based on the
198information provided by the event sources.
199It may cause the application to block if \fItimePtr\fR specifies
200an interval other than 0.
201\fBTcl_WaitForEvent\fR returns when something has happened,
202such as a file becoming readable or the interval given by \fItimePtr\fR
203expiring.  If there are no events for \fBTcl_WaitForEvent\fR to
204wait for, so that it would block forever, then it returns immediately
205and \fBTcl_DoOneEvent\fR returns 0.
206.IP [4]
207Call a \fIcheck procedure\fR in each event source.  The check
208procedure determines whether any events of interest to this source
209occurred.  If so, the events are added to the event queue.
210.IP [5]
211Check the event queue to see if it contains any events that can
212be serviced.  If so, service the first possible event, remove it
213from the queue, and return.
214.IP [6]
215See if there are idle callbacks pending. If so, invoke all of them and
216return.
217.IP [7]
218Either return 0 to indicate that no events were ready, or go back to
219step [2] if blocking was requested by the caller.
220
221.SH "CREATING A NEW EVENT SOURCE"
222.PP
223An event source consists of three procedures invoked by the notifier,
224plus additional C procedures that are invoked by higher-level code
225to arrange for event-driven callbacks.  The three procedures called
226by the notifier consist of the setup and check procedures described
227above, plus an additional procedure that is invoked when an event
228is removed from the event queue for servicing.
229.PP
230The procedure \fBTcl_CreateEventSource\fR creates a new event source.
231Its arguments specify the setup procedure and check procedure for
232the event source.
233\fISetupProc\fR should match the following prototype:
234.CS
235typedef void Tcl_EventSetupProc(
236        ClientData \fIclientData\fR,
237        int \fIflags\fR);
238.CE
239The \fIclientData\fR argument will be the same as the \fIclientData\fR
240argument to \fBTcl_CreateEventSource\fR;  it is typically used to
241point to private information managed by the event source.
242The \fIflags\fR argument will be the same as the \fIflags\fR
243argument passed to \fBTcl_DoOneEvent\fR except that it will never
244be 0 (\fBTcl_DoOneEvent\fR replaces 0 with \fBTCL_ALL_EVENTS\fR).
245\fIFlags\fR indicates what kinds of events should be considered;
246if the bit corresponding to this event source is not set, the event
247source should return immediately without doing anything.  For
248example, the file event source checks for the \fBTCL_FILE_EVENTS\fR
249bit.
250.PP
251\fISetupProc\fR's job is to make sure that the application wakes up
252when events of the desired type occur.  This is typically done in a
253platform-dependent fashion.  For example, under Unix an event source
254might call \fBTcl_CreateFileHandler\fR; under Windows it might
255request notification with a Windows event.  For timer-driven event
256sources such as timer events or any polled event, the event source
257can call \fBTcl_SetMaxBlockTime\fR to force the application to wake
258up after a specified time even if no events have occurred.
259If no event source calls \fBTcl_SetMaxBlockTime\fR
260then \fBTcl_WaitForEvent\fR will wait as long as necessary for an
261event to occur; otherwise, it will only wait as long as the shortest
262interval passed to \fBTcl_SetMaxBlockTime\fR by one of the event
263sources.  If an event source knows that it already has events ready to
264report, it can request a zero maximum block time.  For example, the
265setup procedure for the X event source looks to see if there are
266events already queued.  If there are, it calls
267\fBTcl_SetMaxBlockTime\fR with a 0 block time so that
268\fBTcl_WaitForEvent\fR does not block if there is no new data on the X
269connection.
270The \fItimePtr\fR argument to \fBTcl_WaitForEvent\fR points to
271a structure that describes a time interval in seconds and
272microseconds:
273.CS
274typedef struct Tcl_Time {
275        long \fIsec\fR;
276        long \fIusec\fR;
277} Tcl_Time;
278.CE
279The \fIusec\fR field should be less than 1000000.
280.PP
281Information provided to \fBTcl_SetMaxBlockTime\fR
282is only used for the next call to \fBTcl_WaitForEvent\fR; it is
283discarded after \fBTcl_WaitForEvent\fR returns.
284The next time an event wait is done each of the event sources'
285setup procedures will be called again, and they can specify new
286information for that event wait.
287.PP
288If the application uses an external event loop rather than
289\fBTcl_DoOneEvent\fR, the event sources may need to call
290\fBTcl_SetMaxBlockTime\fR at other times.  For example, if a new event
291handler is registered that needs to poll for events, the event source
292may call \fBTcl_SetMaxBlockTime\fR to set the block time to zero to
293force the external event loop to call Tcl.  In this case,
294\fBTcl_SetMaxBlockTime\fR invokes \fBTcl_SetTimer\fR with the shortest
295interval seen since the last call to \fBTcl_DoOneEvent\fR or
296\fBTcl_ServiceAll\fR.
297.PP
298In addition to the generic procedure \fBTcl_SetMaxBlockTime\fR, other
299platform-specific procedures may also be available for
300\fIsetupProc\fR, if there is additional information needed by
301\fBTcl_WaitForEvent\fR on that platform.  For example, on Unix systems
302the \fBTcl_CreateFileHandler\fR interface can be used to wait for file events.
303.PP
304The second procedure provided by each event source is its check
305procedure, indicated by the \fIcheckProc\fR argument to
306\fBTcl_CreateEventSource\fR.  \fICheckProc\fR must match the
307following prototype:
308.CS
309typedef void Tcl_EventCheckProc(
310        ClientData \fIclientData\fR,
311        int \fIflags\fR);
312.CE
313The arguments to this procedure are the same as those for \fIsetupProc\fR.
314\fBCheckProc\fR is invoked by \fBTcl_DoOneEvent\fR after it has waited
315for events.  Presumably at least one event source is now prepared to
316queue an event.  \fBTcl_DoOneEvent\fR calls each of the event sources
317in turn, so they all have a chance to queue any events that are ready.
318The check procedure does two things.  First, it must see if any events
319have triggered.  Different event sources do this in different ways.
320.PP
321If an event source's check procedure detects an interesting event, it
322must add the event to Tcl's event queue.  To do this, the event source
323calls \fBTcl_QueueEvent\fR.  The \fIevPtr\fR argument is a pointer to
324a dynamically allocated structure containing the event (see below for
325more information on memory management issues).  Each event source can
326define its own event structure with whatever information is relevant
327to that event source.  However, the first element of the structure
328must be a structure of type \fBTcl_Event\fR, and the address of this
329structure is used when communicating between the event source and the
330rest of the notifier.  A \fBTcl_Event\fR has the following definition:
331.CS
332typedef struct {
333    Tcl_EventProc *\fIproc\fR;
334    struct Tcl_Event *\fInextPtr\fR;
335} Tcl_Event;
336.CE
337The event source must fill in the \fIproc\fR field of
338the event before calling \fBTcl_QueueEvent\fR.
339The \fInextPtr\fR is used to link together the events in the queue
340and should not be modified by the event source.
341.PP
342An event may be added to the queue at any of three positions, depending
343on the \fIposition\fR argument to \fBTcl_QueueEvent\fR:
344.IP \fBTCL_QUEUE_TAIL\fR 24
345Add the event at the back of the queue, so that all other pending
346events will be serviced first.  This is almost always the right
347place for new events.
348.IP \fBTCL_QUEUE_HEAD\fR 24
349Add the event at the front of the queue, so that it will be serviced
350before all other queued events.
351.IP \fBTCL_QUEUE_MARK\fR 24
352Add the event at the front of the queue, unless there are other
353events at the front whose position is \fBTCL_QUEUE_MARK\fR;  if so,
354add the new event just after all other \fBTCL_QUEUE_MARK\fR events.
355This value of \fIposition\fR is used to insert an ordered sequence of
356events at the front of the queue, such as a series of
357Enter and Leave events synthesized during a grab or ungrab operation
358in Tk.
359.PP
360When it is time to handle an event from the queue (steps 1 and 4
361above) \fBTcl_ServiceEvent\fR will invoke the \fIproc\fR specified
362in the first queued \fBTcl_Event\fR structure.
363\fIProc\fR must match the following prototype:
364.CS
365typedef int Tcl_EventProc(
366        Tcl_Event *\fIevPtr\fR,
367        int \fIflags\fR);
368.CE
369The first argument to \fIproc\fR is a pointer to the event, which will
370be the same as the first argument to the \fBTcl_QueueEvent\fR call that
371added the event to the queue.
372The second argument to \fIproc\fR is the \fIflags\fR argument for the
373current call to \fBTcl_ServiceEvent\fR;  this is used by the event source
374to return immediately if its events are not relevant.
375.PP
376It is up to \fIproc\fR to handle the event, typically by invoking
377one or more Tcl commands or C-level callbacks.
378Once the event source has finished handling the event it returns 1
379to indicate that the event can be removed from the queue.
380If for some reason the event source decides that the event cannot
381be handled at this time, it may return 0 to indicate that the event
382should be deferred for processing later;  in this case \fBTcl_ServiceEvent\fR
383will go on to the next event in the queue and attempt to service it.
384There are several reasons why an event source might defer an event.
385One possibility is that events of this type are excluded by the
386\fIflags\fR argument.
387For example, the file event source will always return 0 if the
388\fBTCL_FILE_EVENTS\fR bit is not set in \fIflags\fR.
389Another example of deferring events happens in Tk if
390\fBTk_RestrictEvents\fR has been invoked to defer certain kinds
391of window events.
392.PP
393When \fIproc\fR returns 1, \fBTcl_ServiceEvent\fR will remove the
394event from the event queue and free its storage.
395Note that the storage for an event must be allocated by
396the event source (using \fBTcl_Alloc\fR or the Tcl macro \fBckalloc\fR)
397before calling \fBTcl_QueueEvent\fR, but it
398will be freed by \fBTcl_ServiceEvent\fR, not by the event source.
399.PP
400Threaded applications work in a
401similar manner, except that there is a separate event queue for
402each thread containing a Tcl interpreter.
403Calling \fBTcl_QueueEvent\fR in a multithreaded application adds
404an event to the current thread's queue.
405To add an event to another thread's queue, use \fBTcl_ThreadQueueEvent\fR.
406\fBTcl_ThreadQueueEvent\fR accepts as an argument a Tcl_ThreadId argument,
407which uniquely identifies a thread in a Tcl application.  To obtain the
408Tcl_ThreadID for the current thread, use the \fBTcl_GetCurrentThread\fR
409procedure.  (A thread would then need to pass this identifier to other
410threads for those threads to be able to add events to its queue.)
411After adding an event to another thread's queue, you then typically
412need to call \fBTcl_ThreadAlert\fR to
413.QW "wake up"
414that thread's notifier to alert it to the new event.
415.PP
416\fBTcl_DeleteEvents\fR can be used to explicitly remove one or more
417events from the event queue.  \fBTcl_DeleteEvents\fR calls \fIproc\fR
418for each event in the queue, deleting those for with the procedure
419returns 1.  Events for which the procedure returns 0 are left in the
420queue.  \fIProc\fR should match the following prototype:
421.CS
422typedef int Tcl_EventDeleteProc(
423        Tcl_Event *\fIevPtr\fR,
424        ClientData \fIclientData\fR);
425.CE
426The \fIclientData\fR argument will be the same as the \fIclientData\fR
427argument to \fBTcl_DeleteEvents\fR; it is typically used to point to
428private information managed by the event source.  The \fIevPtr\fR will
429point to the next event in the queue.
430.PP
431\fBTcl_DeleteEventSource\fR deletes an event source.  The \fIsetupProc\fR,
432\fIcheckProc\fR, and \fIclientData\fR arguments must exactly match those
433provided to the \fBTcl_CreateEventSource\fR for the event source to be deleted.
434If no such source exists, \fBTcl_DeleteEventSource\fR has no effect.
435
436.SH "CREATING A NEW NOTIFIER"
437.PP
438The notifier consists of all the procedures described in this manual
439entry, plus \fBTcl_DoOneEvent\fR and \fBTcl_Sleep\fR, which are
440available on all platforms, and \fBTcl_CreateFileHandler\fR and
441\fBTcl_DeleteFileHandler\fR, which are Unix-specific.  Most of these
442procedures are generic, in that they are the same for all notifiers.
443However, none of the procedures are notifier-dependent:
444\fBTcl_InitNotifier\fR, \fBTcl_AlertNotifier\fR,
445\fBTcl_FinalizeNotifier\fR, \fBTcl_SetTimer\fR, \fBTcl_Sleep\fR,
446\fBTcl_WaitForEvent\fR, \fBTcl_CreateFileHandler\fR,
447\fBTcl_DeleteFileHandler\fR and \fBTcl_ServiceModeHook\fR.  To support a
448new platform or to integrate Tcl with an application-specific event loop,
449you must write new versions of these procedures.
450.PP
451\fBTcl_InitNotifier\fR initializes the notifier state and returns
452a handle to the notifier state.  Tcl calls this
453procedure when initializing a Tcl interpreter.  Similarly,
454\fBTcl_FinalizeNotifier\fR shuts down the notifier, and is
455called by \fBTcl_Finalize\fR when shutting down a Tcl interpreter.
456.PP
457\fBTcl_WaitForEvent\fR is the lowest-level procedure in the notifier;
458it is responsible for waiting for an
459.QW interesting
460event to occur or
461for a given time to elapse.  Before \fBTcl_WaitForEvent\fR is invoked,
462each of the event sources' setup procedure will have been invoked.
463The \fItimePtr\fR argument to
464\fBTcl_WaitForEvent\fR gives the maximum time to block for an event,
465based on calls to \fBTcl_SetMaxBlockTime\fR made by setup procedures
466and on other information (such as the \fBTCL_DONT_WAIT\fR bit in
467\fIflags\fR).
468.PP
469Ideally, \fBTcl_WaitForEvent\fR should only wait for an event
470to occur; it should not actually process the event in any way.
471Later on, the
472event sources will process the raw events and create Tcl_Events on
473the event queue in their \fIcheckProc\fR procedures.
474However, on some platforms (such as Windows) this is not possible;
475events may be processed in \fBTcl_WaitForEvent\fR, including queuing
476Tcl_Events and more (for example, callbacks for native widgets may be
477invoked).  The return value from \fBTcl_WaitForEvent\fR must be either
4780, 1, or \-1.  On platforms such as Windows where events get processed in
479\fBTcl_WaitForEvent\fR, a return value of 1 means that there may be more
480events still pending that have not been processed.  This is a sign to the
481caller that it must call \fBTcl_WaitForEvent\fR again if it wants all
482pending events to be processed. A 0 return value means that calling
483\fBTcl_WaitForEvent\fR again will not have any effect: either this is a
484platform where \fBTcl_WaitForEvent\fR only waits without doing any event
485processing, or \fBTcl_WaitForEvent\fR knows for sure that there are no
486additional events to process (e.g. it returned because the time
487elapsed).  Finally, a return value of \-1 means that the event loop is
488no longer operational and the application should probably unwind and
489terminate.  Under Windows this happens when a WM_QUIT message is received;
490under Unix it happens when \fBTcl_WaitForEvent\fR would have waited
491forever because there were no active event sources and the timeout was
492infinite.
493.PP
494\fBTcl_AlertNotifier\fR is used in multithreaded applications to allow
495any thread to
496.QW "wake up"
497the notifier to alert it to new events on its
498queue.  \fBTcl_AlertNotifier\fR requires as an argument the notifier
499handle returned by \fBTcl_InitNotifier\fR.
500.PP
501If the notifier will be used with an external event loop, then it must
502also support the \fBTcl_SetTimer\fR interface.  \fBTcl_SetTimer\fR is
503invoked by \fBTcl_SetMaxBlockTime\fR whenever the maximum blocking
504time has been reduced.  \fBTcl_SetTimer\fR should arrange for the
505external event loop to invoke \fBTcl_ServiceAll\fR after the specified
506interval even if no events have occurred.  This interface is needed
507because \fBTcl_WaitForEvent\fR is not invoked when there is an external
508event loop.  If the
509notifier will only be used from \fBTcl_DoOneEvent\fR, then
510\fBTcl_SetTimer\fR need not do anything.
511.PP
512\fBTcl_ServiceModeHook\fR is called by the platform-independent portion
513of the notifier when client code makes a call to
514\fBTcl_SetServiceMode\fR. This hook is provided to support operating
515systems that require special event handling when the application is in
516a modal loop (the Windows notifier, for instance, uses this hook to
517create a communication window).
518.PP
519On Unix systems, the file event source also needs support from the
520notifier.  The file event source consists of the
521\fBTcl_CreateFileHandler\fR and \fBTcl_DeleteFileHandler\fR
522procedures, which are described in the \fBTcl_CreateFileHandler\fR
523manual page.
524.PP
525The \fBTcl_Sleep\fR and \fBTcl_DoOneEvent\fR interfaces are described
526in their respective manual pages.
527.PP
528The easiest way to create a new notifier is to look at the code
529for an existing notifier, such as the files \fBunix/tclUnixNotfy.c\fR
530or \fBwin/tclWinNotify.c\fR in the Tcl source distribution.
531
532.SH "REPLACING THE NOTIFIER"
533.PP
534A notifier that has been written according to the conventions above
535can also be installed in a running process in place of the standard
536notifier.  This mechanism is used so that a single executable can be
537used (with the standard notifier) as a stand-alone program and reused
538(with a replacement notifier in a loadable extension) as an extension
539to another program, such as a Web browser plugin.
540.PP
541To do this, the extension makes a call to \fBTcl_SetNotifier\fR
542passing a pointer to a \fBTcl_NotifierProcs\fR data structure.  The
543structure has the following layout:
544.CS
545typedef struct Tcl_NotifierProcs {
546    Tcl_SetTimerProc *setTimerProc;
547    Tcl_WaitForEventProc *waitForEventProc;
548    Tcl_CreateFileHandlerProc *createFileHandlerProc;
549    Tcl_DeleteFileHandlerProc *deleteFileHandlerProc;
550    Tcl_InitNotifierProc *initNotifierProc;
551    Tcl_FinalizeNotifierProc *finalizeNotifierProc;
552    Tcl_AlertNotifierProc *alertNotifierProc;
553    Tcl_ServiceModeHookProc *serviceModeHookProc;
554} Tcl_NotifierProcs;
555.CE
556Following the call to \fBTcl_SetNotifier\fR, the pointers given in
557the \fBTcl_NotifierProcs\fR structure replace whatever notifier had
558been installed in the process.
559.PP
560It is extraordinarily unwise to replace a running notifier. Normally,
561\fBTcl_SetNotifier\fR should be called at process initialization time
562before the first call to \fBTcl_InitNotifier\fR.
563
564.SH "EXTERNAL EVENT LOOPS"
565.PP
566The notifier interfaces are designed so that Tcl can be embedded into
567applications that have their own private event loops.  In this case,
568the application does not call \fBTcl_DoOneEvent\fR except in the case
569of recursive event loops such as calls to the Tcl commands \fBupdate\fR
570or \fBvwait\fR.  Most of the time is spent in the external event loop
571of the application.  In this case the notifier must arrange for the
572external event loop to call back into Tcl when something
573happens on the various Tcl event sources.  These callbacks should
574arrange for appropriate Tcl events to be placed on the Tcl event queue.
575.PP
576Because the external event loop is not calling \fBTcl_DoOneEvent\fR on
577a regular basis, it is up to the notifier to arrange for
578\fBTcl_ServiceEvent\fR to be called whenever events are pending on the
579Tcl event queue.  The easiest way to do this is to invoke
580\fBTcl_ServiceAll\fR at the end of each callback from the external
581event loop.  This will ensure that all of the event sources are
582polled, any queued events are serviced, and any pending idle handlers
583are processed before returning control to the application.  In
584addition, event sources that need to poll for events can call
585\fBTcl_SetMaxBlockTime\fR to force the external event loop to call
586Tcl even if no events are available on the system event queue.
587.PP
588As a side effect of processing events detected in the main external
589event loop, Tcl may invoke \fBTcl_DoOneEvent\fR to start a recursive event
590loop in commands like \fBvwait\fR.  \fBTcl_DoOneEvent\fR will invoke
591the external event loop, which will result in callbacks as described
592in the preceding paragraph, which will result in calls to
593\fBTcl_ServiceAll\fR.  However, in these cases it is undesirable to
594service events in \fBTcl_ServiceAll\fR.  Servicing events there is
595unnecessary because control will immediately return to the
596external event loop and hence to \fBTcl_DoOneEvent\fR, which can
597service the events itself.  Furthermore, \fBTcl_DoOneEvent\fR is
598supposed to service only a single event, whereas \fBTcl_ServiceAll\fR
599normally services all pending events.  To handle this situation,
600\fBTcl_DoOneEvent\fR sets a flag for \fBTcl_ServiceAll\fR
601that causes it to return without servicing any events.
602This flag is called the \fIservice mode\fR;
603\fBTcl_DoOneEvent\fR restores it to its previous value before it returns.
604.PP
605In some cases, however, it may be necessary for \fBTcl_ServiceAll\fR
606to service events
607even when it has been invoked from \fBTcl_DoOneEvent\fR.  This happens
608when there is yet another recursive event loop invoked via an
609event handler called by \fBTcl_DoOneEvent\fR (such as one that is
610part of a native widget).  In this case, \fBTcl_DoOneEvent\fR may not
611have a chance to service events so \fBTcl_ServiceAll\fR must service
612them all.  Any recursive event loop that calls an external event
613loop rather than \fBTcl_DoOneEvent\fR must reset the service mode so
614that all events get processed in \fBTcl_ServiceAll\fR.  This is done
615by invoking the \fBTcl_SetServiceMode\fR procedure.  If
616\fBTcl_SetServiceMode\fR is passed \fBTCL_SERVICE_NONE\fR, then calls
617to \fBTcl_ServiceAll\fR will return immediately without processing any
618events.  If \fBTcl_SetServiceMode\fR is passed \fBTCL_SERVICE_ALL\fR,
619then calls to \fBTcl_ServiceAll\fR will behave normally.
620\fBTcl_SetServiceMode\fR returns the previous value of the service
621mode, which should be restored when the recursive loop exits.
622\fBTcl_GetServiceMode\fR returns the current value of the service
623mode.
624
625.SH "SEE ALSO"
626\fBTcl_CreateFileHandler\fR, \fBTcl_DeleteFileHandler\fR, \fBTcl_Sleep\fR,
627\fBTcl_DoOneEvent\fR, \fBThread(3)\fR
628.SH KEYWORDS
629event, notifier, event queue, event sources, file events, timer, idle, service mode, threads
Note: See TracBrowser for help on using the repository browser.