VirtualBox

source: vbox/trunk/include/iprt/semaphore.h@ 28700

Last change on this file since 28700 was 28700, checked in by vboxsync, 15 years ago

iprt/semaphore.h: RTEvent*Signal() - ring-0 clarification.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 42.8 KB
Line 
1/** @file
2 * IPRT - Semaphore.
3 */
4
5/*
6 * Copyright (C) 2006-2007 Sun Microsystems, Inc.
7 *
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.virtualbox.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License (GPL) as published by the Free Software
12 * Foundation, in version 2 as it comes in the "COPYING" file of the
13 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
14 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * The contents of this file may alternatively be used under the terms
17 * of the Common Development and Distribution License Version 1.0
18 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
19 * VirtualBox OSE distribution, in which case the provisions of the
20 * CDDL are applicable instead of those of the GPL.
21 *
22 * You may elect to license modified versions of this file under the
23 * terms and conditions of either the GPL or the CDDL or both.
24 *
25 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
26 * Clara, CA 95054 USA or visit http://www.sun.com if you need
27 * additional information or have any questions.
28 */
29
30#ifndef ___iprt_semaphore_h
31#define ___iprt_semaphore_h
32
33#include <iprt/cdefs.h>
34#include <iprt/types.h>
35#if defined(RT_LOCK_STRICT_ORDER) && defined(IN_RING3)
36# include <iprt/lockvalidator.h>
37#endif
38
39
40RT_C_DECLS_BEGIN
41
42/** @defgroup grp_rt_sems RTSem - Semaphores
43 *
44 * This module implements all kinds of event and mutex semaphores; in addition
45 * to these, IPRT implements "critical sections", which are fast recursive
46 * mutexes (see @ref grp_rt_critsect ). C++ users may find @ref grp_rt_lock
47 * interesting.
48 *
49 * @ingroup grp_rt
50 * @{
51 */
52
53
54/** @defgroup grp_rt_sems_event RTSemEvent - Single Release Event Semaphores
55 *
56 * Event semaphores can be used for inter-thread communication when one thread
57 * wants to notify another thread that something happened. A thread can block
58 * ("wait") on an event semaphore until it is signalled by another thread; see
59 * RTSemEventCreate, RTSemEventSignal and RTSemEventWait.
60 *
61 * @{ */
62
63/**
64 * Create an event semaphore.
65 *
66 * @returns iprt status code.
67 * @param phEventSem Where to store the handle to the newly created
68 * event semaphore.
69 */
70RTDECL(int) RTSemEventCreate(PRTSEMEVENT phEventSem);
71
72/**
73 * Create an event semaphore.
74 *
75 * @returns iprt status code.
76 * @param phEventSem Where to store the handle to the newly created
77 * event semaphore.
78 * @param fFlags Flags, any combination of the
79 * RTSEMEVENT_FLAGS_XXX \#defines.
80 * @param hClass The class (no reference consumed). Since we
81 * don't do order checks on event semaphores, the
82 * use of the class is limited to controlling the
83 * timeout threshold for deadlock detection.
84 * @param pszNameFmt Name format string for the lock validator,
85 * optional (NULL). Max length is 32 bytes.
86 * @param ... Format string arguments.
87 */
88RTDECL(int) RTSemEventCreateEx(PRTSEMEVENT phEventSem, uint32_t fFlags, RTLOCKVALCLASS hClass, const char *pszNameFmt, ...);
89
90/** @name RTSemMutexCreateEx flags
91 * @{ */
92/** Disables lock validation. */
93#define RTSEMEVENT_FLAGS_NO_LOCK_VAL UINT32_C(0x00000001)
94/** @} */
95
96/**
97 * Destroy an event semaphore.
98 *
99 * @returns iprt status code.
100 * @param hEventSem Handle of the event sempahore. NIL_RTSEMEVENT
101 * is quitely ignored (VINF_SUCCESS).
102 */
103RTDECL(int) RTSemEventDestroy(RTSEMEVENT hEventSem);
104
105/**
106 * Signal an event semaphore.
107 *
108 * The event semaphore will be signaled and automatically reset after exactly
109 * one thread have successfully returned from RTSemEventWait() after
110 * waiting/polling on that semaphore.
111 *
112 * @returns iprt status code.
113 * @param hEventSem The event semaphore to signal.
114 *
115 * @remarks ring-0: This works when preemption is disabled. However it is
116 * system specific whether it works in interrupt context or with
117 * interrupts disabled.
118 */
119RTDECL(int) RTSemEventSignal(RTSEMEVENT hEventSem);
120
121/**
122 * Wait for the event semaphore to be signaled, resume on interruption.
123 *
124 * This function will resume if the wait is interrupted by an async system event
125 * (like a unix signal) or similar.
126 *
127 * @returns iprt status code.
128 * Will not return VERR_INTERRUPTED.
129 * @param hEventSem The event semaphore to wait on.
130 * @param cMillies Number of milliseconds to wait.
131 */
132RTDECL(int) RTSemEventWait(RTSEMEVENT hEventSem, RTMSINTERVAL cMillies);
133
134/**
135 * Wait for the event semaphore to be signaled, return on interruption.
136 *
137 * This function will not resume the wait if interrupted.
138 *
139 * @returns iprt status code.
140 * @param hEventSem The event semaphore to wait on.
141 * @param cMillies Number of milliseconds to wait.
142 */
143RTDECL(int) RTSemEventWaitNoResume(RTSEMEVENT hEventSem, RTMSINTERVAL cMillies);
144
145/**
146 * Sets the signaller thread to one specific thread.
147 *
148 * This is only used for validating usage and deadlock detection. When used
149 * after calls to RTSemEventAddSignaller, the specified thread will be the only
150 * signalling thread.
151 *
152 * @param hEventSem The event semaphore.
153 * @param hThread The thread that will signal it. Pass
154 * NIL_RTTHREAD to indicate that there is no
155 * special signalling thread.
156 */
157RTDECL(void) RTSemEventSetSignaller(RTSEMEVENT hEventSem, RTTHREAD hThread);
158
159/**
160 * To add more signalling threads.
161 *
162 * First call RTSemEventSetSignaller then add further threads with this.
163 *
164 * @param hEventSem The event semaphore.
165 * @param hThread The thread that will signal it. NIL_RTTHREAD is
166 * not accepted.
167 */
168RTDECL(void) RTSemEventAddSignaller(RTSEMEVENT hEventSem, RTTHREAD hThread);
169
170/**
171 * To remove a signalling thread.
172 *
173 * Reverts work done by RTSemEventAddSignaller and RTSemEventSetSignaller.
174 *
175 * @param hEventSem The event semaphore.
176 * @param hThread A previously added thread.
177 */
178RTDECL(void) RTSemEventRemoveSignaller(RTSEMEVENT hEventSem, RTTHREAD hThread);
179
180/** @} */
181
182
183/** @defgroup grp_rt_sems_event_multi RTSemEventMulti - Multiple Release Event Semaphores
184 *
185 * A variant of @ref grp_rt_sems_event where all threads will be unblocked when
186 * signalling the semaphore.
187 *
188 * @{ */
189
190/**
191 * Creates a multiple release event semaphore.
192 *
193 * @returns iprt status code.
194 * @param phEventMultiSem Where to store the handle to the newly created
195 * multiple release event semaphore.
196 */
197RTDECL(int) RTSemEventMultiCreate(PRTSEMEVENTMULTI phEventMultiSem);
198
199/**
200 * Creates a multiple release event semaphore.
201 *
202 * @returns iprt status code.
203 * @param phEventMultiSem Where to store the handle to the newly created
204 * multiple release event semaphore.
205 * @param fFlags Flags, any combination of the
206 * RTSEMEVENTMULTI_FLAGS_XXX \#defines.
207 * @param hClass The class (no reference consumed). Since we
208 * don't do order checks on event semaphores, the
209 * use of the class is limited to controlling the
210 * timeout threshold for deadlock detection.
211 * @param pszNameFmt Name format string for the lock validator,
212 * optional (NULL). Max length is 32 bytes.
213 * @param ... Format string arguments.
214 */
215RTDECL(int) RTSemEventMultiCreateEx(PRTSEMEVENTMULTI phEventMultiSem, uint32_t fFlags, RTLOCKVALCLASS hClass,
216 const char *pszNameFmt, ...);
217
218/** @name RTSemMutexCreateEx flags
219 * @{ */
220/** Disables lock validation. */
221#define RTSEMEVENTMULTI_FLAGS_NO_LOCK_VAL UINT32_C(0x00000001)
222/** @} */
223
224/**
225 * Destroy an event multi semaphore.
226 *
227 * @returns iprt status code.
228 * @param hEventMultiSem The multiple release event sempahore. NIL is
229 * quietly ignored (VINF_SUCCESS).
230 */
231RTDECL(int) RTSemEventMultiDestroy(RTSEMEVENTMULTI hEventMultiSem);
232
233/**
234 * Signal an event multi semaphore.
235 *
236 * @returns iprt status code.
237 * @param hEventMultiSem The multiple release event sempahore.
238 *
239 * @remarks ring-0: This works when preemption is disabled. However it is
240 * system specific whether it works in interrupt context or with
241 * interrupts disabled.
242 */
243RTDECL(int) RTSemEventMultiSignal(RTSEMEVENTMULTI hEventMultiSem);
244
245/**
246 * Resets an event multi semaphore to non-signaled state.
247 *
248 * @returns iprt status code.
249 * @param hEventMultiSem The multiple release event sempahore.
250 */
251RTDECL(int) RTSemEventMultiReset(RTSEMEVENTMULTI hEventMultiSem);
252
253/**
254 * Wait for the event multi semaphore to be signaled, resume on interruption.
255 *
256 * This function will resume if the wait is interrupted by an async
257 * system event (like a unix signal) or similar.
258 *
259 * @returns iprt status code.
260 * Will not return VERR_INTERRUPTED.
261 * @param hEventMultiSem The multiple release event sempahore.
262 * @param cMillies Number of milliseconds to wait.
263 */
264RTDECL(int) RTSemEventMultiWait(RTSEMEVENTMULTI hEventMultiSem, RTMSINTERVAL cMillies);
265
266
267/**
268 * Wait for the event multi semaphore to be signaled, return on interruption.
269 *
270 * This function will not resume the wait if interrupted.
271 *
272 * @returns iprt status code.
273 * @param hEventMultiSem The multiple release event sempahore.
274 * @param cMillies Number of milliseconds to wait.
275 */
276RTDECL(int) RTSemEventMultiWaitNoResume(RTSEMEVENTMULTI hEventMultiSem, RTMSINTERVAL cMillies);
277
278/**
279 * Sets the signaller thread to one specific thread.
280 *
281 * This is only used for validating usage and deadlock detection. When used
282 * after calls to RTSemEventAddSignaller, the specified thread will be the only
283 * signalling thread.
284 *
285 * @param hEventMultiSem The multiple release event semaphore.
286 * @param hThread The thread that will signal it. Pass
287 * NIL_RTTHREAD to indicate that there is no
288 * special signalling thread.
289 */
290RTDECL(void) RTSemEventMultiSetSignaller(RTSEMEVENTMULTI hEventMultiSem, RTTHREAD hThread);
291
292/**
293 * To add more signalling threads.
294 *
295 * First call RTSemEventSetSignaller then add further threads with this.
296 *
297 * @param hEventMultiSem The multiple release event semaphore.
298 * @param hThread The thread that will signal it. NIL_RTTHREAD is
299 * not accepted.
300 */
301RTDECL(void) RTSemEventMultiAddSignaller(RTSEMEVENTMULTI hEventMultiSem, RTTHREAD hThread);
302
303/**
304 * To remove a signalling thread.
305 *
306 * Reverts work done by RTSemEventAddSignaller and RTSemEventSetSignaller.
307 *
308 * @param hEventMultiSem The multiple release event semaphore.
309 * @param hThread A previously added thread.
310 */
311RTDECL(void) RTSemEventMultiRemoveSignaller(RTSEMEVENTMULTI hEventMultiSem, RTTHREAD hThread);
312
313/** @} */
314
315
316/** @defgroup grp_rt_sems_mutex RTSemMutex - Mutex semaphores.
317 *
318 * Mutex semaphores protect a section of code or data to which access must be
319 * exclusive. Only one thread can hold access to a critical section at one
320 * time. See RTSemMutexCreate, RTSemMutexRequest and RTSemMutexRelease.
321 *
322 * @remarks These are less efficient than "fast mutexes" and "critical
323 * sections", which IPRT implements as well; see @ref
324 * grp_rt_sems_fast_mutex and @ref grp_rt_critsect .
325 *
326 * @{ */
327
328/**
329 * Create a mutex semaphore.
330 *
331 * @returns iprt status code.
332 * @param phMutexSem Where to store the mutex semaphore handle.
333 */
334RTDECL(int) RTSemMutexCreate(PRTSEMMUTEX phMutexSem);
335
336/**
337 * Creates a read/write semaphore.
338 *
339 * @returns iprt status code.
340 * @param phRWSem Where to store the handle to the newly created
341 * RW semaphore.
342 * @param fFlags Flags, any combination of the
343 * RTSEMMUTEX_FLAGS_XXX \#defines.
344 * @param hClass The class (no reference consumed). If NIL, no
345 * lock order validation will be performed on this
346 * lock.
347 * @param uSubClass The sub-class. This is used to define lock
348 * order within a class. RTLOCKVAL_SUB_CLASS_NONE
349 * is the recommended value here.
350 * @param pszNameFmt Name format string for the lock validator,
351 * optional (NULL). Max length is 32 bytes.
352 * @param ... Format string arguments.
353 */
354RTDECL(int) RTSemMutexCreateEx(PRTSEMMUTEX phMutexSem, uint32_t fFlags,
355 RTLOCKVALCLASS hClass, uint32_t uSubClass, const char *pszNameFmt, ...);
356
357/** @name RTSemMutexCreateEx flags
358 * @{ */
359/** Disables lock validation. */
360#define RTSEMMUTEX_FLAGS_NO_LOCK_VAL UINT32_C(0x00000001)
361/** @} */
362
363
364/**
365 * Destroy a mutex semaphore.
366 *
367 * @returns iprt status code.
368 * @param hMutexSem The mutex semaphore to destroy. NIL is quitely
369 * ignored (VINF_SUCCESS).
370 */
371RTDECL(int) RTSemMutexDestroy(RTSEMMUTEX hMutexSem);
372
373/**
374 * Changes the lock validator sub-class of the mutex semaphore.
375 *
376 * It is recommended to try make sure that nobody is using this sempahore while
377 * changing the value.
378 *
379 * @returns The old sub-class. RTLOCKVAL_SUB_CLASS_INVALID is returns if the
380 * lock validator isn't compiled in or either of the parameters are
381 * invalid.
382 * @param hMutexSem The handle to the mutex semaphore.
383 * @param uSubClass The new sub-class value.
384 */
385RTDECL(uint32_t) RTSemMutexSetSubClass(RTSEMMUTEX hMutexSem, uint32_t uSubClass);
386
387/**
388 * Request ownership of a mutex semaphore, resume on interruption.
389 *
390 * This function will resume if the wait is interrupted by an async
391 * system event (like a unix signal) or similar.
392 *
393 * The same thread may request a mutex semaphore multiple times,
394 * a nested counter is kept to make sure it's released on the right
395 * RTSemMutexRelease() call.
396 *
397 * @returns iprt status code.
398 * Will not return VERR_INTERRUPTED.
399 * @param hMutexSem The mutex semaphore to request ownership over.
400 * @param cMillies The number of milliseconds to wait.
401 */
402RTDECL(int) RTSemMutexRequest(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies);
403
404/**
405 * Request ownership of a mutex semaphore, return on interruption.
406 *
407 * This function will not resume the wait if interrupted.
408 *
409 * The same thread may request a mutex semaphore multiple times,
410 * a nested counter is kept to make sure it's released on the right
411 * RTSemMutexRelease() call.
412 *
413 * @returns iprt status code.
414 * @param hMutexSem The mutex semaphore to request ownership over.
415 * @param cMillies The number of milliseconds to wait.
416 */
417RTDECL(int) RTSemMutexRequestNoResume(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies);
418
419/**
420 * Debug version of RTSemMutexRequest that tracks the location.
421 *
422 * @returns iprt status code.
423 * Will not return VERR_INTERRUPTED.
424 * @param hMutexSem The mutex semaphore to request ownership over.
425 * @param cMillies The number of milliseconds to wait.
426 * @param uId Some kind of locking location ID. Typically a
427 * return address up the stack. Optional (0).
428 * @param pszFile The file where the lock is being acquired from.
429 * Optional.
430 * @param iLine The line number in that file. Optional (0).
431 * @param pszFunction The functionn where the lock is being acquired
432 * from. Optional.
433 */
434RTDECL(int) RTSemMutexRequestDebug(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
435
436/**
437 * Debug version of RTSemMutexRequestNoResume that tracks the location.
438 *
439 * @returns iprt status code.
440 * @param hMutexSem The mutex semaphore to request ownership over.
441 * @param cMillies The number of milliseconds to wait.
442 * @param uId Some kind of locking location ID. Typically a
443 * return address up the stack. Optional (0).
444 * @param pszFile The file where the lock is being acquired from.
445 * Optional.
446 * @param iLine The line number in that file. Optional (0).
447 * @param pszFunction The functionn where the lock is being acquired
448 * from. Optional.
449 */
450RTDECL(int) RTSemMutexRequestNoResumeDebug(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
451
452/**
453 * Release the ownership of a mutex semaphore.
454 *
455 * @returns iprt status code.
456 * @param hMutexSem The mutex to release the ownership of. It goes
457 * without saying the the calling thread must own
458 * it.
459 */
460RTDECL(int) RTSemMutexRelease(RTSEMMUTEX hMutexSem);
461
462/**
463 * Checks if the mutex semaphore is owned or not.
464 *
465 * @returns true if owned, false if not.
466 * @param hMutexSem The mutex semaphore.
467 */
468RTDECL(bool) RTSemMutexIsOwned(RTSEMMUTEX hMutexSem);
469
470/* Strict build: Remap the two request calls to the debug versions. */
471#ifdef RT_STRICT
472# ifdef ___iprt_asm_h
473# define RTSemMutexRequest(pCritSect, cMillies) RTSemMutexRequestDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
474# define RTSemMutexRequestNoResume(pCritSect, cMillies) RTSemMutexRequestNoResumeDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
475# else
476# define RTSemMutexRequest(pCritSect, cMillies) RTSemMutexRequestDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
477# define RTSemMutexRequestNoResume(pCritSect, cMillies) RTSemMutexRequestNoResumeDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
478# endif
479#endif
480
481/* Strict lock order: Automatically classify locks by init location. */
482#if defined(RT_LOCK_STRICT_ORDER) && defined(IN_RING3)
483# define RTSemMutexCreate(phMutexSem) \
484 RTSemMutexCreateEx((phMutexSem), 0 /*fFlags*/, \
485 RTLockValidatorClassForSrcPos(RT_SRC_POS, NULL), \
486 RTLOCKVAL_SUB_CLASS_NONE, NULL)
487#endif
488
489/** @} */
490
491
492/** @defgroup grp_rt_sems_fast_mutex RTSemFastMutex - Fast Mutex Semaphores
493 *
494 * Fast mutexes work like regular mutexes in that they allow only a single
495 * thread access to a critical piece of code or data. As opposed to mutexes,
496 * they require no syscall if the fast mutex is not held (like critical
497 * sections). Unlike critical sections however, they are *not* recursive.
498 *
499 * @{ */
500
501/**
502 * Create a fast mutex semaphore.
503 *
504 * @returns iprt status code.
505 * @param phFastMtx Where to store the handle to the newly created
506 * fast mutex semaphore.
507 *
508 * @remarks Fast mutex semaphores are not recursive.
509 */
510RTDECL(int) RTSemFastMutexCreate(PRTSEMFASTMUTEX phFastMtx);
511
512/**
513 * Destroy a fast mutex semaphore.
514 *
515 * @returns iprt status code.
516 * @param hFastMtx Handle to the fast mutex semaphore. NIL is
517 * quietly ignored (VINF_SUCCESS).
518 */
519RTDECL(int) RTSemFastMutexDestroy(RTSEMFASTMUTEX hFastMtx);
520
521/**
522 * Request ownership of a fast mutex semaphore.
523 *
524 * The same thread may request a mutex semaphore multiple times,
525 * a nested counter is kept to make sure it's released on the right
526 * RTSemMutexRelease() call.
527 *
528 * @returns iprt status code.
529 * @param hFastMtx Handle to the fast mutex semaphore.
530 */
531RTDECL(int) RTSemFastMutexRequest(RTSEMFASTMUTEX hFastMtx);
532
533/**
534 * Release the ownership of a fast mutex semaphore.
535 *
536 * @returns iprt status code.
537 * @param hFastMtx Handle to the fast mutex semaphore. It goes
538 * without saying the the calling thread must own
539 * it.
540 */
541RTDECL(int) RTSemFastMutexRelease(RTSEMFASTMUTEX hFastMtx);
542
543/** @} */
544
545
546/** @defgroup grp_rt_sems_spin_mutex RTSemSpinMutex - Spinning Mutex Semaphores
547 *
548 * A very adaptive variant of mutex semaphore that is tailored for the ring-0
549 * logger.
550 *
551 * @{ */
552
553/**
554 * Creates a spinning mutex semaphore.
555 *
556 * @returns iprt status code.
557 * @retval VERR_INVALID_PARAMETER on invalid flags.
558 * @retval VERR_NO_MEMORY if out of memory for the semaphore structure and
559 * handle.
560 *
561 * @param phSpinMtx Where to return the handle to the create semaphore.
562 * @param fFlags Flags, see RTSEMSPINMUTEX_FLAGS_XXX.
563 */
564RTDECL(int) RTSemSpinMutexCreate(PRTSEMSPINMUTEX phSpinMtx, uint32_t fFlags);
565
566/** @name RTSemSpinMutexCreate flags.
567 * @{ */
568/** Always take the semaphore in a IRQ safe way.
569 * (In plain words: always disable interrupts.) */
570#define RTSEMSPINMUTEX_FLAGS_IRQ_SAFE RT_BIT_32(0)
571/** Mask of valid flags. */
572#define RTSEMSPINMUTEX_FLAGS_VALID_MASK UINT32_C(0x00000001)
573/** @} */
574
575/**
576 * Destroys a spinning mutex semaphore.
577 *
578 * @returns iprt status code.
579 * @retval VERR_INVALID_HANDLE (or crash) if the handle is invalid. (NIL will
580 * not cause this status.)
581 *
582 * @param hSpinMtx The semaphore handle. NIL_RTSEMSPINMUTEX is ignored
583 * quietly (VINF_SUCCESS).
584 */
585RTDECL(int) RTSemSpinMutexDestroy(RTSEMSPINMUTEX hSpinMtx);
586
587/**
588 * Request the spinning mutex semaphore.
589 *
590 * This may block if the context we're called in allows this. If not it will
591 * spin. If called in an interrupt context, we will only spin if the current
592 * owner isn't interrupted. Also, on some systems it is not always possible to
593 * wake up blocking threads in all contexts, so, which will either be indicated
594 * by returning VERR_SEM_BAD_CONTEXT or by temporarily switching the semaphore
595 * into pure spinlock state.
596 *
597 * Preemption will be disabled upon return. IRQs may also be disabled.
598 *
599 * @returns iprt status code.
600 * @retval VERR_SEM_BAD_CONTEXT if the context it's called in isn't suitable
601 * for releasing it if someone is sleeping on it.
602 * @retval VERR_SEM_DESTROYED if destroyed.
603 * @retval VERR_SEM_NESTED if held by the caller. Asserted.
604 * @retval VERR_INVALID_HANDLE if the handle is invalid. Asserted
605 *
606 * @param hSpinMtx The semaphore handle.
607 */
608RTDECL(int) RTSemSpinMutexRequest(RTSEMSPINMUTEX hSpinMtx);
609
610/**
611 * Like RTSemSpinMutexRequest but it won't block or spin if the semaphore is
612 * held by someone else.
613 *
614 * @returns iprt status code.
615 * @retval VERR_SEM_BUSY if held by someone else.
616 * @retval VERR_SEM_DESTROYED if destroyed.
617 * @retval VERR_SEM_NESTED if held by the caller. Asserted.
618 * @retval VERR_INVALID_HANDLE if the handle is invalid. Asserted
619 *
620 * @param hSpinMtx The semaphore handle.
621 */
622RTDECL(int) RTSemSpinMutexTryRequest(RTSEMSPINMUTEX hSpinMtx);
623
624/**
625 * Releases the semaphore previously acquired by RTSemSpinMutexRequest or
626 * RTSemSpinMutexTryRequest.
627 *
628 * @returns iprt status code.
629 * @retval VERR_SEM_DESTROYED if destroyed.
630 * @retval VERR_NOT_OWNER if not owner. Asserted.
631 * @retval VERR_INVALID_HANDLE if the handle is invalid. Asserted.
632 *
633 * @param hSpinMtx The semaphore handle.
634 */
635RTDECL(int) RTSemSpinMutexRelease(RTSEMSPINMUTEX hSpinMtx);
636
637/** @} */
638
639
640/** @defgroup grp_rt_sem_rw RTSemRW - Read / Write Semaphores
641 *
642 * Read/write semaphores are a fancier version of mutexes in that they grant
643 * read access to the protected data to several threads at the same time but
644 * allow only one writer at a time. This can make code scale better at the
645 * expense of slightly more overhead in mutex management.
646 *
647 * @{ */
648
649/**
650 * Creates a read/write semaphore.
651 *
652 * @returns iprt status code.
653 * @param phRWSem Where to store the handle to the newly created
654 * RW semaphore.
655 */
656RTDECL(int) RTSemRWCreate(PRTSEMRW phRWSem);
657
658/**
659 * Creates a read/write semaphore.
660 *
661 * @returns iprt status code.
662 * @param phRWSem Where to store the handle to the newly created
663 * RW semaphore.
664 * @param fFlags Flags, any combination of the RTSEMRW_FLAGS_XXX
665 * \#defines.
666 * @param hClass The class (no reference consumed). If NIL, no
667 * lock order validation will be performed on this
668 * lock.
669 * @param uSubClass The sub-class. This is used to define lock
670 * order within a class. RTLOCKVAL_SUB_CLASS_NONE
671 * is the recommended value here.
672 * @param pszNameFmt Name format string for the lock validator,
673 * optional (NULL). Max length is 32 bytes.
674 * @param ... Format string arguments.
675 */
676RTDECL(int) RTSemRWCreateEx(PRTSEMRW phRWSem, uint32_t fFlags,
677 RTLOCKVALCLASS hClass, uint32_t uSubClass, const char *pszNameFmt, ...);
678
679/** @name RTSemRWCreateEx flags
680 * @{ */
681/** Disables lock validation. */
682#define RTSEMRW_FLAGS_NO_LOCK_VAL UINT32_C(0x00000001)
683/** @} */
684
685/**
686 * Destroys a read/write semaphore.
687 *
688 * @returns iprt status code.
689 * @param hRWSem Handle to the read/write semaphore. NIL is
690 * quitly ignored (VINF_SUCCESS).
691 */
692RTDECL(int) RTSemRWDestroy(RTSEMRW hRWSem);
693
694/**
695 * Changes the lock validator sub-class of the read/write semaphore.
696 *
697 * It is recommended to try make sure that nobody is using this sempahore while
698 * changing the value.
699 *
700 * @returns The old sub-class. RTLOCKVAL_SUB_CLASS_INVALID is returns if the
701 * lock validator isn't compiled in or either of the parameters are
702 * invalid.
703 * @param hRWSem Handle to the read/write semaphore.
704 * @param uSubClass The new sub-class value.
705 */
706RTDECL(uint32_t) RTSemRWSetSubClass(RTSEMRW hRWSem, uint32_t uSubClass);
707
708/**
709 * Request read access to a read/write semaphore, resume on interruption
710 *
711 * @returns iprt status code.
712 * @retval VINF_SUCCESS on success.
713 * @retval VERR_INTERRUPT if the wait was interrupted.
714 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
715 *
716 * @param hRWSem Handle to the read/write semaphore.
717 * @param cMillies The number of milliseconds to wait.
718 */
719RTDECL(int) RTSemRWRequestRead(RTSEMRW hRWSem, RTMSINTERVAL cMillies);
720
721/**
722 * Request read access to a read/write semaphore, return on interruption
723 *
724 * @returns iprt status code.
725 * @retval VINF_SUCCESS on success.
726 * @retval VERR_INTERRUPT if the wait was interrupted.
727 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
728 *
729 * @param hRWSem Handle to the read/write semaphore.
730 * @param cMillies The number of milliseconds to wait.
731 */
732RTDECL(int) RTSemRWRequestReadNoResume(RTSEMRW hRWSem, RTMSINTERVAL cMillies);
733
734/**
735 * Debug version of RTSemRWRequestRead that tracks the location.
736 *
737 * @returns iprt status code.
738 * @retval VINF_SUCCESS on success.
739 * @retval VERR_INTERRUPT if the wait was interrupted.
740 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
741 *
742 * @param hRWSem Handle to the read/write semaphore.
743 * @param cMillies The number of milliseconds to wait.
744 * @param uId Some kind of locking location ID. Typically a
745 * return address up the stack. Optional (0).
746 * @param pszFile The file where the lock is being acquired from.
747 * Optional.
748 * @param iLine The line number in that file. Optional (0).
749 * @param pszFunction The functionn where the lock is being acquired
750 * from. Optional.
751 */
752RTDECL(int) RTSemRWRequestReadDebug(RTSEMRW hRWSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
753
754/**
755 * Debug version of RTSemRWRequestWriteNoResume that tracks the location.
756 *
757 * @returns iprt status code.
758 * @retval VINF_SUCCESS on success.
759 * @retval VERR_INTERRUPT if the wait was interrupted.
760 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
761 *
762 * @param hRWSem Handle to the read/write semaphore.
763 * @param cMillies The number of milliseconds to wait.
764 * @param uId Some kind of locking location ID. Typically a
765 * return address up the stack. Optional (0).
766 * @param pszFile The file where the lock is being acquired from.
767 * Optional.
768 * @param iLine The line number in that file. Optional (0).
769 * @param pszFunction The functionn where the lock is being acquired
770 * from. Optional.
771 */
772RTDECL(int) RTSemRWRequestReadNoResumeDebug(RTSEMRW hRWSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
773
774/**
775 * Release read access to a read/write semaphore.
776 *
777 * @returns iprt status code.
778 * @param hRWSem Handle to the read/write semaphore. It goes
779 * without saying that caller must own read
780 * privileges to the semaphore.
781 */
782RTDECL(int) RTSemRWReleaseRead(RTSEMRW hRWSem);
783
784/**
785 * Request write access to a read/write semaphore, resume on interruption.
786 *
787 * @returns iprt status code.
788 * @retval VINF_SUCCESS on success.
789 * @retval VERR_DEADLOCK if the caller owned the read lock.
790 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
791 *
792 * @param hRWSem Handle to the read/write semaphore.
793 * @param cMillies The number of milliseconds to wait.
794 */
795RTDECL(int) RTSemRWRequestWrite(RTSEMRW hRWSem, RTMSINTERVAL cMillies);
796
797/**
798 * Request write access to a read/write semaphore, return on interruption.
799 *
800 * @returns iprt status code.
801 * @retval VINF_SUCCESS on success.
802 * @retval VERR_INTERRUPT if the wait was interrupted.
803 * @retval VERR_DEADLOCK if the caller owned the read lock.
804 * @retval VERR_INVALID_HANDLE if hRWSem is invalid.
805 *
806 * @param hRWSem Handle to the read/write semaphore.
807 * @param cMillies The number of milliseconds to wait.
808 */
809RTDECL(int) RTSemRWRequestWriteNoResume(RTSEMRW hRWSem, RTMSINTERVAL cMillies);
810
811/**
812 * Debug version of RTSemRWRequestWrite that tracks the location.
813 *
814 * @returns IPRT status code, see RTSemRWRequestWrite.
815 * @param hRWSem Handle to the read/write semaphore.
816 * @param cMillies The number of milliseconds to wait.
817 * @param uId Some kind of locking location ID. Typically a
818 * return address up the stack. Optional (0).
819 * @param pszFile The file where the lock is being acquired from.
820 * Optional.
821 * @param iLine The line number in that file. Optional (0).
822 * @param pszFunction The functionn where the lock is being acquired
823 * from. Optional.
824 */
825RTDECL(int) RTSemRWRequestWriteDebug(RTSEMRW hRWSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
826
827/**
828 * Debug version of RTSemRWRequestWriteNoResume that tracks the location.
829 *
830 * @returns IPRT status code, see RTSemRWRequestWriteNoResume.
831 * @param hRWSem Handle to the read/write semaphore.
832 * @param cMillies The number of milliseconds to wait.
833 * @param uId Some kind of locking location ID. Typically a
834 * return address up the stack. Optional (0).
835 * @param pszFile The file where the lock is being acquired from.
836 * Optional.
837 * @param iLine The line number in that file. Optional (0).
838 * @param pszFunction The functionn where the lock is being acquired
839 * from. Optional.
840 */
841RTDECL(int) RTSemRWRequestWriteNoResumeDebug(RTSEMRW hRWSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL);
842
843/**
844 * Release write access to a read/write semaphore.
845 *
846 * @returns iprt status code.
847 * @param hRWSem Handle to the read/write semaphore. Goes
848 * without saying that caller must have write
849 * access to the semaphore.
850 */
851RTDECL(int) RTSemRWReleaseWrite(RTSEMRW hRWSem);
852
853/**
854 * Checks if the caller is the exclusive semaphore owner.
855 *
856 * @returns true / false accoringly.
857 * @param hRWSem Handle to the read/write semaphore.
858 */
859RTDECL(bool) RTSemRWIsWriteOwner(RTSEMRW hRWSem);
860
861/**
862 * Checks if the caller is one of the read owners of the sempahore.
863 *
864 * @note !CAUTION! This API doesn't work reliably if lock validation isn't
865 * enabled. Meaning, the answer is not trustworhty unless
866 * RT_LOCK_STRICT or RTSEMRW_STRICT was defined at build time. Also,
867 * make sure you do not use RTSEMRW_FLAGS_NO_LOCK_VAL when creating
868 * the semaphore. And finally, if you used a locking class, don't
869 * disable deadlock detection by setting cMsMinDeadlock to
870 * RT_INDEFINITE_WAIT.
871 *
872 * In short, only use this for assertions.
873 *
874 * @returns true if reader, false if not.
875 * @param hRWSem Handle to the read/write semaphore.
876 * @param fWannaHear What you'd like to hear when lock validation is
877 * not available. (For avoiding asserting all over
878 * the place.)
879 */
880RTDECL(bool) RTSemRWIsReadOwner(RTSEMRW hRWSem, bool fWannaHear);
881
882/**
883 * Gets the write recursion count.
884 *
885 * @returns The write recursion count (0 if bad semaphore handle).
886 * @param hRWSem Handle to the read/write semaphore.
887 */
888RTDECL(uint32_t) RTSemRWGetWriteRecursion(RTSEMRW hRWSem);
889
890/**
891 * Gets the read recursion count of the current writer.
892 *
893 * @returns The read recursion count (0 if bad semaphore handle).
894 * @param hRWSem Handle to the read/write semaphore.
895 */
896RTDECL(uint32_t) RTSemRWGetWriterReadRecursion(RTSEMRW hRWSem);
897
898/**
899 * Gets the current number of reads.
900 *
901 * This includes all read recursions, so it might be higher than the number of
902 * read owners. It does not include reads done by the current writer.
903 *
904 * @returns The read count (0 if bad semaphore handle).
905 * @param hRWSem Handle to the read/write semaphore.
906 */
907RTDECL(uint32_t) RTSemRWGetReadCount(RTSEMRW hRWSem);
908
909/* Strict build: Remap the four request calls to the debug versions. */
910#ifdef RT_STRICT
911# ifdef ___iprt_asm_h
912# define RTSemRWRequestRead(pCritSect, cMillies) RTSemRWRequestReadDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
913# define RTSemRWRequestReadNoResume(pCritSect, cMillies) RTSemRWRequestReadNoResumeDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
914# define RTSemRWRequestWrite(pCritSect, cMillies) RTSemRWRequestWriteDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
915# define RTSemRWRequestWriteNoResume(pCritSect, cMillies) RTSemRWRequestWriteNoResumeDebug((pCritSect), (cMillies), (uintptr_t)ASMReturnAddress(), RT_SRC_POS)
916# else
917# define RTSemRWRequestRead(pCritSect, cMillies) RTSemRWRequestReadDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
918# define RTSemRWRequestReadNoResume(pCritSect, cMillies) RTSemRWRequestReadNoResumeDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
919# define RTSemRWRequestWrite(pCritSect, cMillies) RTSemRWRequestWriteDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
920# define RTSemRWRequestWriteNoResume(pCritSect, cMillies) RTSemRWRequestWriteNoResumeDebug((pCritSect), (cMillies), 0, RT_SRC_POS)
921# endif
922#endif
923
924/* Strict lock order: Automatically classify locks by init location. */
925#if defined(RT_LOCK_STRICT_ORDER) && defined(IN_RING3)
926# define RTSemRWCreate(phSemRW) \
927 RTSemRWCreateEx((phSemRW), 0 /*fFlags*/, \
928 RTLockValidatorClassForSrcPos(RT_SRC_POS, NULL), \
929 RTLOCKVAL_SUB_CLASS_NONE, NULL)
930#endif
931
932/** @} */
933
934
935/** @defgroup grp_rt_sems_pingpong RTSemPingPong - Ping-Pong Construct
936 *
937 * Serialization of a two way communication.
938 *
939 * @{ */
940
941/**
942 * Ping-pong speaker
943 */
944typedef enum RTPINGPONGSPEAKER
945{
946 /** Not initialized. */
947 RTPINGPONGSPEAKER_UNINITIALIZE = 0,
948 /** Ping is speaking, Pong is waiting. */
949 RTPINGPONGSPEAKER_PING,
950 /** Pong is signaled, Ping is waiting. */
951 RTPINGPONGSPEAKER_PONG_SIGNALED,
952 /** Pong is speaking, Ping is waiting. */
953 RTPINGPONGSPEAKER_PONG,
954 /** Ping is signaled, Pong is waiting. */
955 RTPINGPONGSPEAKER_PING_SIGNALED,
956 /** Hack to ensure that it's at least 32-bits wide. */
957 RTPINGPONGSPEAKER_HACK = 0x7fffffff
958} RTPINGPONGSPEAKER;
959
960/**
961 * Ping-Pong construct.
962 *
963 * Two threads, one saying Ping and the other saying Pong. The construct
964 * makes sure they don't speak out of turn and that they can wait and poll
965 * on the conversation.
966 */
967typedef struct RTPINGPONG
968{
969 /** The semaphore the Ping thread waits on. */
970 RTSEMEVENT Ping;
971 /** The semaphore the Pong thread waits on. */
972 RTSEMEVENT Pong;
973 /** The current speaker. */
974 volatile RTPINGPONGSPEAKER enmSpeaker;
975#if HC_ARCH_BITS == 64
976 /** Padding the structure to become a multiple of sizeof(RTHCPTR). */
977 uint32_t u32Padding;
978#endif
979} RTPINGPONG;
980/** Pointer to Ping-Pong construct. */
981typedef RTPINGPONG *PRTPINGPONG;
982
983/**
984 * Init a Ping-Pong construct.
985 *
986 * @returns iprt status code.
987 * @param pPP Pointer to the ping-pong structure which needs initialization.
988 */
989RTDECL(int) RTSemPingPongInit(PRTPINGPONG pPP);
990
991/**
992 * Deletes a Ping-Pong construct.
993 *
994 * @returns iprt status code.
995 * @param pPP Pointer to the ping-pong structure which is to be destroyed.
996 * (I.e. put into uninitialized state.)
997 */
998RTDECL(int) RTSemPingPongDelete(PRTPINGPONG pPP);
999
1000/**
1001 * Signals the pong thread in a ping-pong construct. (I.e. sends ping.)
1002 * This is called by the ping thread.
1003 *
1004 * @returns iprt status code.
1005 * @param pPP Pointer to the ping-pong structure to ping.
1006 */
1007RTDECL(int) RTSemPing(PRTPINGPONG pPP);
1008
1009/**
1010 * Signals the ping thread in a ping-pong construct. (I.e. sends pong.)
1011 * This is called by the pong thread.
1012 *
1013 * @returns iprt status code.
1014 * @param pPP Pointer to the ping-pong structure to pong.
1015 */
1016RTDECL(int) RTSemPong(PRTPINGPONG pPP);
1017
1018/**
1019 * Wait function for the ping thread.
1020 *
1021 * @returns iprt status code.
1022 * Will not return VERR_INTERRUPTED.
1023 * @param pPP Pointer to the ping-pong structure to wait on.
1024 * @param cMillies Number of milliseconds to wait.
1025 */
1026RTDECL(int) RTSemPingWait(PRTPINGPONG pPP, RTMSINTERVAL cMillies);
1027
1028/**
1029 * Wait function for the pong thread.
1030 *
1031 * @returns iprt status code.
1032 * Will not return VERR_INTERRUPTED.
1033 * @param pPP Pointer to the ping-pong structure to wait on.
1034 * @param cMillies Number of milliseconds to wait.
1035 */
1036RTDECL(int) RTSemPongWait(PRTPINGPONG pPP, RTMSINTERVAL cMillies);
1037
1038
1039/**
1040 * Checks if the pong thread is speaking.
1041 *
1042 * @returns true / false.
1043 * @param pPP Pointer to the ping-pong structure.
1044 * @remark This is NOT the same as !RTSemPongIsSpeaker().
1045 */
1046DECLINLINE(bool) RTSemPingIsSpeaker(PRTPINGPONG pPP)
1047{
1048 RTPINGPONGSPEAKER enmSpeaker = pPP->enmSpeaker;
1049 return enmSpeaker == RTPINGPONGSPEAKER_PING;
1050}
1051
1052
1053/**
1054 * Checks if the pong thread is speaking.
1055 *
1056 * @returns true / false.
1057 * @param pPP Pointer to the ping-pong structure.
1058 * @remark This is NOT the same as !RTSemPingIsSpeaker().
1059 */
1060DECLINLINE(bool) RTSemPongIsSpeaker(PRTPINGPONG pPP)
1061{
1062 RTPINGPONGSPEAKER enmSpeaker = pPP->enmSpeaker;
1063 return enmSpeaker == RTPINGPONGSPEAKER_PONG;
1064}
1065
1066
1067/**
1068 * Checks whether the ping thread should wait.
1069 *
1070 * @returns true / false.
1071 * @param pPP Pointer to the ping-pong structure.
1072 * @remark This is NOT the same as !RTSemPongShouldWait().
1073 */
1074DECLINLINE(bool) RTSemPingShouldWait(PRTPINGPONG pPP)
1075{
1076 RTPINGPONGSPEAKER enmSpeaker = pPP->enmSpeaker;
1077 return enmSpeaker == RTPINGPONGSPEAKER_PONG
1078 || enmSpeaker == RTPINGPONGSPEAKER_PONG_SIGNALED
1079 || enmSpeaker == RTPINGPONGSPEAKER_PING_SIGNALED;
1080}
1081
1082
1083/**
1084 * Checks whether the pong thread should wait.
1085 *
1086 * @returns true / false.
1087 * @param pPP Pointer to the ping-pong structure.
1088 * @remark This is NOT the same as !RTSemPingShouldWait().
1089 */
1090DECLINLINE(bool) RTSemPongShouldWait(PRTPINGPONG pPP)
1091{
1092 RTPINGPONGSPEAKER enmSpeaker = pPP->enmSpeaker;
1093 return enmSpeaker == RTPINGPONGSPEAKER_PING
1094 || enmSpeaker == RTPINGPONGSPEAKER_PING_SIGNALED
1095 || enmSpeaker == RTPINGPONGSPEAKER_PONG_SIGNALED;
1096}
1097
1098/** @} */
1099
1100
1101/** @defgroup grp_rt_sems_xroads RTSemXRoads - Crossroads
1102 *
1103 * The crossroads semaphore is intended to prevent two classes of incompatible
1104 * events from occuring simultaneously, like south/north bound traffic and
1105 * west/east bound traffic at a 4-way junction.
1106 *
1107 * @remarks In order to simplify the implementation, the current flow is always
1108 * given priority. So, it won't work at all well when busy!
1109 *
1110 * @remarks "XRoads" is used as a name because it is briefer than "crossroads"
1111 * and it slightly stresses that is a 4 way crossing to the users of
1112 * American English.
1113 * @{
1114 */
1115
1116/**
1117 * Creates a crossroads semaphore.
1118 *
1119 * @returns IPRT status code.
1120 *
1121 * @param phXRoads Where to return the handle to the newly created
1122 * crossroads semaphore.
1123 */
1124RTDECL(int) RTSemXRoadsCreate(PRTSEMXROADS phXRoads);
1125
1126/**
1127 * Destroys a crossroads semaphore.
1128 *
1129 * @returns IPRT status code.
1130 *
1131 * @param hXRoads Handle to the crossroads semaphore that is to be
1132 * destroyed. NIL_RTSEMXROADS is quitetly ignored
1133 * (VINF_SUCCESS).
1134 */
1135RTDECL(int) RTSemXRoadsDestroy(RTSEMXROADS hXRoads);
1136
1137/**
1138 * Enter the crossroads from the south or north.
1139 *
1140 * (Coupled with RTSemXRoadsNSLeave.)
1141 *
1142 * @returns IPRT status code.
1143 * @param hXRoads Handle to the crossroads semaphore.
1144 */
1145RTDECL(int) RTSemXRoadsNSEnter(RTSEMXROADS hXRoads);
1146
1147/**
1148 * Leave the crossroads to the north or south.
1149 *
1150 * (Coupled with RTSemXRoadsNSEnter.)
1151 *
1152 * @returns IPRT status code.
1153 * @param hXRoads Handle to the crossroads semaphore.
1154 */
1155RTDECL(int) RTSemXRoadsNSLeave(RTSEMXROADS hXRoads);
1156
1157/**
1158 * Leave the crossroads from the east or west.
1159 *
1160 * (Coupled with RTSemXRoadsEWLeave.)
1161 *
1162 * @returns IPRT status code.
1163 * @param hXRoads Handle to the crossroads semaphore.
1164 */
1165RTDECL(int) RTSemXRoadsEWEnter(RTSEMXROADS hXRoads);
1166
1167/**
1168 * Leave the crossroads to the west or east.
1169 *
1170 * (Coupled with RTSemXRoadsEWEnter.)
1171 *
1172 * @returns IPRT status code.
1173 * @param hXRoads Handle to the crossroads semaphore.
1174 */
1175RTDECL(int) RTSemXRoadsEWLeave(RTSEMXROADS hXRoads);
1176
1177/** @} */
1178
1179/** @} */
1180
1181RT_C_DECLS_END
1182
1183#endif
1184
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette