diff --git a/pvtoolsSrc/eget.cpp b/pvtoolsSrc/eget.cpp index a4cd903..19bc9bf 100644 --- a/pvtoolsSrc/eget.cpp +++ b/pvtoolsSrc/eget.cpp @@ -919,10 +919,10 @@ void printValue(std::string const & channelName, PVStructure::shared_pointer con } else { - // switch to structure mode, unless it's NTEnum - if (!dumpStructure && value->getField()->getID() == "enum_t") + // switch to structure mode, unless it's T-type + if (valueType == structure && isTType(static_pointer_cast(value))) { - formatNTEnum(std::cout, pv); + formatTType(std::cout, static_pointer_cast(value)); std::cout << std::endl; } else @@ -1033,6 +1033,7 @@ void usage (void) " -w : Wait time, specifies timeout, default is %f second(s)\n" " -z: Pure pvAccess RPC based service (send NTURI.query as request argument)\n" " -N: Do not format NT types, dump structure instead\n" + " -i: Do not format standard types (enum_t, time_t, ...)\n" " -t: Terse mode\n" " -T: Transpose vector, table, matrix\n" " -m: Monitor mode\n" @@ -1042,7 +1043,7 @@ void usage (void) " -d: Enable debug output\n" " -F : Use as an alternate output field separator\n" " -f : Use as an input that provides a list PV name(s) to be read, use '-' for stdin\n" - " -c: Wait for clean shutdown and report used instance count (for expert users)" + " -c: Wait for clean shutdown and report used instance count (for expert users)\n" " enum format:\n" " -n: Force enum interpretation of values as numbers (default is enum string)\n" "\n\nexamples:\n\n" @@ -1368,8 +1369,8 @@ class MonitorRequesterImpl : public MonitorRequester Type valueType = value->getField()->getType(); if (valueType != scalar && valueType != scalarArray) { - // switch to structure mode, unless it's NTEnum - if (!dumpStructure && value->getField()->getID() == "enum_t") + // switch to structure mode, unless it's T-type + if (valueType == structure && isTType(static_pointer_cast(value))) { if (fieldSeparator == ' ') std::cout << std::setw(30) << std::left << m_channelName; @@ -1377,7 +1378,7 @@ class MonitorRequesterImpl : public MonitorRequester std::cout << m_channelName; std::cout << fieldSeparator; - formatNTEnum(std::cout, element->pvStructurePtr); + formatTType(std::cout, static_pointer_cast(value)); std::cout << std::endl; } else @@ -1461,7 +1462,7 @@ int main (int argc, char *argv[]) setvbuf(stdout,NULL,_IOLBF,BUFSIZ); /* Set stdout to line buffering */ - while ((opt = getopt(argc, argv, ":hr:s:a:w:zNtTmxp:qdcF:f:n")) != -1) { + while ((opt = getopt(argc, argv, ":hr:s:a:w:zNtTmxp:qdcF:f:ni")) != -1) { switch (opt) { case 'h': /* Print usage */ usage(); @@ -1531,6 +1532,9 @@ int main (int argc, char *argv[]) case 'N': /* Do not format NT types */ dumpStructure = true; break; + case 'i': /* T-types format mode */ + formatTTypes(false); + break; case 't': /* Terse mode */ mode = TerseMode; break; diff --git a/pvtoolsSrc/pvget.cpp b/pvtoolsSrc/pvget.cpp index b75fd0e..0fa0307 100644 --- a/pvtoolsSrc/pvget.cpp +++ b/pvtoolsSrc/pvget.cpp @@ -51,6 +51,7 @@ void usage (void) " -r : Request, specifies what fields to return and options, default is '%s'\n" " -w : Wait time, specifies timeout, default is %f second(s)\n" " -t: Terse mode - print only value, without names\n" + " -i: Do not format standard types (enum_t, time_t, ...)\n" " -m: Monitor mode\n" " -q: Quiet mode, print only error messages\n" " -d: Enable debug output\n" @@ -59,6 +60,8 @@ void usage (void) " -c: Wait for clean shutdown and report used instance count (for expert users)\n" " enum format:\n" " -n: Force enum interpretation of values as numbers (default is enum string)\n" +// " time format:\n" +// " -u: print userTag\n" "\nexample: pvget double01\n\n" , DEFAULT_REQUEST, DEFAULT_TIMEOUT); } @@ -80,12 +83,12 @@ void printValue(std::string const & channelName, PVStructure::shared_pointer con Type valueType = value->getField()->getType(); if (valueType != scalar && valueType != scalarArray) { - // switch to structure mode, unless it's NTEnum - if (value->getField()->getID() == "enum_t") + // switch to structure mode, unless it's T-type + if (valueType == structure && isTType(static_pointer_cast(value))) { std::cout << std::setw(30) << std::left << channelName; std::cout << fieldSeparator; - printEnumT(std::cout, static_pointer_cast(value)); + formatTType(std::cout, static_pointer_cast(value)); std::cout << std::endl; } else @@ -284,12 +287,12 @@ class MonitorRequesterImpl : public MonitorRequester Type valueType = value->getField()->getType(); if (valueType != scalar && valueType != scalarArray) { - // switch to structure mode, unless it's NTEnum - if (value->getField()->getID() == "enum_t") + // switch to structure mode, unless it's T-type + if (valueType == structure && isTType(static_pointer_cast(value))) { std::cout << std::setw(30) << std::left << m_channelName; std::cout << fieldSeparator; - printEnumT(std::cout, static_pointer_cast(value)); + formatTType(std::cout, static_pointer_cast(value)); std::cout << std::endl; } else @@ -375,7 +378,7 @@ int main (int argc, char *argv[]) setvbuf(stdout,NULL,_IOLBF,BUFSIZ); /* Set stdout to line buffering */ - while ((opt = getopt(argc, argv, ":hr:w:tmqdcF:f:n")) != -1) { + while ((opt = getopt(argc, argv, ":hr:w:tmqdcF:f:ni")) != -1) { switch (opt) { case 'h': /* Print usage */ usage(); @@ -396,6 +399,9 @@ int main (int argc, char *argv[]) case 't': /* Terse mode */ mode = TerseMode; break; + case 'i': /* T-types format mode */ + formatTTypes(false); + break; case 'm': /* Monitor mode */ monitor = true; break; diff --git a/pvtoolsSrc/pvlist.cpp b/pvtoolsSrc/pvlist.cpp index d263a55..52ceb87 100644 --- a/pvtoolsSrc/pvlist.cpp +++ b/pvtoolsSrc/pvlist.cpp @@ -600,7 +600,7 @@ int main (int argc, char *argv[]) // TODO timeOut string cmd = "eget -"; if (debug) - cmd =+ 'd'; + cmd += 'd'; if (quiet) cmd += 'q'; if (printInfo) diff --git a/pvtoolsSrc/pvutils.cpp b/pvtoolsSrc/pvutils.cpp index aa43535..56e45ef 100644 --- a/pvtoolsSrc/pvutils.cpp +++ b/pvtoolsSrc/pvutils.cpp @@ -81,6 +81,11 @@ void formatTTypes(bool flag) formatTTypesFlag = flag; } +bool printUserTagFlag = true; +void printUserTag(bool flag) +{ + printUserTagFlag = flag; +} std::ostream& terse(std::ostream& o, PVField::shared_pointer const & pv) { @@ -146,6 +151,7 @@ std::ostream& printTimeT(std::ostream& o, epics::pvData::PVStructure::shared_poi #define TIMETEXTLEN 32 char timeText[TIMETEXTLEN]; epicsTimeStamp epicsTS; + int32 userTag; PVTimeStamp pvTimeStamp; if (pvTimeStamp.attach(pvTimeT)) @@ -153,6 +159,17 @@ std::ostream& printTimeT(std::ostream& o, epics::pvData::PVStructure::shared_poi TimeStamp ts; pvTimeStamp.get(ts); + userTag = ts.getUserTag(); + + if (ts.getSecondsPastEpoch() == 0 && + ts.getNanoseconds() == 0) + { + o << ""; + if (printUserTagFlag) + o << separator << userTag; + return o; + } + epicsTS.secPastEpoch = ts.getEpicsSecondsPastEpoch(); epicsTS.nsec = ts.getNanoseconds(); } @@ -161,10 +178,45 @@ std::ostream& printTimeT(std::ostream& o, epics::pvData::PVStructure::shared_poi epicsTimeToStrftime(timeText, TIMETEXTLEN, "%Y-%m-%dT%H:%M:%S.%03f", &epicsTS); o << timeText; + if (printUserTagFlag) + o << separator << userTag; return o; } +bool isTType(epics::pvData::PVStructure::shared_pointer const & pvStructure) +{ + // "forget" about Ttype if disabled + if (!formatTTypesFlag) + return false; + + string id = pvStructure->getStructure()->getID(); + return (id == "enum_t" || + id == "time_t"); +} + +bool formatTType(std::ostream& o, epics::pvData::PVStructure::shared_pointer const & pvStructure) +{ + // special t-types support (enum_t and time_t, etc.) + if (formatTTypesFlag) + { + string id = pvStructure->getStructure()->getID(); + if (id == "enum_t") + { + printEnumT(o, pvStructure); + return true; + } + else if (id == "time_t") + { + printTimeT(o, pvStructure); + return true; + } + } + + return false; +} + + std::ostream& terseStructure(std::ostream& o, PVStructure::shared_pointer const & pvStructure) { if (!pvStructure) @@ -174,20 +226,8 @@ std::ostream& terseStructure(std::ostream& o, PVStructure::shared_pointer const } // special t-types support (enum_t and time_t, etc.) - if (formatTTypesFlag) - { - string id = pvStructure->getStructure()->getID(); - if (id == "enum_t") - { - printEnumT(o, pvStructure); - return o; - } - else if (id == "time_t") - { - printTimeT(o, pvStructure); - return o; - } - } + if (formatTType(o, pvStructure)) + return o; PVFieldPtrArray fieldsData = pvStructure->getPVFields(); size_t length = pvStructure->getStructure()->getNumberFields(); diff --git a/pvtoolsSrc/pvutils.h b/pvtoolsSrc/pvutils.h index 184c662..ec2bfb4 100644 --- a/pvtoolsSrc/pvutils.h +++ b/pvtoolsSrc/pvutils.h @@ -20,9 +20,12 @@ enum EnumMode { AutoEnum, NumberEnum, StringEnum }; void setEnumPrintMode(EnumMode mode); void formatTTypes(bool flag); +bool isTType(epics::pvData::PVStructure::shared_pointer const & pvStructure); +bool formatTType(std::ostream& o, epics::pvData::PVStructure::shared_pointer const & pvStructure); + +void printUserTag(bool flag); std::ostream& printEnumT(std::ostream& o, epics::pvData::PVStructure const & pvEnumT); -//std::ostream& printTimeT(std::ostream& o, epics::pvData::PVStructure const & pvTimeT); std::ostream& printEnumT(std::ostream& o, epics::pvData::PVStructure::shared_pointer const & pvEnumT); std::ostream& printTimeT(std::ostream& o, epics::pvData::PVStructure::shared_pointer const & pvTimeT); @@ -173,21 +176,13 @@ template <> inline pvutil_ostream& operator<<(pvutil_ostream& o, const epics::pvData::PVStructure::shared_pointer & value) { - std::string id = value->getStructure()->getID(); - if (id == "enum_t") + if (isTType(value)) { - o << epics::pvData::format::indent() << id << ' ' << value->getFieldName() << " # "; - printEnumT(o, value); + o << epics::pvData::format::indent() << value->getStructure()->getID() + << ' ' << value->getFieldName() << ' '; //" # "; + formatTType(o, value); o << std::endl; - dumpPVStructure(o, *value, false); - return o; - } - else if (id == "time_t") - { - o << epics::pvData::format::indent() << id << ' ' << value->getFieldName() << " # "; - printTimeT(o, value); - o << std::endl; - dumpPVStructure(o, *value, false); + //dumpPVStructure(o, *value, false); return o; }