summaryrefslogtreecommitdiff
path: root/snapshot.c
diff options
context:
space:
mode:
authorLaurent Pinchart <laurent.pinchart@ideasonboard.com>2012-02-22 23:27:15 +0100
committerLaurent Pinchart <laurent.pinchart@ideasonboard.com>2012-04-16 23:40:56 +0200
commit211507d598b67e6e274275ab472d5e81ec1afcec (patch)
tree47d4ba219c740b85dd563e312083f2787016d0ec /snapshot.c
parent4dd4dcb4f594c872df222390031975d06adc7e71 (diff)
Factor event handling code out into events.c
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Diffstat (limited to 'snapshot.c')
-rw-r--r--snapshot.c153
1 files changed, 19 insertions, 134 deletions
diff --git a/snapshot.c b/snapshot.c
index bc2b7da..da63b36 100644
--- a/snapshot.c
+++ b/snapshot.c
@@ -46,8 +46,9 @@
#include "isp/v4l2.h"
#include "isp/v4l2-pool.h"
+#include "events.h"
+
#define MEDIA_DEVICE "/dev/media0"
-#define SELECT_TIMEOUT 2000 /* in milliseconds */
#define VIEWFINDER_WIDTH 1024
#define VIEWFINDER_HEIGHT 768
@@ -55,115 +56,33 @@
#define SNAPSHOT_HEIGHT 1536
static unsigned int frame_count = 0;
-static bool done = false;
static unsigned int snapshot_interval = 20;
static struct timespec snapshot_time;
+static struct events events;
+
/* -----------------------------------------------------------------------------
* Events
*/
-struct event_fd {
- struct list_entry list;
-
- int fd;
- enum omap3_isp_event_type type;
- void (*callback)(void *priv);
- void *priv;
-};
-
-static struct {
- struct list_entry events;
-
- int maxfd;
- fd_set rfds;
- fd_set wfds;
-} events;
-
-static void events_watch_fd(int fd, enum omap3_isp_event_type type,
- void(*callback)(void *), void *priv)
-{
- struct event_fd *event;
-
- event = malloc(sizeof *event);
- if (event == NULL)
- return;
-
- event->fd = fd;
- event->type = type;
- event->callback = callback;
- event->priv = priv;
-
- if (event->type == OMAP3_ISP_EVENT_READ)
- FD_SET(fd, &events.rfds);
- else
- FD_SET(fd, &events.wfds);
-
- events.maxfd = max(events.maxfd, fd);
-
- list_append(&event->list, &events.events);
-}
-
-static void events_unwatch_fd(int fd)
-{
- struct event_fd *event = NULL;
- struct event_fd *entry;
- int maxfd = 0;
-
- list_for_each_entry(entry, &events.events, list) {
- if (entry->fd == fd)
- event = entry;
- else
- maxfd = max(maxfd, entry->fd);
- }
-
- if (event == NULL)
- return;
-
- if (event->type == OMAP3_ISP_EVENT_READ)
- FD_CLR(fd, &events.rfds);
- else
- FD_CLR(fd, &events.wfds);
-
- events.maxfd = maxfd;
-
- list_remove(&event->list);
- free(event);
-}
-
-static void events_init(void)
+static void __events_watch_fd(int fd, enum omap3_isp_event_type type,
+ void(*callback)(void *), void *priv)
{
- memset(&events, 0, sizeof events);
-
- FD_ZERO(&events.rfds);
- FD_ZERO(&events.wfds);
- events.maxfd = 0;
- list_init(&events.events);
+ events_watch_fd(&events, fd, type, callback, priv);
}
-static void events_dispatch(const fd_set *rfds, const fd_set *wfds)
+static void __events_unwatch_fd(int fd)
{
- struct event_fd *event;
-
- list_for_each_entry(event, &events.events, list) {
- if (event->type == OMAP3_ISP_EVENT_READ &&
- FD_ISSET(event->fd, rfds))
- event->callback(event->priv);
- if (event->type == OMAP3_ISP_EVENT_WRITE &&
- FD_ISSET(event->fd, wfds))
- event->callback(event->priv);
- }
+ events_unwatch_fd(&events, fd);
}
/* -------------------------------------------------------------------------- */
static void sigint_handler(int signal __attribute__((__unused__)))
{
- /* Set the done flag to true when the user presses CTRL-C to interrupt
- * the main loop.
- */
- done = true;
+ /* Stop the main loop when the user presses CTRL-C. */
+ events_stop(&events);
}
static void snapshot_process(struct omap3_isp_device *isp,
@@ -284,7 +203,6 @@ int main(int argc __attribute__((__unused__)), char *argv[] __attribute__((__unu
struct omap3_isp_device *isp = NULL;
struct omap3_isp_operations ops;
struct timespec start, end;
- unsigned int count = 0;
int exit_code = EXIT_FAILURE;
float fps;
int ret;
@@ -316,7 +234,7 @@ int main(int argc __attribute__((__unused__)), char *argv[] __attribute__((__unu
}
}
- events_init();
+ events_init(&events);
/* Register a signal handler for SIGINT, received when the user presses
* CTRL-C. This will allow the main loop to be interrupted, and resources
@@ -328,8 +246,8 @@ int main(int argc __attribute__((__unused__)), char *argv[] __attribute__((__unu
memset(&ops, 0, sizeof ops);
ops.viewfinder_ready = viewfinder_process;
ops.snapshot_ready = snapshot_process;
- ops.watch_fd = events_watch_fd;
- ops.unwatch_fd = events_unwatch_fd;
+ ops.watch_fd = __events_watch_fd;
+ ops.unwatch_fd = __events_unwatch_fd;
isp = omap3_isp_open(MEDIA_DEVICE, &ops);
if (isp == NULL) {
@@ -391,42 +309,9 @@ int main(int argc __attribute__((__unused__)), char *argv[] __attribute__((__unu
clock_gettime(CLOCK_MONOTONIC, &start);
- /* Main capture loop. Wait for a video buffer using select() and process
- * it.
- */
- while (!done) {
- struct timeval timeout;
- fd_set rfds;
- fd_set wfds;
-
- timeout.tv_sec = SELECT_TIMEOUT / 1000;
- timeout.tv_usec = (SELECT_TIMEOUT % 1000) * 1000;
- rfds = events.rfds;
- wfds = events.wfds;
-
- ret = select(events.maxfd + 1, &rfds, &wfds, NULL, &timeout);
- if (ret < 0) {
- /* EINTR means that a signal has been received, continue
- * to the next iteration in that case.
- */
- if (errno == EINTR)
- continue;
-
- printf("error: select failed with %d\n", errno);
- goto cleanup;
- }
- if (ret == 0) {
- /* select() should never time out as the ISP is supposed
- * to capture images continuously. A timeout is thus
- * considered as a fatal error.
- */
- printf("error: select timeout\n");
- goto cleanup;
- }
-
- events_dispatch(&rfds, &wfds);
- count++;
- }
+ /* Main capture loop. */
+ if (events_loop(&events))
+ goto cleanup;
clock_gettime(CLOCK_MONOTONIC, &end);
@@ -441,9 +326,9 @@ int main(int argc __attribute__((__unused__)), char *argv[] __attribute__((__unu
end.tv_nsec += 1000000000;
}
- fps = count / (end.tv_sec + end.tv_nsec / 1000000000.0);
+ fps = frame_count / (end.tv_sec + end.tv_nsec / 1000000000.0);
- printf("%u images processed in %lu.%06lu seconds (%f fps)\n", count,
+ printf("%u images processed in %lu.%06lu seconds (%f fps)\n", frame_count,
end.tv_sec, end.tv_nsec / 1000, fps);
exit_code = EXIT_SUCCESS;