/alps/ipecamera

To get this branch, use:
bzr branch http://suren.me/webbzr/alps/ipecamera
15 by Suren A. Chilingaryan
Infrastructure for event API
1
#define _IPECAMERA_IMAGE_C
277 by Suren A. Chilingaryan
Build RPM
2
#define _DEFAULT_SOURCE
15 by Suren A. Chilingaryan
Infrastructure for event API
3
#define _BSD_SOURCE
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
4
#define _GNU_SOURCE
15 by Suren A. Chilingaryan
Infrastructure for event API
5
6
#include <stdio.h>
7
#include <stdlib.h>
8
#include <unistd.h>
9
#include <string.h>
10
#include <sys/time.h>
117 by Suren A. Chilingaryan
new event architecture, first trial
11
#include <pthread.h>
15 by Suren A. Chilingaryan
Infrastructure for event API
12
#include <assert.h>
13
124 by Suren A. Chilingaryan
Image frames decoding
14
#include <ufodecode.h>
15
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
16
#include <pcilib.h>
17
#include <pcilib/tools.h>
18
#include <pcilib/error.h>
19
#include <pcilib/event.h>
276 by Suren A. Chilingaryan
Update to new version of pcitool
20
#include <pcilib/cpu.h>
21
#include <pcilib/timing.h>
15 by Suren A. Chilingaryan
Infrastructure for event API
22
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
23
#include "private.h"
15 by Suren A. Chilingaryan
Infrastructure for event API
24
#include "model.h"
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
25
#include "reader.h"
26
#include "events.h"
27
#include "data.h"
15 by Suren A. Chilingaryan
Infrastructure for event API
28
70 by Suren A. Chilingaryan
Support modifications of DMA engine and allow DMA customizations by Event engine
29
15 by Suren A. Chilingaryan
Infrastructure for event API
30
#define FIND_REG(var, bank, name)  \
31
        ctx->var = pcilib_find_register(pcilib, bank, name); \
32
	if (ctx->var ==  PCILIB_REGISTER_INVALID) { \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
33
	    err = PCILIB_ERROR_NOTFOUND; \
15 by Suren A. Chilingaryan
Infrastructure for event API
34
	    pcilib_error("Unable to find a %s register", name); \
35
	}
36
    
37
38
#define GET_REG(reg, var) \
93 by root
DMA support in IPE Camera
39
    if (!err) { \
40
	err = pcilib_read_register_by_id(pcilib, ctx->reg, &var); \
41
	if (err) { \
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
42
	    pcilib_error("Error reading %s register", model_info->registers[ctx->reg].name); \
93 by root
DMA support in IPE Camera
43
	} \
15 by Suren A. Chilingaryan
Infrastructure for event API
44
    }
45
46
#define SET_REG(reg, val) \
93 by root
DMA support in IPE Camera
47
    if (!err) { \
48
	err = pcilib_write_register_by_id(pcilib, ctx->reg, val); \
49
	if (err) { \
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
50
	    pcilib_error("Error writting %s register", model_info->registers[ctx->reg].name); \
93 by root
DMA support in IPE Camera
51
	} \
52
    }
15 by Suren A. Chilingaryan
Infrastructure for event API
53
54
#define CHECK_REG(reg, check) \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
55
    if (!err) { \
56
	err = pcilib_read_register_by_id(pcilib, ctx->reg, &value); \
57
	if (err) { \
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
58
	    pcilib_error("Error reading %s register", model_info->registers[ctx->reg].name); \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
59
	} \
171 by Suren A. Chilingaryan
Fix temperature register of ipecamera and prepend all cmosis registers with _cmosis prefix
60
	if (value != check) { \
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
61
	    pcilib_error("Unexpected value (0x%lx) of register %s", value, model_info->registers[ctx->reg].name); \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
62
	    err = PCILIB_ERROR_INVALID_DATA; \
63
	} \
64
    }
65
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
66
#define CHECK_STATUS()
67
	    //CHECK_REG(status_reg, IPECAMERA_GET_EXPECTED_STATUS(ctx))
175 by Suren A. Chilingaryan
Support both UFO4 and UFO5 frame formats
68
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
69
#define CHECK_VALUE(value, val) \
70
    if ((!err)&&(value != val)) { \
35 by Suren A. Chilingaryan
Multiline grabbing
71
	pcilib_error("Unexpected value (0x%x) in data stream (0x%x is expected)", value, val); \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
72
	err = PCILIB_ERROR_INVALID_DATA; \
73
    }
74
75
#define CHECK_FLAG(flag, check, ...) \
76
    if ((!err)&&(!(check))) { \
35 by Suren A. Chilingaryan
Multiline grabbing
77
	pcilib_error("Unexpected value (0x%x) of " flag,  __VA_ARGS__); \
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
78
	err = PCILIB_ERROR_INVALID_DATA; \
15 by Suren A. Chilingaryan
Infrastructure for event API
79
    }
80
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
81
#define LOCK(lock_name) \
82
    err = pcilib_try_lock(ctx->lock_name##_lock); \
83
    if (err) { \
84
	pcilib_error("IPECamera is busy"); \
85
	return PCILIB_ERROR_BUSY; \
86
    } \
87
    ctx->lock_name##_locked = 1;
88
89
#define UNLOCK(lock_name) \
90
    if (ctx->lock_name##_locked) { \
91
	pcilib_unlock(ctx->lock_name##_lock); \
92
	ctx->lock_name##_locked = 0; \
93
    }
15 by Suren A. Chilingaryan
Infrastructure for event API
94
31 by Suren A. Chilingaryan
Introduce pcilib_context_t type instead pointer to void
95
pcilib_context_t *ipecamera_init(pcilib_t *pcilib) {
15 by Suren A. Chilingaryan
Infrastructure for event API
96
    int err = 0; 
97
    
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
98
    const pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
99
15 by Suren A. Chilingaryan
Infrastructure for event API
100
    ipecamera_t *ctx = malloc(sizeof(ipecamera_t));
101
102
    if (ctx) {
178 by Suren A. Chilingaryan
Detect firmware version during initialization
103
	pcilib_register_value_t value;
104
	
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
105
	memset(ctx, 0, sizeof(ipecamera_t));
178 by Suren A. Chilingaryan
Detect firmware version during initialization
106
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
107
	ctx->run_lock = pcilib_get_lock(pcilib, PCILIB_LOCK_FLAGS_DEFAULT, "ipecamera");
108
	ctx->stream_lock = pcilib_get_lock(pcilib, PCILIB_LOCK_FLAGS_DEFAULT, "ipecamera/stream");
109
	ctx->trigger_lock = pcilib_get_lock(pcilib, PCILIB_LOCK_FLAGS_DEFAULT, "ipecamera/trigger");
110
111
	if (!ctx->run_lock||!ctx->stream_lock||!ctx->trigger_lock) {
112
	    free(ctx);
113
	    pcilib_error("Failed to initialize locks to protect ipecamera operation");
114
	    return NULL;
115
	}
116
272 by Suren A. Chilingaryan
Adjust buffer sizes to reduce memory consumption with CMOSIS20 camera
117
	ctx->dim.bpp = sizeof(ipecamera_pixel_t) * 8;
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
118
	ctx->buffer_size = IPECAMERA_DEFAULT_BUFFER_SIZE;
252 by Suren A. Chilingaryan
Cleanup
119
15 by Suren A. Chilingaryan
Infrastructure for event API
120
	FIND_REG(status_reg, "fpga", "status");
121
	FIND_REG(control_reg, "fpga", "control");
132 by Suren A. Chilingaryan
Minor fixes and improvements
122
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
123
	FIND_REG(status2_reg, "fpga", "status2");
132 by Suren A. Chilingaryan
Minor fixes and improvements
124
	FIND_REG(status3_reg, "fpga", "status3");
15 by Suren A. Chilingaryan
Infrastructure for event API
125
175 by Suren A. Chilingaryan
Support both UFO4 and UFO5 frame formats
126
	FIND_REG(firmware_version_reg, "fpga", "firmware_version");
168 by Suren A. Chilingaryan
Support 12-bit modes
127
	FIND_REG(adc_resolution_reg, "fpga", "adc_resolution");
128
	FIND_REG(output_mode_reg, "fpga", "output_mode");
174 by Suren A. Chilingaryan
Check for free space in camera DDR buffer before triggering event
129
	
130
	FIND_REG(max_frames_reg, "fpga", "ddr_max_frames");
131
	FIND_REG(num_frames_reg, "fpga", "ddr_num_frames");
117 by Suren A. Chilingaryan
new event architecture, first trial
132
178 by Suren A. Chilingaryan
Detect firmware version during initialization
133
	GET_REG(firmware_version_reg, value);
134
	switch (value) {
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
135
	 case IPECAMERA_FIRMWARE_UFO5:
178 by Suren A. Chilingaryan
Detect firmware version during initialization
136
	    ctx->firmware = value;
276 by Suren A. Chilingaryan
Update to new version of pcitool
137
	    err = pcilib_add_registers(pcilib, 0, 0, cmosis_registers, NULL);
260 by Suren A. Chilingaryan
Support registers of CMOSIS20000 camera
138
	    break;
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
139
	 case IPECAMERA_FIRMWARE_CMOSIS20:
260 by Suren A. Chilingaryan
Support registers of CMOSIS20000 camera
140
	    ctx->firmware = value;
272 by Suren A. Chilingaryan
Adjust buffer sizes to reduce memory consumption with CMOSIS20 camera
141
	    ctx->buffer_size = IPECAMERA_DEFAULT_CMOSIS20_BUFFER_SIZE;
276 by Suren A. Chilingaryan
Update to new version of pcitool
142
	    err = pcilib_add_registers(pcilib, 0, 0, cmosis20000_registers, NULL);
178 by Suren A. Chilingaryan
Detect firmware version during initialization
143
	    break;
144
	 default:
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
145
	    ctx->firmware = IPECAMERA_FIRMWARE_UNKNOWN;
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
146
    	    pcilib_warning("Unsupported version of firmware (%lu)", value);
178 by Suren A. Chilingaryan
Detect firmware version during initialization
147
	}
148
260 by Suren A. Chilingaryan
Support registers of CMOSIS20000 camera
149
//	FIND_REG(n_lines_reg, "cmosis", "cmosis_number_lines"); // cmosis_number_lines_single v.6 ?
150
//	FIND_REG(line_reg, "cmosis", "cmosis_start1"); // cmosis_start_single v.6 ?
151
//	FIND_REG(exposure_reg, "cmosis", "cmosis_exp_time");
152
//	FIND_REG(flip_reg, "cmosis", "cmosis_image_flipping");
153
154
252 by Suren A. Chilingaryan
Cleanup
155
#ifdef IPECAMERA_ADJUST_BUFFER_SIZE 
185 by Suren A. Chilingaryan
More fixes to frame separation in multiframe mode; debugging mode
156
	GET_REG(max_frames_reg, value);
187 by Suren A. Chilingaryan
Consider RESERVE_BUFFERS while computing buffer size required for ipecamera fast reject
157
	if ((value + IPECAMERA_RESERVE_BUFFERS + 3) > ctx->buffer_size) {
252 by Suren A. Chilingaryan
Cleanup
158
	    int val, bits = 0;
187 by Suren A. Chilingaryan
Consider RESERVE_BUFFERS while computing buffer size required for ipecamera fast reject
159
	    ctx->buffer_size = (value + 1) + IPECAMERA_RESERVE_BUFFERS + 2;
252 by Suren A. Chilingaryan
Cleanup
160
	    for (val = ctx->buffer_size; val; val = val >> 1) bits++;
161
	    ctx->buffer_size = 1 << bits; 
185 by Suren A. Chilingaryan
More fixes to frame separation in multiframe mode; debugging mode
162
	}
252 by Suren A. Chilingaryan
Cleanup
163
#endif /* IPECAMERA_ADJUST_BUFFER_SIZE */
185 by Suren A. Chilingaryan
More fixes to frame separation in multiframe mode; debugging mode
164
165
93 by root
DMA support in IPE Camera
166
	ctx->rdma = PCILIB_DMA_ENGINE_INVALID;
167
15 by Suren A. Chilingaryan
Infrastructure for event API
168
	if (err) {
169
	    free(ctx);
170
	    return NULL;
171
	}
172
    }
173
    
43 by root
Enumerate DMA engines
174
    return (pcilib_context_t*)ctx;
15 by Suren A. Chilingaryan
Infrastructure for event API
175
}
176
31 by Suren A. Chilingaryan
Introduce pcilib_context_t type instead pointer to void
177
void ipecamera_free(pcilib_context_t *vctx) {
15 by Suren A. Chilingaryan
Infrastructure for event API
178
    if (vctx) {
179
	ipecamera_t *ctx = (ipecamera_t*)vctx;
117 by Suren A. Chilingaryan
new event architecture, first trial
180
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
181
182
	if (ctx->trigger_lock)
183
	    pcilib_return_lock(vctx->pcilib, PCILIB_LOCK_FLAGS_DEFAULT, ctx->trigger_lock);
184
185
	if (ctx->stream_lock)
186
	    pcilib_return_lock(vctx->pcilib, PCILIB_LOCK_FLAGS_DEFAULT, ctx->stream_lock);
187
	
188
	if (ctx->run_lock)
189
	    pcilib_return_lock(vctx->pcilib, PCILIB_LOCK_FLAGS_DEFAULT, ctx->run_lock);
190
15 by Suren A. Chilingaryan
Infrastructure for event API
191
	free(ctx);
192
    }
193
}
194
70 by Suren A. Chilingaryan
Support modifications of DMA engine and allow DMA customizations by Event engine
195
pcilib_dma_context_t *ipecamera_init_dma(pcilib_context_t *vctx) {
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
196
    ipecamera_t *ctx = (ipecamera_t*)vctx;
70 by Suren A. Chilingaryan
Support modifications of DMA engine and allow DMA customizations by Event engine
197
    
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
198
    const pcilib_model_description_t *model_info = pcilib_get_model_description(vctx->pcilib);
199
    if ((!model_info->dma)||(!model_info->dma->api)||(!model_info->dma->api->init)) {
70 by Suren A. Chilingaryan
Support modifications of DMA engine and allow DMA customizations by Event engine
200
	pcilib_error("The DMA engine is not configured in model");
201
	return NULL;
202
    }
89 by Suren A. Chilingaryan
Few fixes for IPE Camera modification
203
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
204
    if (ctx->firmware) {
276 by Suren A. Chilingaryan
Update to new version of pcitool
205
	return model_info->dma->api->init(vctx->pcilib, "ipecamera", NULL);
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
206
    } else {
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
207
	return model_info->dma->api->init(vctx->pcilib, "pci", NULL);
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
208
    }
70 by Suren A. Chilingaryan
Support modifications of DMA engine and allow DMA customizations by Event engine
209
}
210
211
17 by Suren A. Chilingaryan
Allow access to implementation context and provide call to set size of internal buffer for IPECamera
212
int ipecamera_set_buffer_size(ipecamera_t *ctx, int size) {
213
    if (ctx->started) {
214
	pcilib_error("Can't change buffer size while grabbing");
215
	return PCILIB_ERROR_INVALID_REQUEST;
216
    }
217
    
117 by Suren A. Chilingaryan
new event architecture, first trial
218
    if (size < 2) {
17 by Suren A. Chilingaryan
Allow access to implementation context and provide call to set size of internal buffer for IPECamera
219
	pcilib_error("The buffer size is too small");
220
	return PCILIB_ERROR_INVALID_REQUEST;
221
    }
117 by Suren A. Chilingaryan
new event architecture, first trial
222
    
250 by Suren A. Chilingaryan
Added a small grabbing example
223
    if ((size^(size-1)) < size) {
117 by Suren A. Chilingaryan
new event architecture, first trial
224
	pcilib_error("The buffer size is not power of 2");
225
    }
226
    
17 by Suren A. Chilingaryan
Allow access to implementation context and provide call to set size of internal buffer for IPECamera
227
    ctx->buffer_size = size;
228
    
229
    return 0;
230
}
231
31 by Suren A. Chilingaryan
Introduce pcilib_context_t type instead pointer to void
232
int ipecamera_reset(pcilib_context_t *vctx) {
117 by Suren A. Chilingaryan
new event architecture, first trial
233
    int err = 0;
15 by Suren A. Chilingaryan
Infrastructure for event API
234
    ipecamera_t *ctx = (ipecamera_t*)vctx;
117 by Suren A. Chilingaryan
new event architecture, first trial
235
    pcilib_t *pcilib = vctx->pcilib;
15 by Suren A. Chilingaryan
Infrastructure for event API
236
237
    pcilib_register_t control, status;
238
    pcilib_register_value_t value;
27 by Suren A. Chilingaryan
Set correct hexdecimal values of registers during IPECamera reset and readout (I was setting them as decimals before)
239
15 by Suren A. Chilingaryan
Infrastructure for event API
240
    if (!ctx) {
241
	pcilib_error("IPECamera imaging is not initialized");
242
	return PCILIB_ERROR_NOTINITIALIZED;
243
    }
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
244
    
117 by Suren A. Chilingaryan
new event architecture, first trial
245
    pcilib = vctx->pcilib;
15 by Suren A. Chilingaryan
Infrastructure for event API
246
    control = ctx->control_reg;
247
    status = ctx->status_reg;
248
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
249
    LOCK(run);
250
251
    ipecamera_debug(API, "ipecamera: starting");
252
253
    if (ctx->firmware == IPECAMERA_FIRMWARE_UFO5) {
254
	    // Set Reset bit to CMOSIS
255
	err = pcilib_write_register_by_id(pcilib, control, 0x1e4);
256
	if (err) {
257
	    UNLOCK(run);
258
	    pcilib_error("Error setting FPGA reset bit");
259
	    return err;
260
	}
261
	usleep(IPECAMERA_CMOSIS_RESET_DELAY);
15 by Suren A. Chilingaryan
Infrastructure for event API
262
263
	// Remove Reset bit to CMOSIS
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
264
	err = pcilib_write_register_by_id(pcilib, control, 0x1e1);
265
	if (err) {
266
	    UNLOCK(run);
267
	    pcilib_error("Error reseting FPGA reset bit");
268
	    return err;
269
	}
270
	usleep(IPECAMERA_CMOSIS_REGISTER_DELAY);
15 by Suren A. Chilingaryan
Infrastructure for event API
271
272
	// Special settings for CMOSIS v.2
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
273
	value = 01; err = pcilib_write_register_space(pcilib, "cmosis", 115, 1, &value);
274
	if (err) {
275
	    UNLOCK(run);
276
	    pcilib_error("Error setting CMOSIS configuration");
277
	    return err;
278
	}
279
	usleep(IPECAMERA_CMOSIS_REGISTER_DELAY);
27 by Suren A. Chilingaryan
Set correct hexdecimal values of registers during IPECamera reset and readout (I was setting them as decimals before)
280
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
281
	value = 07; err = pcilib_write_register_space(pcilib, "cmosis", 82, 1, &value);
282
	if (err) {
283
	    UNLOCK(run);
284
	    pcilib_error("Error setting CMOSIS configuration");
285
	    return err;
286
	}
287
	usleep(IPECAMERA_CMOSIS_REGISTER_DELAY);
288
	pcilib_warning("Reset procedure is not complete");
289
    } else {
290
	pcilib_warning("Reset procedure is not implemented");
15 by Suren A. Chilingaryan
Infrastructure for event API
291
    }
292
39 by root
Move to new FPGA design
293
    usleep(10000);
117 by Suren A. Chilingaryan
new event architecture, first trial
294
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
295
296
    CHECK_STATUS();
15 by Suren A. Chilingaryan
Infrastructure for event API
297
    if (err) {
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
298
	err = pcilib_read_register_by_id(pcilib, status, &value);
299
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
300
	UNLOCK(run);
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
301
	if (err) pcilib_error("Error reading status register");
302
	else pcilib_error("Camera returns unexpected status (status: %lx)", value);
303
15 by Suren A. Chilingaryan
Infrastructure for event API
304
	return PCILIB_ERROR_VERIFY;
305
    }
306
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
307
    err = pcilib_skip_dma(vctx->pcilib, ctx->rdma);
308
    UNLOCK(run);
309
310
    ipecamera_debug(API, "ipecamera: reset done");
311
    return err;
15 by Suren A. Chilingaryan
Infrastructure for event API
312
}
313
117 by Suren A. Chilingaryan
new event architecture, first trial
314
315
int ipecamera_start(pcilib_context_t *vctx, pcilib_event_t event_mask, pcilib_event_flags_t flags) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
316
    int i;
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
317
    int err = 0;
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
318
15 by Suren A. Chilingaryan
Infrastructure for event API
319
    ipecamera_t *ctx = (ipecamera_t*)vctx;
117 by Suren A. Chilingaryan
new event architecture, first trial
320
    pcilib_t *pcilib = vctx->pcilib;
35 by Suren A. Chilingaryan
Multiline grabbing
321
    pcilib_register_value_t value;
117 by Suren A. Chilingaryan
new event architecture, first trial
322
    
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
323
    const pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
324
117 by Suren A. Chilingaryan
new event architecture, first trial
325
    pthread_attr_t attr;
326
    struct sched_param sched;
327
    
15 by Suren A. Chilingaryan
Infrastructure for event API
328
    if (!ctx) {
329
	pcilib_error("IPECamera imaging is not initialized");
330
	return PCILIB_ERROR_NOTINITIALIZED;
331
    }
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
332
17 by Suren A. Chilingaryan
Allow access to implementation context and provide call to set size of internal buffer for IPECamera
333
    if (ctx->started) {
334
	pcilib_error("IPECamera grabbing is already started");
335
	return PCILIB_ERROR_INVALID_REQUEST;
336
    }
35 by Suren A. Chilingaryan
Multiline grabbing
337
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
338
    LOCK(run);
339
262 by Suren A. Chilingaryan
Introduce API debugging
340
    ipecamera_debug(API, "ipecamera: starting");
341
15 by Suren A. Chilingaryan
Infrastructure for event API
342
    ctx->event_id = 0;
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
343
    ctx->preproc_id = 0;
29 by Suren A. Chilingaryan
Support non-callback way of getting events
344
    ctx->reported_id = 0;
117 by Suren A. Chilingaryan
new event architecture, first trial
345
    ctx->buffer_pos = 0;
346
    ctx->parse_data = (flags&PCILIB_EVENT_FLAG_RAW_DATA_ONLY)?0:1;
347
    ctx->cur_size = 0;
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
348
267 by Suren A. Chilingaryan
Handle frame headers split between 2 packets
349
#ifdef IPECAMERA_BUG_MULTIFRAME_HEADERS
350
    ctx->saved_header_size = 0;
351
#endif /* IPECAMERA_BUG_MULTIFRAME_HEADERS */
352
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
353
    switch (ctx->firmware) {
354
     case IPECAMERA_FIRMWARE_UFO5:
355
	ctx->dim.width = CMOSIS_WIDTH;
356
	ctx->dim.height = CMOSIS_MAX_LINES;
282 by Suren A. Chilingaryan
Support HighFlex-based ipecamera
357
358
	ctx->data_line_size = (1 + CMOSIS_PIXELS_PER_CHANNEL) * 32; 
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
359
	break;
360
     case IPECAMERA_FIRMWARE_CMOSIS20:
361
	ctx->dim.width = CMOSIS20_WIDTH;
362
	ctx->dim.height = CMOSIS20_MAX_LINES;
282 by Suren A. Chilingaryan
Support HighFlex-based ipecamera
363
284 by Suren A. Chilingaryan
Fix estimation of size of UFO6 frame (works for Desy camera)
364
	    // There is skipped C0 line once per every two lines (which are in fact encoded together)
365
	ctx->data_line_size = CMOSIS20_PIXELS_PER_CHANNEL * 32 + 16;
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
366
	break;
168 by Suren A. Chilingaryan
Support 12-bit modes
367
     default:
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
368
	UNLOCK(run);
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
369
	pcilib_error("Can't start undefined version (%lu) of IPECamera", ctx->firmware);
370
	return PCILIB_ERROR_INVALID_REQUEST;
371
    }
372
282 by Suren A. Chilingaryan
Support HighFlex-based ipecamera
373
    if ((1)||(ctx->firmware == IPECAMERA_FIRMWARE_UFO5)) {
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
374
	GET_REG(output_mode_reg, value);
375
	switch (value) {
376
	 case IPECAMERA_MODE_16_CHAN_IO:
377
	    ctx->cmosis_outputs = 16;
378
	    break;
379
         case IPECAMERA_MODE_4_CHAN_IO:
380
	    ctx->cmosis_outputs = 4;
381
	    break;
382
	 default:
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
383
	    UNLOCK(run);
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
384
	    pcilib_error("IPECamera reporting invalid output_mode 0x%lx", value);
385
	    return PCILIB_ERROR_INVALID_STATE;
386
	}
282 by Suren A. Chilingaryan
Support HighFlex-based ipecamera
387
    } 
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
388
389
	// We should be careful here (currently firmware matches format, but this may not be the case in future)
390
    ipecamera_compute_buffer_size(ctx, ctx->firmware, CMOSIS_FRAME_HEADER_SIZE, ctx->dim.height);
162 by Suren A. Chilingaryan
UFO5 size estimation
391
249 by Suren A. Chilingaryan
Simplify size tracking in the reader
392
    ctx->raw_size = ctx->roi_raw_size;
393
    ctx->padded_size = ctx->roi_padded_size;
162 by Suren A. Chilingaryan
UFO5 size estimation
394
124 by Suren A. Chilingaryan
Image frames decoding
395
    ctx->image_size = ctx->dim.width * ctx->dim.height;
117 by Suren A. Chilingaryan
new event architecture, first trial
396
174 by Suren A. Chilingaryan
Check for free space in camera DDR buffer before triggering event
397
    
398
    GET_REG(max_frames_reg, value);
399
    ctx->max_frames = value;
400
117 by Suren A. Chilingaryan
new event architecture, first trial
401
    ctx->buffer = malloc(ctx->padded_size * ctx->buffer_size);
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
402
    if (!ctx->buffer) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
403
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
117 by Suren A. Chilingaryan
new event architecture, first trial
404
	pcilib_error("Unable to allocate ring buffer (%lu bytes)", ctx->padded_size * ctx->buffer_size);
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
405
	return PCILIB_ERROR_MEMORY;
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
406
    }
407
124 by Suren A. Chilingaryan
Image frames decoding
408
    ctx->image = (ipecamera_pixel_t*)malloc(ctx->image_size * ctx->buffer_size * sizeof(ipecamera_pixel_t));
409
    if (!ctx->image) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
410
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
124 by Suren A. Chilingaryan
Image frames decoding
411
	pcilib_error("Unable to allocate image buffer (%lu bytes)", ctx->image_size * ctx->buffer_size * sizeof(ipecamera_pixel_t));
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
412
	return PCILIB_ERROR_MEMORY;
124 by Suren A. Chilingaryan
Image frames decoding
413
    }
414
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
415
    ctx->cmask = malloc(ctx->dim.height * ctx->buffer_size * sizeof(ipecamera_change_mask_t));
416
    if (!ctx->cmask) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
417
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
418
	pcilib_error("Unable to allocate change-mask buffer");
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
419
	return PCILIB_ERROR_MEMORY;
117 by Suren A. Chilingaryan
new event architecture, first trial
420
    }
421
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
422
    ctx->frame = (ipecamera_frame_t*)malloc(ctx->buffer_size * sizeof(ipecamera_frame_t));
423
    if (!ctx->frame) {
424
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
117 by Suren A. Chilingaryan
new event architecture, first trial
425
	pcilib_error("Unable to allocate frame-info buffer");
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
426
	return PCILIB_ERROR_MEMORY;
427
    }
428
    
429
    memset(ctx->frame, 0, ctx->buffer_size * sizeof(ipecamera_frame_t));
430
    
431
    for (i = 0; i < ctx->buffer_size; i++) {
432
	err = pthread_rwlock_init(&ctx->frame[i].mutex, NULL);
433
	if (err) break;
434
    }
435
436
    ctx->frame_mutex_destroy = i;
437
438
    if (err) {
439
        ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
440
	pcilib_error("Initialization of rwlock mutexes for frame synchronization has failed");
441
	return PCILIB_ERROR_FAILED;
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
442
    }
124 by Suren A. Chilingaryan
Image frames decoding
443
    
444
    ctx->ipedec = ufo_decoder_new(ctx->dim.height, ctx->dim.width, NULL, 0);
445
    if (!ctx->ipedec) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
446
        ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
124 by Suren A. Chilingaryan
Image frames decoding
447
	pcilib_error("Unable to initialize IPECamera decoder library");
448
	return PCILIB_ERROR_FAILED;
449
    }
93 by root
DMA support in IPE Camera
450
451
    if (!err) {
117 by Suren A. Chilingaryan
new event architecture, first trial
452
	ctx->rdma = pcilib_find_dma_by_addr(vctx->pcilib, PCILIB_DMA_FROM_DEVICE, IPECAMERA_DMA_ADDRESS);
93 by root
DMA support in IPE Camera
453
	if (ctx->rdma == PCILIB_DMA_ENGINE_INVALID) {
454
	    err = PCILIB_ERROR_NOTFOUND;
455
	    pcilib_error("The C2S channel of IPECamera DMA Engine (%u) is not found", IPECAMERA_DMA_ADDRESS);
456
	} else {
117 by Suren A. Chilingaryan
new event architecture, first trial
457
	    err = pcilib_start_dma(vctx->pcilib, ctx->rdma, PCILIB_DMA_FLAGS_DEFAULT);
93 by root
DMA support in IPE Camera
458
	    if (err) {
459
		ctx->rdma = PCILIB_DMA_ENGINE_INVALID;
460
		pcilib_error("Failed to initialize C2S channel of IPECamera DMA Engine (%u)", IPECAMERA_DMA_ADDRESS);
461
	    }
462
	}
463
    }
464
    
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
465
    if (err) {
466
        ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
467
	return err;
468
    }
469
252 by Suren A. Chilingaryan
Cleanup
470
#ifdef IPECAMERA_CLEAN_ON_START
117 by Suren A. Chilingaryan
new event architecture, first trial
471
    err = pcilib_skip_dma(vctx->pcilib, ctx->rdma);
472
    if (err) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
473
        ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
117 by Suren A. Chilingaryan
new event architecture, first trial
474
	pcilib_error("Can't start grabbing, device continuously writes unexpected data using DMA engine");
475
	return err;
476
    }
252 by Suren A. Chilingaryan
Cleanup
477
#endif /* IPECAMERA_CLEAN_ON_START */
117 by Suren A. Chilingaryan
new event architecture, first trial
478
479
    if (vctx->params.autostop.duration) {
480
	gettimeofday(&ctx->autostop.timestamp, NULL);
481
	ctx->autostop.timestamp.tv_usec += vctx->params.autostop.duration % 1000000;
482
	if (ctx->autostop.timestamp.tv_usec > 999999) {
483
	    ctx->autostop.timestamp.tv_sec += 1 + vctx->params.autostop.duration / 1000000;
484
	    ctx->autostop.timestamp.tv_usec -= 1000000;
485
	} else {
486
	    ctx->autostop.timestamp.tv_sec += vctx->params.autostop.duration / 1000000;
487
	}
488
    }
489
    
490
    if (vctx->params.autostop.max_events) {
491
	ctx->autostop.evid = vctx->params.autostop.max_events;
492
    }
15 by Suren A. Chilingaryan
Infrastructure for event API
493
    
144 by Suren A. Chilingaryan
Do not call the normall callback in the raw-data-only mode
494
    if ((ctx->parse_data)&&(flags&PCILIB_EVENT_FLAG_PREPROCESS)) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
495
	ctx->n_preproc = pcilib_get_cpu_count();
135 by Suren A. Chilingaryan
Allow to configure the number of preprocessing threads
496
	
497
	    // it would be greate to detect hyperthreading cores and ban them
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
498
	switch (ctx->n_preproc) {
499
	    case 1: break;
208 by Suren A. Chilingaryan
I have no clue how to properly write switch statements.... Fixed.
500
	    case 2 ... 3: ctx->n_preproc -= 1; break;
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
501
	    default: ctx->n_preproc -= 2; break;
502
	}
135 by Suren A. Chilingaryan
Allow to configure the number of preprocessing threads
503
504
	if ((vctx->params.parallel.max_threads)&&(vctx->params.parallel.max_threads < ctx->n_preproc))
505
	    ctx->n_preproc = vctx->params.parallel.max_threads;
506
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
507
	ctx->preproc = (ipecamera_preprocessor_t*)malloc(ctx->n_preproc * sizeof(ipecamera_preprocessor_t));
508
	if (!ctx->preproc) {
509
	    ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
510
	    pcilib_error("Unable to allocate memory for preprocessor contexts");
511
	    return PCILIB_ERROR_MEMORY;
512
	}
513
514
	memset(ctx->preproc, 0, ctx->n_preproc * sizeof(ipecamera_preprocessor_t));
515
516
	err = pthread_mutex_init(&ctx->preproc_mutex, NULL);
517
	if (err) {
518
	    ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
519
	    pcilib_error("Failed to initialize event mutex");
520
	    return PCILIB_ERROR_FAILED;
521
	}
522
	ctx->preproc_mutex_destroy = 1;
523
	
524
525
	ctx->run_preprocessors = 1;
526
	for (i = 0; i < ctx->n_preproc; i++) {
527
	    ctx->preproc[i].i = i;
528
	    ctx->preproc[i].ipecamera = ctx;
529
	    err = pthread_create(&ctx->preproc[i].thread, NULL, ipecamera_preproc_thread, ctx->preproc + i);
530
	    if (err) {
531
		err = PCILIB_ERROR_FAILED;
532
		break;
533
	    } else {
534
		ctx->preproc[i].started = 1;
535
	    }
536
	}
537
	
538
	if (err) {
539
	    ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
540
	    pcilib_error("Failed to schedule some of the preprocessor threads");
541
	    return err;
542
	}
543
    } else {
544
	ctx->n_preproc = 0;
545
    }
546
21 by Suren A. Chilingaryan
Small bug fix: forgot to set a flag indicating what we are started
547
    ctx->started = 1;
117 by Suren A. Chilingaryan
new event architecture, first trial
548
    ctx->run_reader = 1;
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
549
117 by Suren A. Chilingaryan
new event architecture, first trial
550
    pthread_attr_init(&attr);
551
552
    if (pthread_attr_setschedpolicy(&attr, SCHED_FIFO)) {
553
	pcilib_warning("Can't schedule a real-time thread, you may consider running as root");
554
    } else {
555
	sched.sched_priority = sched_get_priority_max(SCHED_FIFO) - 1;	// Let 1 priority for something really critcial
556
	pthread_attr_setschedparam(&attr, &sched);
557
    }
171 by Suren A. Chilingaryan
Fix temperature register of ipecamera and prepend all cmosis registers with _cmosis prefix
558
117 by Suren A. Chilingaryan
new event architecture, first trial
559
    if (pthread_create(&ctx->rthread, &attr, &ipecamera_reader_thread, (void*)ctx)) {
560
	ctx->started = 0;
561
	ipecamera_stop(vctx, PCILIB_EVENT_FLAGS_DEFAULT);
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
562
	err = PCILIB_ERROR_FAILED;
117 by Suren A. Chilingaryan
new event architecture, first trial
563
    }
564
    
565
    pthread_attr_destroy(&attr);    
566
262 by Suren A. Chilingaryan
Introduce API debugging
567
    ipecamera_debug(API, "ipecamera: started");
568
117 by Suren A. Chilingaryan
new event architecture, first trial
569
    return err;
15 by Suren A. Chilingaryan
Infrastructure for event API
570
}
571
572
117 by Suren A. Chilingaryan
new event architecture, first trial
573
int ipecamera_stop(pcilib_context_t *vctx, pcilib_event_flags_t flags) {
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
574
    int i;
117 by Suren A. Chilingaryan
new event architecture, first trial
575
    int err;
576
    void *retcode;
15 by Suren A. Chilingaryan
Infrastructure for event API
577
    ipecamera_t *ctx = (ipecamera_t*)vctx;
578
579
    if (!ctx) {
580
	pcilib_error("IPECamera imaging is not initialized");
581
	return PCILIB_ERROR_NOTINITIALIZED;
582
    }
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
583
119 by Suren A. Chilingaryan
Initial support of event streaming in cli
584
    if (flags&PCILIB_EVENT_FLAG_STOP_ONLY) {
585
	ctx->run_reader = 0;
586
	return 0;
587
    }
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
588
262 by Suren A. Chilingaryan
Introduce API debugging
589
    ipecamera_debug(API, "ipecamera: stopping");
590
117 by Suren A. Chilingaryan
new event architecture, first trial
591
    if (ctx->started) {
592
	ctx->run_reader = 0;
593
	err = pthread_join(ctx->rthread, &retcode);
594
	if (err) pcilib_error("Error joining the reader thread");
595
    }
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
596
    
597
    if (ctx->preproc) {
598
	ctx->run_preprocessors = 0;
599
	
600
	for (i = 0; i < ctx->n_preproc; i++) {
601
	    if (ctx->preproc[i].started) {
602
		pthread_join(ctx->preproc[i].thread, &retcode);
603
		ctx->preproc[i].started = 0;
604
	    }
605
	}
21 by Suren A. Chilingaryan
Small bug fix: forgot to set a flag indicating what we are started
606
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
607
	if (ctx->preproc_mutex_destroy) {
608
	    pthread_mutex_destroy(&ctx->preproc_mutex);
609
	    ctx->preproc_mutex_destroy = 0;
610
	}
611
	
612
	free(ctx->preproc);
613
	ctx->preproc = NULL;
614
    }
615
    
616
    if (ctx->frame_mutex_destroy) {
617
	for (i = 0; i < ctx->frame_mutex_destroy; i++) {
618
	    pthread_rwlock_destroy(&ctx->frame[i].mutex);
619
	}
620
	ctx->frame_mutex_destroy = 0;
621
    }
93 by root
DMA support in IPE Camera
622
623
    if (ctx->rdma != PCILIB_DMA_ENGINE_INVALID) {
117 by Suren A. Chilingaryan
new event architecture, first trial
624
	pcilib_stop_dma(vctx->pcilib, ctx->rdma, PCILIB_DMA_FLAGS_DEFAULT);
93 by root
DMA support in IPE Camera
625
	ctx->rdma = PCILIB_DMA_ENGINE_INVALID;
626
    }
190.1.1 by Suren A. Chilingaryan
In ipecamera_stop wait until streaming user-thread is terminated
627
628
    while (ctx->streaming) {
629
        usleep(IPECAMERA_NOFRAME_SLEEP);
630
    }
631
124 by Suren A. Chilingaryan
Image frames decoding
632
    if (ctx->ipedec) {
633
	ufo_decoder_free(ctx->ipedec);
634
	ctx->ipedec = NULL;
635
    }
93 by root
DMA support in IPE Camera
636
126 by Suren A. Chilingaryan
multithread preprocessing of ipecamera frames and code reorganization
637
    if (ctx->frame) {
638
	free(ctx->frame);
639
	ctx->frame = NULL;
117 by Suren A. Chilingaryan
new event architecture, first trial
640
    }
641
124 by Suren A. Chilingaryan
Image frames decoding
642
    if (ctx->cmask) {
643
	free(ctx->cmask);
644
	ctx->cmask = NULL;
645
    }
646
647
    if (ctx->image) {
648
	free(ctx->image);
649
	ctx->image = NULL;
650
    }
651
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
652
    if (ctx->buffer) {
653
	free(ctx->buffer);
654
	ctx->buffer = NULL;
655
    }
656
117 by Suren A. Chilingaryan
new event architecture, first trial
657
    memset(&ctx->autostop, 0, sizeof(ipecamera_autostop_t));
16 by Suren A. Chilingaryan
Prototype of IPECamera image protocol
658
659
    ctx->event_id = 0;
29 by Suren A. Chilingaryan
Support non-callback way of getting events
660
    ctx->reported_id = 0;
117 by Suren A. Chilingaryan
new event architecture, first trial
661
    ctx->buffer_pos = 0; 
662
    ctx->started = 0;
663
262 by Suren A. Chilingaryan
Introduce API debugging
664
    ipecamera_debug(API, "ipecamera: stopped");
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
665
    UNLOCK(run);
666
117 by Suren A. Chilingaryan
new event architecture, first trial
667
    return 0;
15 by Suren A. Chilingaryan
Infrastructure for event API
668
}
669
670
31 by Suren A. Chilingaryan
Introduce pcilib_context_t type instead pointer to void
671
int ipecamera_trigger(pcilib_context_t *vctx, pcilib_event_t event, size_t trigger_size, void *trigger_data) {
117 by Suren A. Chilingaryan
new event architecture, first trial
672
    int err = 0;
673
    pcilib_register_value_t value;
674
15 by Suren A. Chilingaryan
Infrastructure for event API
675
    ipecamera_t *ctx = (ipecamera_t*)vctx;
117 by Suren A. Chilingaryan
new event architecture, first trial
676
    pcilib_t *pcilib = vctx->pcilib;
15 by Suren A. Chilingaryan
Infrastructure for event API
677
245 by Suren A. Chilingaryan
First stand-alone ipecamera implementation
678
    const pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
679
15 by Suren A. Chilingaryan
Infrastructure for event API
680
    if (!ctx) {
681
	pcilib_error("IPECamera imaging is not initialized");
682
	return PCILIB_ERROR_NOTINITIALIZED;
683
    }
223 by Suren A. Chilingaryan
Merge changes from xilinx_dma branch providing support of multipage kmem allocations and mapping memory regions reserved with memmap boot option
684
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
685
    ipecamera_debug(API, "ipecamera: trigger");
686
    LOCK(trigger);
687
132 by Suren A. Chilingaryan
Minor fixes and improvements
688
    pcilib_sleep_until_deadline(&ctx->next_trigger);
239 by Suren A. Chilingaryan
ipecamera hack
689
/*
174 by Suren A. Chilingaryan
Check for free space in camera DDR buffer before triggering event
690
    GET_REG(num_frames_reg, value);
691
    if (value == ctx->max_frames) {
692
	return PCILIB_ERROR_BUSY;
693
    }
239 by Suren A. Chilingaryan
ipecamera hack
694
*/
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
695
696
    GET_REG(status2_reg, value);
697
    if (value&0x40000000) {
252 by Suren A. Chilingaryan
Cleanup
698
	if (value == 0xffffffff)
699
	    pcilib_info("Failed to read status2_reg while triggering");
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
700
252 by Suren A. Chilingaryan
Cleanup
701
#ifdef IPECAMERA_TRIGGER_TIMEOUT
702
	if (IPECAMERA_TRIGGER_TIMEOUT) {
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
703
	    struct timeval deadline;
252 by Suren A. Chilingaryan
Cleanup
704
	    pcilib_calc_deadline(&deadline, IPECAMERA_TRIGGER_TIMEOUT);
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
705
	    do {
706
		usleep(IPECAMERA_READ_STATUS_DELAY);
707
		GET_REG(status2_reg, value);
708
	    } while ((value&0x40000000)&&(pcilib_calc_time_to_deadline(&deadline) > 0));
709
	}
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
710
	if (value&0x40000000) {
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
711
#endif /* IPECAMERA_TRIGGER_WAIT_IDLE */
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
712
	    UNLOCK(trigger);
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
713
	    return PCILIB_ERROR_BUSY;
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
714
#ifdef IPECAMERA_TRIGGER_TIMEOUT
715
	}
716
#endif /* IPECAMERA_TRIGGER_WAIT_IDLE */
240 by Suren A. Chilingaryan
Fix frame size computation in ipecamera and few debuging options
717
    }
215 by Suren A. Chilingaryan
Properly support triggering with new revision of UFO camera
718
261 by Suren A. Chilingaryan
Support for new CMOSIS 20MPix camera
719
    GET_REG(control_reg, value);
215 by Suren A. Chilingaryan
Properly support triggering with new revision of UFO camera
720
    SET_REG(control_reg, value|IPECAMERA_FRAME_REQUEST);
252 by Suren A. Chilingaryan
Cleanup
721
    usleep(IPECAMERA_TRIGGER_DELAY);
215 by Suren A. Chilingaryan
Properly support triggering with new revision of UFO camera
722
    SET_REG(control_reg, value);
117 by Suren A. Chilingaryan
new event architecture, first trial
723
252 by Suren A. Chilingaryan
Cleanup
724
	// DS: We need to compute it differently, on top of that add exposure time and the time FPGA takes to read frame from CMOSIS
132 by Suren A. Chilingaryan
Minor fixes and improvements
725
    pcilib_calc_deadline(&ctx->next_trigger, IPECAMERA_NEXT_FRAME_DELAY);
265 by Suren A. Chilingaryan
Use new locking subsystem to ensure integrity
726
    
727
    UNLOCK(trigger);
117 by Suren A. Chilingaryan
new event architecture, first trial
728
119 by Suren A. Chilingaryan
Initial support of event streaming in cli
729
    return 0;
117 by Suren A. Chilingaryan
new event architecture, first trial
730
}