/alps/ipecamera

To get this branch, use:
bzr branch http://suren.me/webbzr/alps/ipecamera

« back to all changes in this revision

Viewing changes to ipecamera/events.c

  • Committer: Suren A. Chilingaryan
  • Date: 2011-12-12 04:45:35 UTC
  • Revision ID: csa@dside.dyndns.org-20111212044535-6no1q7g230i8uvlv
multithread preprocessing of ipecamera frames and code reorganization

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#define _IPECAMERA_IMAGE_C
 
2
#define _BSD_SOURCE
 
3
#define _GNU_SOURCE
 
4
 
 
5
#include <stdio.h>
 
6
#include <stdlib.h>
 
7
#include <unistd.h>
 
8
#include <string.h>
 
9
#include <sys/time.h>
 
10
#include <pthread.h>
 
11
#include <assert.h>
 
12
 
 
13
#include <ufodecode.h>
 
14
 
 
15
#include "../tools.h"
 
16
#include "../error.h"
 
17
 
 
18
#include "pcilib.h"
 
19
#include "public.h"
 
20
#include "private.h"
 
21
#include "events.h"
 
22
 
 
23
int ipecamera_stream(pcilib_context_t *vctx, pcilib_event_callback_t callback, void *user) {
 
24
    int err = 0;
 
25
    int do_stop = 0;
 
26
    
 
27
    ipecamera_event_info_t info;
 
28
    ipecamera_t *ctx = (ipecamera_t*)vctx;
 
29
 
 
30
    if (!ctx) {
 
31
        pcilib_error("IPECamera imaging is not initialized");
 
32
        return PCILIB_ERROR_NOTINITIALIZED;
 
33
    }
 
34
 
 
35
    ctx->streaming = 1;
 
36
    ctx->run_streamer = 1;
 
37
 
 
38
    if (!ctx->started) {
 
39
        err = ipecamera_start(vctx, PCILIB_EVENTS_ALL, PCILIB_EVENT_FLAGS_DEFAULT);
 
40
        if (err) {
 
41
            ctx->streaming = 0;
 
42
            return err;
 
43
        }
 
44
        
 
45
        do_stop = 1;
 
46
    }
 
47
    
 
48
        // This loop iterates while the generation
 
49
    while ((ctx->run_streamer)||(ctx->reported_id != ctx->event_id)) {
 
50
        while (ctx->reported_id != ctx->event_id) {
 
51
            if ((ctx->event_id - ctx->reported_id) > (ctx->buffer_size - IPECAMERA_RESERVE_BUFFERS)) ctx->reported_id = ctx->event_id - (ctx->buffer_size - 1) - IPECAMERA_RESERVE_BUFFERS;
 
52
            else ++ctx->reported_id;
 
53
 
 
54
            memcpy(&info, ctx->frame + ((ctx->reported_id-1)%ctx->buffer_size), sizeof(ipecamera_event_info_t));
 
55
 
 
56
            if ((ctx->event_id - ctx->reported_id) < ctx->buffer_size) {
 
57
                err = callback(ctx->reported_id, (pcilib_event_info_t*)&info, user);
 
58
                if (err <= 0) {
 
59
                    if (err < 0) err = -err;
 
60
                    break;
 
61
                }
 
62
            }
 
63
        }
 
64
        usleep(IPECAMERA_NOFRAME_SLEEP);
 
65
    }
 
66
 
 
67
    ctx->streaming = 0;
 
68
 
 
69
    if (do_stop) {
 
70
        ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
 
71
    }
 
72
    
 
73
 
 
74
    return err;
 
75
}
 
76
 
 
77
int ipecamera_next_event(pcilib_context_t *vctx, pcilib_timeout_t timeout, pcilib_event_id_t *evid, size_t info_size, pcilib_event_info_t *info) {
 
78
    struct timeval tv;
 
79
    ipecamera_t *ctx = (ipecamera_t*)vctx;
 
80
 
 
81
    if (!ctx) {
 
82
        pcilib_error("IPECamera imaging is not initialized");
 
83
        return PCILIB_ERROR_NOTINITIALIZED;
 
84
    }
 
85
 
 
86
    if (!ctx->started) {
 
87
        pcilib_error("IPECamera is not in grabbing mode");
 
88
        return PCILIB_ERROR_INVALID_REQUEST;
 
89
    }
 
90
 
 
91
    if (ctx->reported_id == ctx->event_id) {
 
92
        if (timeout) {
 
93
            pcilib_calc_deadline(&tv, timeout);
 
94
            
 
95
            while ((pcilib_calc_time_to_deadline(&tv) > 0)&&(ctx->reported_id == ctx->event_id))
 
96
                usleep(IPECAMERA_NOFRAME_SLEEP);
 
97
        }
 
98
        
 
99
        if (ctx->reported_id == ctx->event_id) return PCILIB_ERROR_TIMEOUT;
 
100
    }
 
101
 
 
102
retry:
 
103
    if ((ctx->event_id - ctx->reported_id) > (ctx->buffer_size - IPECAMERA_RESERVE_BUFFERS)) ctx->reported_id = ctx->event_id - (ctx->buffer_size - 1) - IPECAMERA_RESERVE_BUFFERS;
 
104
    else ++ctx->reported_id;
 
105
 
 
106
    if (evid) *evid = ctx->reported_id;
 
107
 
 
108
    if (info) {
 
109
        if (info_size >= sizeof(ipecamera_event_info_t))
 
110
            memcpy(info, ctx->frame + ((ctx->reported_id-1)%ctx->buffer_size), sizeof(ipecamera_event_info_t));
 
111
        else if (info_size >= sizeof(pcilib_event_info_t))
 
112
            memcpy(info, ctx->frame + ((ctx->reported_id-1)%ctx->buffer_size), sizeof(pcilib_event_info_t));
 
113
        else
 
114
            return PCILIB_ERROR_INVALID_ARGUMENT;
 
115
    }
 
116
    
 
117
    if ((ctx->event_id - ctx->reported_id) >= ctx->buffer_size) goto retry;
 
118
    
 
119
    return 0;
 
120
}
 
121