Data Structures | |
struct | libusb_pollfd |
File descriptor for polling. More... | |
Typedefs | |
typedef void(* | libusb_pollfd_added_cb )(int fd, short events, void *user_data) |
Callback function, invoked when a new file descriptor should be added to the set of file descriptors monitored for events. | |
typedef void(* | libusb_pollfd_removed_cb )(int fd, void *user_data) |
Callback function, invoked when a file descriptor should be removed from the set of file descriptors being monitored for events. | |
Functions | |
int | libusb_try_lock_events (libusb_context *ctx) |
Attempt to acquire the event handling lock. | |
void | libusb_lock_events (libusb_context *ctx) |
Acquire the event handling lock, blocking until successful acquisition if it is contended. | |
void | libusb_unlock_events (libusb_context *ctx) |
Release the lock previously acquired with libusb_try_lock_events() or libusb_lock_events(). | |
int | libusb_event_handling_ok (libusb_context *ctx) |
Determine if it is still OK for this thread to be doing event handling. | |
int | libusb_event_handler_active (libusb_context *ctx) |
Determine if an active thread is handling events (i.e. | |
void | libusb_lock_event_waiters (libusb_context *ctx) |
Acquire the event waiters lock. | |
void | libusb_unlock_event_waiters (libusb_context *ctx) |
Release the event waiters lock. | |
int | libusb_wait_for_event (libusb_context *ctx, struct timeval *tv) |
Wait for another thread to signal completion of an event. | |
int | libusb_handle_events_timeout (libusb_context *ctx, struct timeval *tv) |
Handle any pending events. | |
int | libusb_handle_events (libusb_context *ctx) |
Handle any pending events in blocking mode. | |
int | libusb_handle_events_locked (libusb_context *ctx, struct timeval *tv) |
Handle any pending events by polling file descriptors, without checking if any other threads are already doing so. | |
int | libusb_pollfds_handle_timeouts (libusb_context *ctx) |
Determines whether your application must apply special timing considerations when monitoring libusb's file descriptors. | |
int | libusb_get_next_timeout (libusb_context *ctx, struct timeval *tv) |
Determine the next internal timeout that libusb needs to handle. | |
void | libusb_set_pollfd_notifiers (libusb_context *ctx, libusb_pollfd_added_cb added_cb, libusb_pollfd_removed_cb removed_cb, void *user_data) |
Register notification functions for file descriptor additions/removals. | |
struct libusb_pollfd ** | libusb_get_pollfds (libusb_context *ctx) |
Retrieve a list of file descriptors that should be polled by your main loop as libusb event sources. |
These functions are only necessary for users of the asynchronous API. If you are only using the simpler synchronous API then you do not need to ever call these functions.
The justification for the functionality described here has already been discussed in the event handling section of the asynchronous API documentation. In summary, libusb does not create internal threads for event processing and hence relies on your application calling into libusb at certain points in time so that pending events can be handled. In order to know precisely when libusb needs to be called into, libusb offers you a set of pollable file descriptors and information about when the next timeout expires.
If you are using the asynchronous I/O API, you must take one of the two following options, otherwise your I/O will not complete.
// initialize libusb // find and open device // maybe fire off some initial async I/O while (user_has_not_requested_exit) libusb_handle_events(ctx); // clean up and exit
With such a simple main loop, you do not have to worry about managing sets of file descriptors or handling timeouts. libusb_handle_events() will handle those details internally.
In addition to polling file descriptors for the other event sources, you take a set of file descriptors from libusb and monitor those too. When you detect activity on libusb's file descriptors, you call libusb_handle_events_timeout() in non-blocking mode.
What's more, libusb may also need to handle events at specific moments in time. No file descriptor activity is generated at these times, so your own application needs to be continually aware of when the next one of these moments occurs (through calling libusb_get_next_timeout()), and then it needs to call libusb_handle_events_timeout() in non-blocking mode when these moments occur. This means that you need to adjust your poll()/select() timeout accordingly.
libusb provides you with a set of file descriptors to poll and expects you to poll all of them, treating them as a single entity. The meaning of each file descriptor in the set is an internal implementation detail, platform-dependent and may vary from release to release. Don't try and interpret the meaning of the file descriptors, just do as libusb indicates, polling all of them at once.
In pseudo-code, you want something that looks like:
// initialise libusb libusb_get_pollfds(ctx) while (user has not requested application exit) { libusb_get_next_timeout(ctx); poll(on libusb file descriptors plus any other event sources of interest, using a timeout no larger than the value libusb just suggested) if (poll() indicated activity on libusb file descriptors) libusb_handle_events_timeout(ctx, 0); if (time has elapsed to or beyond the libusb timeout) libusb_handle_events_timeout(ctx, 0); // handle events from other sources here } // clean up and exit
These time-based event complications are not required on the following platforms:
Under these configurations, libusb_get_next_timeout() will always return 0, so your main loop can be simplified to:
// initialise libusb libusb_get_pollfds(ctx) while (user has not requested application exit) { poll(on libusb file descriptors plus any other event sources of interest, using any timeout that you like) if (poll() indicated activity on libusb file descriptors) libusb_handle_events_timeout(ctx, 0); // handle events from other sources here } // clean up and exit
Do remember that if you simplify your main loop to the above, you will lose compatibility with some platforms (including legacy Linux platforms, and any future platforms supported by libusb which may have time-based event requirements). The resultant problems will likely appear as strange bugs in your application.
You can use the libusb_pollfds_handle_timeouts() function to do a runtime check to see if it is safe to ignore the time-based event complications. If your application has taken the shortcut of ignoring libusb's next timeout in your main loop, then you are advised to check the return value of libusb_pollfds_handle_timeouts() during application startup, and to abort if the platform does suffer from these timing complications.
The events lock, event waiters lock, and libusb_handle_events_locked() entities are added to solve these problems. You do not need to be concerned with these entities otherwise.
See the extra documentation: Multi-threaded applications and asynchronous I/O
typedef void(* libusb_pollfd_added_cb)(int fd, short events, void *user_data) |
Callback function, invoked when a new file descriptor should be added to the set of file descriptors monitored for events.
fd | the new file descriptor | |
events | events to monitor for, see libusb_pollfd for a description | |
user_data | User data pointer specified in libusb_set_pollfd_notifiers() call |
typedef void(* libusb_pollfd_removed_cb)(int fd, void *user_data) |
Callback function, invoked when a file descriptor should be removed from the set of file descriptors being monitored for events.
After returning from this callback, do not use that file descriptor again.
fd | the file descriptor to stop monitoring | |
user_data | User data pointer specified in libusb_set_pollfd_notifiers() call |
int libusb_try_lock_events | ( | libusb_context * | ctx | ) |
Attempt to acquire the event handling lock.
This lock is used to ensure that only one thread is monitoring libusb event sources at any one time.
You only need to use this lock if you are developing an application which calls poll() or select() on libusb's file descriptors directly. If you stick to libusb's event handling loop functions (e.g. libusb_handle_events()) then you do not need to be concerned with this locking.
While holding this lock, you are trusted to actually be handling events. If you are no longer handling events, you must call libusb_unlock_events() as soon as possible.
ctx | the context to operate on, or NULL for the default context |
1 if the lock was not obtained (i.e. another thread holds the lock)
void libusb_lock_events | ( | libusb_context * | ctx | ) |
Acquire the event handling lock, blocking until successful acquisition if it is contended.
This lock is used to ensure that only one thread is monitoring libusb event sources at any one time.
You only need to use this lock if you are developing an application which calls poll() or select() on libusb's file descriptors directly. If you stick to libusb's event handling loop functions (e.g. libusb_handle_events()) then you do not need to be concerned with this locking.
While holding this lock, you are trusted to actually be handling events. If you are no longer handling events, you must call libusb_unlock_events() as soon as possible.
ctx | the context to operate on, or NULL for the default context |
void libusb_unlock_events | ( | libusb_context * | ctx | ) |
Release the lock previously acquired with libusb_try_lock_events() or libusb_lock_events().
Releasing this lock will wake up any threads blocked on libusb_wait_for_event().
ctx | the context to operate on, or NULL for the default context |
int libusb_event_handling_ok | ( | libusb_context * | ctx | ) |
Determine if it is still OK for this thread to be doing event handling.
Sometimes, libusb needs to temporarily pause all event handlers, and this is the function you should use before polling file descriptors to see if this is the case.
If this function instructs your thread to give up the events lock, you should just continue the usual logic that is documented in Multi-threaded applications and asynchronous I/O. On the next iteration, your thread will fail to obtain the events lock, and will hence become an event waiter.
This function should be called while the events lock is held: you don't need to worry about the results of this function if your thread is not the current event handler.
ctx | the context to operate on, or NULL for the default context |
0 if this thread must give up the events lock
int libusb_event_handler_active | ( | libusb_context * | ctx | ) |
Determine if an active thread is handling events (i.e.
if anyone is holding the event handling lock).
ctx | the context to operate on, or NULL for the default context |
0 if there are no threads currently handling events
void libusb_lock_event_waiters | ( | libusb_context * | ctx | ) |
Acquire the event waiters lock.
This lock is designed to be obtained under the situation where you want to be aware when events are completed, but some other thread is event handling so calling libusb_handle_events() is not allowed.
You then obtain this lock, re-check that another thread is still handling events, then call libusb_wait_for_event().
You only need to use this lock if you are developing an application which calls poll() or select() on libusb's file descriptors directly, and may potentially be handling events from 2 threads simultaenously. If you stick to libusb's event handling loop functions (e.g. libusb_handle_events()) then you do not need to be concerned with this locking.
ctx | the context to operate on, or NULL for the default context |
void libusb_unlock_event_waiters | ( | libusb_context * | ctx | ) |
Release the event waiters lock.
ctx | the context to operate on, or NULL for the default context |
int libusb_wait_for_event | ( | libusb_context * | ctx, | |
struct timeval * | tv | |||
) |
Wait for another thread to signal completion of an event.
Must be called with the event waiters lock held, see libusb_lock_event_waiters().
This function will block until any of the following conditions are met:
Condition 1 is obvious. Condition 2 unblocks your thread after the callback for the transfer has completed. Condition 3 is important because it means that the thread that was previously handling events is no longer doing so, so if any events are to complete, another thread needs to step up and start event handling.
This function releases the event waiters lock before putting your thread to sleep, and reacquires the lock as it is being woken up.
ctx | the context to operate on, or NULL for the default context | |
tv | maximum timeout for this blocking function. A NULL value indicates unlimited timeout. |
1 if the timeout expired
int libusb_handle_events_timeout | ( | libusb_context * | ctx, | |
struct timeval * | tv | |||
) |
Handle any pending events.
libusb determines "pending events" by checking if any timeouts have expired and by checking the set of file descriptors for activity.
If a zero timeval is passed, this function will handle any already-pending events and then immediately return in non-blocking style.
If a non-zero timeval is passed and no events are currently pending, this function will block waiting for events to handle up until the specified timeout. If an event arrives or a signal is raised, this function will return early.
ctx | the context to operate on, or NULL for the default context | |
tv | the maximum time to block waiting for events, or zero for non-blocking mode |
int libusb_handle_events | ( | libusb_context * | ctx | ) |
Handle any pending events in blocking mode.
There is currently a timeout hardcoded at 60 seconds but we plan to make it unlimited in future. For finer control over whether this function is blocking or non-blocking, or for control over the timeout, use libusb_handle_events_timeout() instead.
ctx | the context to operate on, or NULL for the default context |
int libusb_handle_events_locked | ( | libusb_context * | ctx, | |
struct timeval * | tv | |||
) |
Handle any pending events by polling file descriptors, without checking if any other threads are already doing so.
Must be called with the event lock held, see libusb_lock_events().
This function is designed to be called under the situation where you have taken the event lock and are calling poll()/select() directly on libusb's file descriptors (as opposed to using libusb_handle_events() or similar). You detect events on libusb's descriptors, so you then call this function with a zero timeout value (while still holding the event lock).
ctx | the context to operate on, or NULL for the default context | |
tv | the maximum time to block waiting for events, or zero for non-blocking mode |
int libusb_pollfds_handle_timeouts | ( | libusb_context * | ctx | ) |
Determines whether your application must apply special timing considerations when monitoring libusb's file descriptors.
This function is only useful for applications which retrieve and poll libusb's file descriptors in their own main loop (The more advanced option).
Ordinarily, libusb's event handler needs to be called into at specific moments in time (in addition to times when there is activity on the file descriptor set). The usual approach is to use libusb_get_next_timeout() to learn about when the next timeout occurs, and to adjust your poll()/select() timeout accordingly so that you can make a call into the library at that time.
Some platforms supported by libusb do not come with this baggage - any events relevant to timing will be represented by activity on the file descriptor set, and libusb_get_next_timeout() will always return 0. This function allows you to detect whether you are running on such a platform.
Since v1.0.5.
ctx | the context to operate on, or NULL for the default context |
int libusb_get_next_timeout | ( | libusb_context * | ctx, | |
struct timeval * | tv | |||
) |
Determine the next internal timeout that libusb needs to handle.
You only need to use this function if you are calling poll() or select() or similar on libusb's file descriptors yourself - you do not need to use it if you are calling libusb_handle_events() or a variant directly.
You should call this function in your main loop in order to determine how long to wait for select() or poll() to return results. libusb needs to be called into at this timeout, so you should use it as an upper bound on your select() or poll() call.
When the timeout has expired, call into libusb_handle_events_timeout() (perhaps in non-blocking mode) so that libusb can handle the timeout.
This function may return 1 (success) and an all-zero timeval. If this is the case, it indicates that libusb has a timeout that has already expired so you should call libusb_handle_events_timeout() or similar immediately. A return code of 0 indicates that there are no pending timeouts.
On some platforms, this function will always returns 0 (no pending timeouts). See Notes on time-based events.
ctx | the context to operate on, or NULL for the default context | |
tv | output location for a relative time against the current clock in which libusb must be called into in order to process timeout events |
void libusb_set_pollfd_notifiers | ( | libusb_context * | ctx, | |
libusb_pollfd_added_cb | added_cb, | |||
libusb_pollfd_removed_cb | removed_cb, | |||
void * | user_data | |||
) |
Register notification functions for file descriptor additions/removals.
These functions will be invoked for every new or removed file descriptor that libusb uses as an event source.
To remove notifiers, pass NULL values for the function pointers.
Note that file descriptors may have been added even before you register these notifiers (e.g. at libusb_init() time).
Additionally, note that the removal notifier may be called during libusb_exit() (e.g. when it is closing file descriptors that were opened and added to the poll set at libusb_init() time). If you don't want this, remove the notifiers immediately before calling libusb_exit().
ctx | the context to operate on, or NULL for the default context | |
added_cb | pointer to function for addition notifications | |
removed_cb | pointer to function for removal notifications | |
user_data | User data to be passed back to callbacks (useful for passing context information) |
struct libusb_pollfd** libusb_get_pollfds | ( | libusb_context * | ctx | ) | [read] |
Retrieve a list of file descriptors that should be polled by your main loop as libusb event sources.
The returned list is NULL-terminated and should be freed with free() when done. The actual list contents must not be touched.
ctx | the context to operate on, or NULL for the default context |