pvalink local:

This commit is contained in:
Michael Davidsaver
2018-04-20 15:41:42 -07:00
parent e70aa0897d
commit 3a5ac39627
4 changed files with 45 additions and 17 deletions

View File

@ -78,7 +78,7 @@ struct pvaLinkConfig : public jlink
MSI,
} ms;
bool defer, pipeline, time, retry;
bool defer, pipeline, time, retry, local;
int monorder;
// internals used by jlif parsing
@ -127,6 +127,7 @@ struct pvaLinkChannel : public pvac::ClientChannel::MonitorCallback,
pvac::Monitor op_mon;
pvac::Operation op_put;
std::string providerName;
size_t num_disconnect, num_type_change;
bool connected;
bool connected_latched; // connection status at the run()

View File

@ -71,12 +71,14 @@ void pvaLinkChannel::open()
try {
chan = pvaGlobal->provider_local.connect(key.first);
TRACE(<<"Local "<<key.first);
providerName = pvaGlobal->provider_local.name();
} catch(std::exception& e){
errlogPrintf("failed to find in QSRV; %s\n", key.first.c_str());
}
if(!pvaLinkIsolate && !chan) {
chan = pvaGlobal->provider_remote.connect(key.first);
TRACE(<<"Remote "<<key.first);
providerName = pvaGlobal->provider_remote.name();
}
op_mon = chan.monitor(this, pvRequest);

View File

@ -16,6 +16,7 @@ pvaLinkConfig::pvaLinkConfig()
,pipeline(false)
,time(false)
,retry(false)
,local(false)
,monorder(0)
{}
pvaLinkConfig::~pvaLinkConfig() {}
@ -40,6 +41,7 @@ using namespace pvalink;
* "monorder":#,// order of processing during CP scan
* "defer":true,// whether to immediately start Put, or only queue value to be sent
* "retry":true,// queue Put while disconnected, and retry on connect
* "local":false,// Require local channel
* }
*/
@ -80,6 +82,8 @@ jlif_result pva_parse_null(jlink *pjlink)
pvt->pp = pvaLinkConfig::Default;
} else if(pvt->jkey == "sevr") {
pvt->ms = pvaLinkConfig::NMS;
} else if(pvt->jkey == "local") {
pvt->local = false; // alias for local:false
} else if(pvt->debug) {
printf("pva link parsing unknown none depth=%u key=\"%s\"\n",
pvt->parseDepth, pvt->jkey.c_str());
@ -108,6 +112,8 @@ jlif_result pva_parse_bool(jlink *pjlink, int val)
pvt->time = !!val;
} else if(pvt->jkey == "retry") {
pvt->retry = !!val;
} else if(pvt->jkey == "local") {
pvt->local = !!val;
} else if(pvt->debug) {
printf("pva link parsing unknown integer depth=%u key=\"%s\" value=%s\n",
pvt->parseDepth, pvt->jkey.c_str(), val ? "true" : "false");
@ -236,29 +242,40 @@ void pva_report(const jlink *rpjlink, int lvl, int indent)
printf("%*s'pva': %s", indent, "", pval->channelName.c_str());
if(!pval->fieldName.empty())
printf("|.%s", pval->fieldName.c_str());
switch(pval->pp) {
case pvaLinkConfig::NPP: printf(" NPP"); break;
case pvaLinkConfig::Default: printf(" Def"); break;
case pvaLinkConfig::PP: printf(" PP"); break;
case pvaLinkConfig::CP: printf(" CP"); break;
case pvaLinkConfig::CPP: printf(" CPP"); break;
}
switch(pval->ms) {
case pvaLinkConfig::NMS: printf(" NMS"); break;
case pvaLinkConfig::MS: printf(" MS"); break;
case pvaLinkConfig::MSI: printf(" MSI"); break;
}
if(lvl>0) {
printf(" Q=%u pipe=%c defer=%c time=%c retry=%c morder=%d",
unsigned(pval->queueSize),
pval->pipeline ? 'T' : 'F',
pval->defer ? 'T' : 'F',
pval->time ? 'T' : 'F',
pval->retry ? 'T' : 'F',
pval->monorder);
}
if(pval->lchan) {
// after open()
Guard G(pval->lchan->lock);
printf(" %sconnected", pval->lchan->connected ? "" : "dis");
printf(" conn=%c", pval->lchan->connected ? 'T' : 'F');
if(lvl>0) {
printf(" #disconn=%zu", pval->lchan->num_disconnect);
switch(pval->pp) {
case pvaLinkConfig::NPP: printf(" NPP"); break;
case pvaLinkConfig::Default: printf(" Def"); break;
case pvaLinkConfig::PP: printf(" PP"); break;
case pvaLinkConfig::CP: printf(" CP"); break;
case pvaLinkConfig::CPP: printf(" CPP"); break;
}
switch(pval->ms) {
case pvaLinkConfig::NMS: printf(" NMS"); break;
case pvaLinkConfig::MS: printf(" MS"); break;
case pvaLinkConfig::MSI: printf(" MSI"); break;
}
printf(" #disconn=%zu prov=%s", pval->lchan->num_disconnect, pval->lchan->providerName.c_str());
}
if(lvl>1) {
printf(" Q=%c",
printf(" inprog=%c",
pval->lchan->queued?'T':'F');
}
if(lvl>5) {
@ -266,6 +283,8 @@ void pva_report(const jlink *rpjlink, int lvl, int indent)
pval->lchan->chan.show(strm);
printf("\n%*s CH: %s", indent, "", strm.str().c_str());
}
} else {
printf(" No Channel");
}
printf("\n");
}CATCH()

View File

@ -2,6 +2,7 @@
#include <epicsString.h>
#include <alarm.h>
#include <recGbl.h>
#include <epicsStdio.h> // redirect stdout/stderr
#define epicsExportSharedSymbols
#include <shareLib.h>
@ -68,13 +69,18 @@ void pvaOpenLink(DBLINK *plink)
chan->open(); // start subscription
}
{
if(!self->local || chan->providerName=="QSRV"){
Guard G(chan->lock);
chan->links.insert(self);
chan->links_changed = true;
self->lchan.swap(chan); // we are now attached
} else {
// TODO: only print duing iocInit()?
fprintf(stderr, "%s local:true link to '%s' can't be fulfilled\n",
plink->precord->name, self->channelName.c_str());
plink->lset = NULL;
}
return;