xref: /NextBSD/lib/libnotify/notify.h (revision 33da5adc555b3bc29986eeadca03829e4ad06b1e)
1 /*
2  * Copyright (c) 2003-2010 Apple Inc. All rights reserved.
3  *
4  * @APPLE_LICENSE_HEADER_START@
5  *
6  * Portions Copyright (c) 2003-2010 Apple Inc.  All Rights Reserved.
7  *
8  * This file contains Original Code and/or Modifications of Original Code
9  * as defined in and that are subject to the Apple Public Source License
10  * Version 2.0 (the 'License'). You may not use this file except in
11  * compliance with the License. Please obtain a copy of the License at
12  * http://www.opensource.apple.com/apsl/ and read it before using this
13  * file.
14  *
15  * The Original Code and all software distributed under the License are
16  * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
17  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
18  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
19  * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
20  * Please see the License for the specific language governing rights and
21  * limitations under the License.
22  *
23  * @APPLE_LICENSE_HEADER_END@
24  */
25 
26 #ifndef __NOTIFICATION_H__
27 #define __NOTIFICATION_H__
28 
29 #include <stdbool.h>
30 #include <sys/cdefs.h>
31 #include <stdint.h>
32 #include <mach/message.h>
33 #include <Availability.h>
34 #ifdef __BLOCKS__
35 #include <dispatch/dispatch.h>
36 #endif /* __BLOCKS__ */
37 
38 /*! @header
39  * These routines allow processes to exchange stateless notification events.
40  * Processes post notifications to a single system-wide notification server,
41  * which then distributes notifications to client processes that have
42  * registered to receive those notifications, including processes run by
43  * other users.
44  *
45  * Notifications are associated with names in a namespace shared by all
46  * clients of the system.  Clients may post notifications for names, and
47  * may monitor names for posted notifications.  Clients may request
48  * notification delivery by a number of different methods.
49  *
50  * Clients desiring to monitor names in the notification system must
51  * register with the system, providing a name and other information
52  * required for the desired notification delivery method.  Clients are
53  * given an integer token representing the registration.
54  *
55  * Note that the kernel provides limited queues for mach message and file
56  * descriptor messages.  It is important to make sure that clients read
57  * mach ports and file descriptors frequently to prevent messages from
58  * being lost due to resource limitations.  Clients that use signal-based
59  * notification should be aware that signals are not delivered to
60  * a process while it is running in a signal handler.  This may affect
61  * the delivery of signals in close succession.
62  *
63  * Notifications may be coalesced in some cases.  Multiple events posted
64  * for a name in rapid succession may result in a single notification sent
65  * to clients registered for notification for that name.  Clients checking
66  * for changes using the notify_check() routine cannot determine if
67  * more than one event pas been posted since a previous call to
68  * notify_check() for that name.
69  *
70  * "False positives" may occur in notify_check() when used with a token
71  * generated by notify_register_check() due to implementation constraints.
72  * This behavior may vary in future releases.
73  *
74  * Synchronization between two processes may be achieved using the
75  * notify_set_state() and notify_get_state() routines.
76  */
77 
78 /*! @defineblock Status Codes
79  * Status codes returned by the API.
80  */
81 #define NOTIFY_STATUS_OK 0
82 #define NOTIFY_STATUS_INVALID_NAME 1
83 #define NOTIFY_STATUS_INVALID_TOKEN 2
84 #define NOTIFY_STATUS_INVALID_PORT 3
85 #define NOTIFY_STATUS_INVALID_FILE 4
86 #define NOTIFY_STATUS_INVALID_SIGNAL 5
87 #define NOTIFY_STATUS_INVALID_REQUEST 6
88 #define NOTIFY_STATUS_NOT_AUTHORIZED 7
89 #define NOTIFY_STATUS_FAILED 1000000
90 /*! @/defineblock */
91 
92 /*!
93  * Flag bits used for registration.
94  */
95 #define NOTIFY_REUSE 0x00000001
96 
97 
98 /*!
99  * Token values are zero or positive integers.
100  * NOTIFY_TOKEN_INVALID is useful as an initial value for
101  * a token value passed as an in/out parameter to one of
102  * the registration routines below.
103  */
104 #define NOTIFY_TOKEN_INVALID -1
105 
106 __BEGIN_DECLS
107 
108 /*!
109  * Post a notification for a name.
110  *
111  * This is the only call that is required for a notification producer.
112  * Returns status.
113  */
114 uint32_t notify_post(const char *name);
115 
116 
117 #ifdef __BLOCKS__
118 typedef void (^notify_handler_t)(int token);
119 
120 /*!
121  * @function   notify_register
122  * @abstract   Request notification delivery to a dispatch queue.
123  * @discussion When notifications are received by the process, the notify
124  *             subsystem will deliver the registered Block to the target
125  *             dispatch queue.  Notification blocks are not re-entrant,
126  *             and subsequent notification Blocks will not be delivered
127  *             for the same registration until the previous Block has
128  *             returned.
129  * @param name (input) The notification name.
130  * @param out_token (output) The registration token.
131  * @param queue (input) The dispatch queue to which the Block is submitted.
132  *              The dispatch queue is retained by the notify subsystem while
133  *              the notification is registered, and will be released when
134  *              notification is canceled.
135  * @param block (input) The Block to invoke on the dispatch queue in response
136  *              to a notification.  The notification token is passed to the
137  *              Block as an argument so that the callee can modify the state
138  *              of the notification or cancel the registration.
139  * @result Returns status.
140  */
141 uint32_t notify_register_dispatch(const char *name, int *out_token, dispatch_queue_t queue, notify_handler_t handler)
142 __OSX_AVAILABLE_STARTING(__MAC_10_6,__IPHONE_3_2);
143 #endif /* __BLOCKS__ */
144 
145 /*!
146  * Creates a registration token be used with notify_check(),
147  * but no active notifications will be delivered.
148  *
149  * @param name
150  *    (input) notification name
151  * @param out_token
152  *    (output) registration token
153  * @result Returns status.
154  */
155 uint32_t notify_register_check(const char *name, int *out_token);
156 
157 /*!
158  * Request notification delivery by UNIX signal.
159  *
160  * A client may request signal notification for multiple names.  After a signal
161  * is delivered, the notify_check() routine may be called with each notification
162  * token to determine which name (if any) generated the signal notification.
163  *
164  * @param name (input) notification name
165  * @param sig (input) signal number (see signal(3))
166  * @param out_token (output) notification token
167  * @result Returns status.
168  */
169 uint32_t notify_register_signal(const char *name, int sig, int *out_token);
170 
171 /*!
172  * Request notification by mach message.
173  *
174  * Notifications are delivered by an empty message sent to a mach port.
175  * By default, a new port is allocated and a pointer to it is returned
176  * as the value of "notify_port".  A mach port previously returned by a
177  * call to this routine may be used for notifications if a pointer to that
178  * port is passed in to the routine and NOTIFY_REUSE is set in the flags
179  * parameter.  The notification service must be able to extract send
180  * rights to the port.
181  *
182  * Note that the kernel limits the size of the message queue for any port.
183  * If it is important that notifications should not be lost due to queue
184  * overflow, clients should service messages quickly, and be careful about
185  * using the same port for notifications for more than one name.
186  *
187  * A notification message has an empty message body.  The msgh_id field
188  * in the mach message header will have the value of the notification
189  * token.  If a port is reused for multiple notification registrations,
190  * the msgh_id value may be used to determine which name generated
191  * the notification.
192  *
193  * @param name
194  *     (input) notification name
195  * @param  out_token
196  *     (output) notification token
197  * @param  notify_port
198  *     (input/output) pointer to a mach port
199  * @result Returns status.
200  */
201 uint32_t notify_register_mach_port(const char *name, mach_port_t *notify_port, int flags, int *out_token);
202 
203 /*
204  * Request notification by a write to a file descriptor.
205  *
206  * Notifications are delivered by a write to a file descriptor.
207  * By default, a new file descriptor is created and a pointer to it
208  * is returned as the value of "notify_fd".  A file descriptor created
209  * by a previous call to this routine may be used for notifications if
210  * a pointer to that file descriptor is passed in to the routine and
211  * NOTIFY_REUSE is set in the flags parameter.
212  *
213  * Note that the kernel limits the buffer space for queued writes on a
214  * file descriptor.  If it is important that notifications should not be
215  * lost due to queue overflow, clients should service messages quickly,
216  * and be careful about using the same file descriptor for notifications
217  * for more than one name.
218  *
219  * Notifications are delivered by an integer value written to the
220  * file descriptor.  The value will match the notification token
221  * for which the notification was generated.
222  *
223  * @param name
224  *     (input) notification name
225  * @param out_token
226  *     (output) notification token
227  * @param notify_fd
228  *     (input/output) pointer to a file descriptor
229  * @result Returns status.
230  */
231 uint32_t notify_register_file_descriptor(const char *name, int *notify_fd, int flags, int *out_token);
232 
233 /*!
234  * Check if any notifications have been posted.
235  *
236  * Output parameter check is set to 0 for false, 1 for true.  Returns status.
237  * check is set to true the first time notify_check is called for a token.
238  * Subsequent calls set check to true when notifications have been posted for
239  * the name associated with the notification token.  This routine is independent
240  * of notify_post().  That is, check will be true if an application calls
241  * notify_post() for a name and then calls notify_check() for a token associated
242  * with that name.
243  *
244  * @param token
245  *     (input)notification token
246  * @param check
247  *     (output) true/false indication
248  * @result Returns status.
249  */
250 uint32_t notify_check(int token, int *check);
251 
252 /*!
253  * Cancel notification and free resources associated with a notification
254  * token.  Mach ports and file descriptor associated with a token are released
255  * (deallocated or closed) when all registration tokens associated with
256  * the port or file descriptor have been cancelled.
257  *
258  * @param token
259  *     (input) notification token
260  * @result Returns status.
261  */
262 uint32_t notify_cancel(int token);
263 
264 /*!
265  * Suspend delivery of notifications for a token. Notifications for this token will be
266  * pended and coalesced, then delivered following a matching call to notify_resume.
267  * Calls to notify_suspend may be nested.  Notifications remain suspended until
268  * an equal number of calls have been made to notify_resume.
269  *
270  * @param token
271  *     (input) notification token
272  * @result Returns status.
273  */
274 uint32_t notify_suspend(int token)
275 __OSX_AVAILABLE_STARTING(__MAC_10_6,__IPHONE_4_0);
276 
277 /*!
278  * Removes one level of suspension for a token previously suspended
279  * by a call to notify_suspend.  Notifications will resume when a matching
280  * call to notify_resume is made for each previous call to notify_suspend.
281  * Notifications posted while a token is suspended are coalesced into
282  * a single notification sent following a resumption.
283  *
284  * @param token
285  *     (input) notification token
286  * @result Returns status.
287  */
288 uint32_t notify_resume(int token)
289 __OSX_AVAILABLE_STARTING(__MAC_10_6,__IPHONE_4_0);
290 
291 /*!
292  * Set or get a state value associated with a notification token.
293  * Each key in the notification namespace has an associated integer value available
294  * for use by clients as for application-specific purposes.  A common usage is to
295  * allow two processes or threads to synchronize their activities.  For example, a
296  * server process may need send a notification when a resource becomes available.
297  * A client process can register for the notification, but when it starts up it will
298  * not know whether the resource is available.  The server can set the state value,
299  * and the client can check the value at startup time to synchronize with the server.
300  *
301  * Set the 64-bit integer state value.
302  *
303  * @param token
304  *     (input) notification token
305  * @param state64
306  *     (input) 64-bit unsigned integer value
307  * @result Returns status.
308  */
309 uint32_t notify_set_state(int token, uint64_t state64)
310 __OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
311 
312 /*!
313  * Get the 64-bit integer state value.
314  *
315  * @param token
316  *     (input) notification token
317  * @param state64
318  *     (output) 64-bit unsigned integer value
319  * @result Returns status.
320  */
321 uint32_t notify_get_state(int token, uint64_t *state64)
322 __OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
323 
324 /*!
325  * Determine if a token is valid (currently registered).
326  * Negative integer values are always invalid.  Positive or
327  * zero values are valid only if they are associated with an
328  * existing registratiom.
329  *
330  * @param val
331  *     (input) integer value
332  * @result Returns true if the value is a valid token, false otherwise.
333  */
334 bool notify_is_valid_token(int val)
335 __OSX_AVAILABLE_STARTING(__MAC_10_10,__IPHONE_8_0);
336 
337 __END_DECLS
338 
339 #endif /* __NOTIFICATION_H__ */
340