Skip to content

Commit

Permalink
Try to automatically reconnect when the camera connection is lost
Browse files Browse the repository at this point in the history
There is a parameter to disable this behaviour if needed
  • Loading branch information
EmilioPeJu committed Feb 1, 2024
1 parent 53bbf86 commit 64404e6
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 4 deletions.
21 changes: 21 additions & 0 deletions aravisApp/Db/aravisCamera.template
Original file line number Diff line number Diff line change
Expand Up @@ -205,3 +205,24 @@ record(mbbo, "$(P)$(R)ARShiftBits") {
field(PINI, "1")
info(autosaveFields, "DESC ZRSV ONSV VAL")
}

record(mbbo, "$(P)$(R)AutoConnect") {
field(DTYP, "asynInt32")
field(OUT, "@asyn($(PORT),$(ADDR=0),$(TIMEOUT=1))ARAVIS_AUTO_CONNECT")
field(ZRST, "Off")
field(ZRVL, "0")
field(ONST, "On")
field(ONVL, "1")
field(PINI, "1")
info(autosaveFields, "VAL")
}

record(mbbi, "$(P)$(R)AutoConnect_RBV") {
field(DTYP, "asynInt32")
field(INP, "@asyn($(PORT),$(ADDR=0),$(TIMEOUT=1))ARAVIS_AUTO_CONNECT")
field(ZRST, "Off")
field(ZRVL, "0")
field(ONST, "On")
field(ONVL, "1")
field(SCAN, "I/O Intr")
}
30 changes: 26 additions & 4 deletions aravisApp/src/ADAravis.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -185,7 +185,8 @@ class ADAravis : public ADGenICam, epicsThreadRunable {
int AravisShiftBits;
int AravisConnection;
int AravisReset;
#define LAST_ARAVIS_CAMERA_PARAM AravisReset
int AravisAutoConnect;
#define LAST_ARAVIS_CAMERA_PARAM AravisAutoConnect

private:
asynStatus allocBuffer();
Expand All @@ -195,6 +196,7 @@ class ADAravis : public ADGenICam, epicsThreadRunable {
asynStatus connectToCamera();
asynStatus makeCameraObject();
asynStatus makeStreamObject();
void reconnectIfNeeded();

ArvStream *stream;
ArvDevice *device;
Expand Down Expand Up @@ -356,6 +358,7 @@ ADAravis::ADAravis(const char *portName, const char *cameraName, int enableCachi
createParam("ARAVIS_SHIFT_BITS", asynParamInt32, &AravisShiftBits);
createParam("ARAVIS_CONNECTION", asynParamInt32, &AravisConnection);
createParam("ARAVIS_RESET", asynParamInt32, &AravisReset);
createParam("ARAVIS_AUTO_CONNECT", asynParamInt32, &AravisAutoConnect);

/* Set some initial values for other parameters */
setStringParam(NDDriverVersion, DRIVER_VERSION);
Expand All @@ -377,7 +380,8 @@ ADAravis::ADAravis(const char *portName, const char *cameraName, int enableCachi
setIntegerParam(AravisShiftDir, 0);
setIntegerParam(AravisShiftBits, 4);
setIntegerParam(AravisReset, 0);

setIntegerParam(AravisAutoConnect, true);

/* Enable the fake camera for simulations */
arv_enable_interface ("Fake");

Expand Down Expand Up @@ -587,8 +591,11 @@ asynStatus ADAravis::writeInt32(asynUser *pasynUser, epicsInt32 value)
status = asynError;
} else if (function == AravisConnection) {
if (this->connectionValid != 1) status = asynError;
} else if (function == AravisFrameRetention || function == AravisPktResend || function == AravisPktTimeout ||
function == AravisShiftDir || function == AravisShiftBits || function == AravisConvertPixelFormat) {
} else if (function == AravisFrameRetention ||
function == AravisPktResend || function == AravisPktTimeout ||
function == AravisShiftDir || function == AravisShiftBits ||
function == AravisConvertPixelFormat ||
function == AravisAutoConnect) {
/* just write the value for these as they get fetched via getIntegerParam when needed */
status = setIntegerParam(function, value);
} else if ((function < FIRST_ARAVIS_CAMERA_PARAM) || (function > LAST_ARAVIS_CAMERA_PARAM)) {
Expand Down Expand Up @@ -670,6 +677,20 @@ asynStatus ADAravis::allocBuffer() {
return asynSuccess;
}

void ADAravis::reconnectIfNeeded() {
int autoConnect;
if (this->connectionValid == 0) {
this->lock();
getIntegerParam(AravisAutoConnect, &autoConnect);
if (autoConnect) {
if(this->connectToCamera() == asynSuccess) {
readStatus();
}
}
this->unlock();
}
}

/** Check what event we have, and deal with new frames.
this->camera exists, lock not taken */
void ADAravis::run() {
Expand All @@ -688,6 +709,7 @@ void ADAravis::run() {
while (1) {
/* Wait 5ms for an array to arrive from the queue */
if (epicsMessageQueueReceiveWithTimeout(this->msgQId, &buffer, sizeof(&buffer), 0.005) == -1) {
reconnectIfNeeded();
} else {
/* Got a buffer, so lock up and process it */
this->lock();
Expand Down

0 comments on commit 64404e6

Please sign in to comment.