LCOV - code coverage report
Current view: top level - INDI/libcommon - IndiProperty.cpp (source / functions) Coverage Total Hit
Test: MagAOX Lines: 23.7 % 624 148
Test Date: 2026-01-03 21:03:39 Functions: 38.1 % 84 32

            Line data    Source code
       1              : /// IndiProperty.cpp
       2              : ///
       3              : /// @author Paul Grenz
       4              : ///
       5              : ////////////////////////////////////////////////////////////////////////////////
       6              : 
       7              : #include <algorithm>
       8              : #include <functional>
       9              : #include <stdexcept>
      10              : #include <string>
      11              : #include "IndiProperty.hpp"
      12              : 
      13              : using std::runtime_error;
      14              : using std::string;
      15              : using std::stringstream;
      16              : using std::map;
      17              : using pcf::TimeStamp;
      18              : using pcf::IndiElement;
      19              : using pcf::IndiProperty;
      20              : 
      21              : ////////////////////////////////////////////////////////////////////////////////
      22              : /// Constructor.
      23              : 
      24         7355 : IndiProperty::IndiProperty()
      25              : {
      26              :   //m_tPerm = UnknownPropertyPerm;
      27              :   //m_oRequested = false;
      28              :   //m_tRule = UnknownSwitchRule;
      29              :   //m_tState = UnknownPropertyState;
      30              :   //m_xTimeout = 0.0f;
      31              :   //m_beValue = UnknownBLOBEnable;
      32         7355 : }
      33              : 
      34              : ////////////////////////////////////////////////////////////////////////////////
      35              : /// Constructor with type - this will be used often.
      36              : 
      37          151 : IndiProperty::IndiProperty( const Type &tType ) : m_tType(tType)
      38              : {
      39          151 : }
      40              : 
      41              : ////////////////////////////////////////////////////////////////////////////////
      42              : /// Constructor with type, device and name - this will be used often.
      43              : 
      44           12 : IndiProperty::IndiProperty( const Type &tType,
      45              :                             const string &szDevice,
      46           12 :                             const string &szName ) :  m_szDevice(szDevice), m_szName(szName), m_tType(tType)
      47              : {
      48           12 : }
      49              : 
      50              : ////////////////////////////////////////////////////////////////////////////////
      51              : /// Constructor with type, device, name, state, and perm.
      52              : 
      53            0 : IndiProperty::IndiProperty( const Type &tType,
      54              :                             const string &szDevice,
      55              :                             const string &szName,
      56              :                             const PropertyStateType &tState,
      57              :                             const PropertyPermType &tPerm,
      58            0 :                             const SwitchRuleType &tRule ) : m_szDevice(szDevice), m_szName(szName), m_tPerm(tPerm),
      59            0 :                                                                m_tRule(tRule), m_tState(tState), m_tType(tType)
      60              : {
      61            0 : }
      62              : 
      63              : ////////////////////////////////////////////////////////////////////////////////
      64              : ///  Copy constructor.
      65              : 
      66           93 : IndiProperty::IndiProperty(const IndiProperty &ipRhs ) : m_szDevice(ipRhs.m_szDevice), m_szGroup(ipRhs.m_szGroup), m_szLabel(ipRhs.m_szLabel),
      67           93 :                                                            m_szMessage(ipRhs.m_szMessage), m_szName(ipRhs.m_szName), m_tPerm(ipRhs.m_tPerm),
      68           93 :                                                             m_tRule(ipRhs.m_tRule), m_tState(ipRhs.m_tState), m_xTimeout(ipRhs.m_xTimeout),
      69           93 :                                                               m_oRequested(ipRhs.m_oRequested),  m_tsTimeStamp(ipRhs.m_tsTimeStamp),
      70           93 :                                                                 m_szVersion(ipRhs.m_szVersion), m_beValue(ipRhs.m_beValue),
      71          186 :                                                                  m_mapElements(ipRhs.m_mapElements), m_tType(ipRhs.m_tType)
      72              : {
      73           93 : }
      74              : 
      75              : ////////////////////////////////////////////////////////////////////////////////
      76              : /// Destructor.
      77              : 
      78         7617 : IndiProperty::~IndiProperty()
      79              : {
      80         7617 : }
      81              : 
      82              : ////////////////////////////////////////////////////////////////////////////////
      83              : /// Assigns the internal data of this object from an existing one.
      84              : 
      85           85 : const IndiProperty &IndiProperty::operator=( const IndiProperty &ipRhs )
      86              : {
      87           85 :   if ( &ipRhs != this )
      88              :   {
      89           85 :     pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
      90              : 
      91           85 :     m_szDevice = ipRhs.m_szDevice;
      92           85 :     m_szGroup = ipRhs.m_szGroup;
      93           85 :     m_szLabel = ipRhs.m_szLabel;
      94           85 :     m_szMessage = ipRhs.m_szMessage;
      95           85 :     m_szName = ipRhs.m_szName;
      96           85 :     m_tPerm = ipRhs.m_tPerm;
      97           85 :     m_oRequested = ipRhs.m_oRequested;
      98           85 :     m_tRule = ipRhs.m_tRule;
      99           85 :     m_tState = ipRhs.m_tState;
     100           85 :     m_xTimeout = ipRhs.m_xTimeout;
     101           85 :     m_tsTimeStamp = ipRhs.m_tsTimeStamp;
     102           85 :     m_szVersion = ipRhs.m_szVersion;
     103           85 :     m_beValue = ipRhs.m_beValue;
     104              : 
     105           85 :     m_mapElements = ipRhs.m_mapElements;
     106           85 :     m_tType = ipRhs.m_tType;
     107           85 :   }
     108           85 :   return *this;
     109              : }
     110              : 
     111              : ////////////////////////////////////////////////////////////////////////////////
     112              : /// This is an alternate way of calling 'setBLOBEnable'.
     113              : 
     114            0 : const IndiProperty::BLOBEnableType &IndiProperty::operator=( const BLOBEnableType &tValue )
     115              : {
     116            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     117            0 :   m_beValue = tValue;
     118            0 :   return tValue;
     119            0 : }
     120              : 
     121              : ////////////////////////////////////////////////////////////////////////////////
     122              : /// Returns true if we have an exact match (value as well).
     123              : 
     124            0 : bool IndiProperty::operator==( const IndiProperty &ipRhs ) const
     125              : {
     126            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     127              : 
     128              :   // If we are comparing ourself to ourself - easy!
     129            0 :   if ( &ipRhs == this )
     130            0 :     return true;
     131              : 
     132              :   // If they are different sizes, they are different.
     133            0 :   if ( ipRhs.m_mapElements.size() != m_mapElements.size() )
     134            0 :     return false;
     135              : 
     136              :   // We need some iterators for each of the maps.
     137            0 :   map<string, IndiElement>::const_iterator itrRhs = ipRhs.m_mapElements.end();
     138            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     139            0 :   for ( ; itr != m_mapElements.end(); ++itr )
     140              :   {
     141              :     // Can we find an element of the same name in the other map?
     142            0 :     itrRhs = ipRhs.m_mapElements.find( itr->first );
     143              : 
     144              :     // If we can't find the name, these are different.
     145            0 :     if ( itrRhs == ipRhs.m_mapElements.end() )
     146            0 :       return false;
     147              : 
     148              :     // If we found it, and they don't match, these are different.
     149            0 :     if ( !(itrRhs->second == itr->second ) )
     150            0 :       return false;
     151              :   }
     152              : 
     153              :   // Otherwise the maps are identical and it comes down to the
     154              :   // attributes here matching.
     155            0 :   return ( m_szDevice == ipRhs.m_szDevice &&
     156            0 :     m_szGroup == ipRhs.m_szGroup &&
     157            0 :     m_szLabel == ipRhs.m_szLabel &&
     158            0 :     m_szMessage == ipRhs.m_szMessage &&
     159            0 :     m_szName == ipRhs.m_szName &&
     160            0 :     m_tPerm == ipRhs.m_tPerm &&
     161              :     //m_oRequested == ipRhs.m_oRequested &&
     162            0 :     m_tRule == ipRhs.m_tRule &&
     163            0 :     m_tState == ipRhs.m_tState &&
     164              :     //m_xTimeout == ipRhs.m_xTimeout &&
     165              :     //m_tsTimeStamp ==ipRhs.m_tsTimeStamp &&  // Don't compare!
     166            0 :     m_szVersion == ipRhs.m_szVersion &&
     167            0 :     m_beValue == ipRhs.m_beValue &&
     168            0 :     m_tType == ipRhs.m_tType );
     169            0 : }
     170              : 
     171              : ////////////////////////////////////////////////////////////////////////////////
     172              : /// Ensures that a name conforms to the INDI standard and can be used as
     173              : /// an identifier. This means:
     174              : ///     1) No ' ' - these will be converted to '_'.
     175              : ///     2) No '.' - these will be converted to '___'.
     176              : ///     3) No Unprintable chars - these will be converted to '_'.
     177              : 
     178            0 : string IndiProperty::scrubName( const string &szName )
     179              : {
     180            0 :   string szScrubbed( szName );
     181              : 
     182              :   // We are replacing one char with multiple chars, so we have to do it
     183              :   // the long way first.
     184            0 :   size_t pp = 0;
     185            0 :   size_t rr = 0;
     186            0 :   while ( ( rr = szScrubbed.find( '.', pp ) ) != string::npos )
     187              :   {
     188            0 :     szScrubbed.replace( rr, 1, "___" );
     189            0 :     pp = rr + 1;
     190              :   }
     191              : 
     192              :   // These are one-for-one replacements, so we can do them in-place.
     193            0 :   std::replace_if( szScrubbed.begin(), szScrubbed.end(),
     194            0 :                    std::not1( std::ptr_fun( ::isalnum ) ), '_' );
     195              : 
     196            0 :   return szScrubbed;
     197            0 : }
     198              : 
     199              : ////////////////////////////////////////////////////////////////////////////////
     200              : /// Compares one property with another instance. The values may not match,
     201              : /// but the type must match, as must the device and name. The names of all the
     202              : /// elements must match as well.
     203              : 
     204            0 : bool IndiProperty::compareProperty( const IndiProperty &ipComp ) const
     205              : {
     206            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     207              : 
     208              :   // If we are comparing ourself to ourself - easy!
     209            0 :   if ( &ipComp == this )
     210            0 :     return true;
     211              : 
     212            0 :   if ( ipComp.getType() != m_tType )
     213            0 :     return false;
     214              : 
     215            0 :   if ( ipComp.getDevice() != m_szDevice || ipComp.getName() != m_szName )
     216            0 :     return false;
     217              : 
     218              :   // If they are different sizes, they are different.
     219            0 :   if ( ipComp.m_mapElements.size() != m_mapElements.size() )
     220            0 :     return false;
     221              : 
     222              :   // We need some iterators for each of the maps.
     223            0 :   map<string, IndiElement>::const_iterator itrComp = ipComp.m_mapElements.end();
     224            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     225            0 :   for ( ; itr != m_mapElements.end(); ++itr )
     226              :   {
     227              :     // Can we find an element of the same name in the other map?
     228            0 :     itrComp = ipComp.m_mapElements.find( itr->first );
     229              : 
     230              :     // If we can't find the name, these are different.
     231            0 :     if ( itrComp == ipComp.m_mapElements.end() )
     232            0 :       return false;
     233              :   }
     234              : 
     235              :   // If we got here, we are identical.
     236            0 :   return true;
     237            0 : }
     238              : 
     239              : ////////////////////////////////////////////////////////////////////////////////
     240              : /// Compares one element value contained in this class with another
     241              : /// instance. The type must match, as must the device and name.
     242              : /// The name of this element must match as well.
     243              : 
     244            0 : bool IndiProperty::compareValue( const IndiProperty &ipComp,
     245              :                                  const std::string &szElementName ) const
     246              : {
     247            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     248              : 
     249              :   // If we are comparing ourself to ourself - easy!
     250            0 :   if ( &ipComp == this )
     251            0 :     return true;
     252              : 
     253            0 :   if ( ipComp.getType() != m_tType )
     254            0 :     return false;
     255              : 
     256            0 :   if ( ipComp.getDevice() != m_szDevice || ipComp.getName() != m_szName )
     257            0 :     return false;
     258              : 
     259              :   // Can we find this element in this map? If not, we fail.
     260              :   map<string, IndiElement>::const_iterator itr =
     261            0 :       m_mapElements.find( szElementName );
     262            0 :   if ( itr == m_mapElements.end() )
     263            0 :     return false;
     264              : 
     265              :   // Can we find this element in the other map? If not, we fail.
     266              :   map<string, IndiElement>::const_iterator itrComp =
     267            0 :       ipComp.m_mapElements.find( szElementName );
     268            0 :   if ( itrComp == ipComp.m_mapElements.end() )
     269            0 :     return false;
     270              : 
     271              :   // If we found it, and the values don't match, these are different.
     272            0 :   if ( itr->second.getValue() != itrComp->second.getValue() )
     273            0 :     return false;
     274              : 
     275              :   // If we got here, we are identical.
     276            0 :   return true;
     277            0 : }
     278              : 
     279              : ////////////////////////////////////////////////////////////////////////////////
     280              : /// Compares all the element values contained in this class with another
     281              : /// instance. The type must match, as must the device and name. The number
     282              : /// and names of all the elements must match as well.
     283              : 
     284            0 : bool IndiProperty::compareValues( const IndiProperty &ipComp ) const
     285              : {
     286            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     287              : 
     288              :   // If we are comparing ourself to ourself - easy!
     289            0 :   if ( &ipComp == this )
     290            0 :     return true;
     291              : 
     292            0 :   if ( ipComp.getType() != m_tType )
     293            0 :     return false;
     294              : 
     295            0 :   if ( ipComp.getDevice() != m_szDevice || ipComp.getName() != m_szName )
     296            0 :     return false;
     297              : 
     298              :   // If they are different sizes, they are different.
     299            0 :   if ( ipComp.m_mapElements.size() != m_mapElements.size() )
     300            0 :     return false;
     301              : 
     302              :   // We need some iterators for each of the maps.
     303            0 :   map<string, IndiElement>::const_iterator itrComp = ipComp.m_mapElements.end();
     304            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     305            0 :   for ( ; itr != m_mapElements.end(); ++itr )
     306              :   {
     307              :     // Can we find an element of the same name in the other map?
     308            0 :     itrComp = ipComp.m_mapElements.find( itr->first );
     309              : 
     310              :     // If we can't find the name, these are different.
     311            0 :     if ( itrComp == ipComp.m_mapElements.end() )
     312            0 :       return false;
     313              : 
     314              :     // If we found it, and the values don't match, these are different.
     315            0 :     if ( itrComp->second.getValue() != itr->second.getValue() )
     316            0 :       return false;
     317              :   }
     318              : 
     319              :   // If we got here, we are identical.
     320            0 :   return true;
     321            0 : }
     322              : 
     323              : ////////////////////////////////////////////////////////////////////////////////
     324              : /// Compares one element value contained in this class with another
     325              : /// instance. The type must match, as must the device and name.
     326              : /// The name of this element must match as well, and the value must be a new,
     327              : /// non-blank value.
     328              : 
     329            0 : bool IndiProperty::hasNewValue( const IndiProperty &ipComp,
     330              :                                 const std::string &szElementName ) const
     331              : {
     332            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     333              : 
     334              :   // If we are comparing ourself to ourself - easy - there is no new value,
     335              :   // so we must return false.
     336            0 :   if ( &ipComp == this )
     337            0 :     return false;
     338              : 
     339              :   // The types don't match, so we can't be compared.
     340            0 :   if ( ipComp.getType() != m_tType )
     341            0 :     return false;
     342              : 
     343            0 :   if ( ipComp.getDevice() != m_szDevice || ipComp.getName() != m_szName )
     344            0 :     return false;
     345              : 
     346              :   // Can we find this element in this map? If not, we fail.
     347              :   map<string, IndiElement>::const_iterator itr =
     348            0 :       m_mapElements.find( szElementName );
     349            0 :   if ( itr == m_mapElements.end() )
     350            0 :     return false;
     351              : 
     352              :   // Can we find this element in the other map? If not, we fail.
     353              :   map<string, IndiElement>::const_iterator itrComp =
     354            0 :       ipComp.m_mapElements.find( szElementName );
     355            0 :   if ( itrComp == ipComp.m_mapElements.end() )
     356            0 :     return false;
     357              : 
     358              :   // If we found it, and the values don't match and the 'comp' is not
     359              :   // empty, the 'comp' is an update.
     360            0 :   if ( itr->second.getValue() != itrComp->second.getValue() &&
     361            0 :       itrComp->second.getValue().length() > 0 )
     362            0 :     return true;
     363              : 
     364              :   // If we got here, we are identical or the 'comp' is empty.
     365            0 :   return false;
     366            0 : }
     367              : 
     368              : ////////////////////////////////////////////////////////////////////////////////
     369              : /// Returns a string with each attribute enumerated.
     370              : 
     371            0 : string IndiProperty::createString() const
     372              : {
     373            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     374              : 
     375            0 :   stringstream ssOutput;
     376              :   ssOutput << "{ "
     377            0 :            << "\"device\" : \"" << m_szDevice << "\" , "
     378            0 :            << "\"name\" : \"" << m_szName << "\" , "
     379            0 :            << "\"type\" : \"" << convertTypeToString( m_tType ) << "\" , "
     380            0 :            << "\"group\" : \"" << m_szGroup << "\" , "
     381            0 :            << "\"label\" : \"" << m_szLabel << "\" , "
     382            0 :            << "\"timeout\" : \"" << m_xTimeout << "\" , "
     383            0 :            << "\"version\" : \"" << m_szVersion << "\" , "
     384            0 :            << "\"timestamp\" : \"" << m_tsTimeStamp.getFormattedIso8601Str() << "\" , "
     385            0 :            << "\"perm\" : \"" << getPropertyPermString( m_tPerm ) << "\" , "
     386            0 :            << "\"rule\" : \"" << getSwitchRuleString( m_tRule ) << "\" , "
     387            0 :            << "\"state\" : \"" << getPropertyStateString( m_tState ) << "\" , "
     388            0 :            << "\"BLOBenable\" : \"" << getBLOBEnableString( m_beValue ) << "\" , "
     389            0 :            << "\"message\" : \"" << m_szMessage << "\" "
     390            0 :            << "\"elements\" : [ \n";
     391              : 
     392            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     393            0 :   for ( ; itr != m_mapElements.end(); ++itr )
     394              :   {
     395            0 :     ssOutput << "    ";
     396            0 :     if ( itr != m_mapElements.begin() )
     397            0 :       ssOutput << " , ";
     398            0 :     ssOutput << itr->second.createString();
     399              :   }
     400              : 
     401              :   ssOutput << "\n] "
     402            0 :            << " } ";
     403              : 
     404            0 :   return ssOutput.str();
     405            0 : }
     406              : 
     407              : ////////////////////////////////////////////////////////////////////////////////
     408              : /// Create a name for this property based on the device name and the
     409              : /// property name. A '.' is used as the chracter to join them together.
     410              : /// This key should be unique for all indi devices.
     411              : 
     412          741 : string IndiProperty::createUniqueKey() const
     413              : {
     414          741 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     415         2223 :   return m_szDevice + "." + m_szName;
     416          741 : }
     417              : 
     418              : ////////////////////////////////////////////////////////////////////////////////
     419              : 
     420            0 : bool IndiProperty::hasValidBLOBEnable() const
     421              : {
     422            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     423            0 :   return ( m_beValue != UnknownBLOBEnable );
     424            0 : }
     425              : 
     426              : ////////////////////////////////////////////////////////////////////////////////
     427              : /// Returns true if this contains a non-empty'device' attribute.
     428              : 
     429           10 : bool IndiProperty::hasValidDevice() const
     430              : {
     431           10 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     432           20 :   return ( m_szDevice.size() != 0 );
     433           10 : }
     434              : 
     435              : ////////////////////////////////////////////////////////////////////////////////
     436              : /// Returns true if this contains a non-empty 'group' attribute.
     437              : 
     438            0 : bool IndiProperty::hasValidGroup() const
     439              : {
     440            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     441            0 :   return ( m_szGroup.size() != 0 );
     442            0 : }
     443              : 
     444              : ////////////////////////////////////////////////////////////////////////////////
     445              : /// Returns true if this contains a non-empty 'label' attribute.
     446              : 
     447            0 : bool IndiProperty::hasValidLabel() const
     448              : {
     449            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     450            0 :   return ( m_szLabel.size() != 0 );
     451            0 : }
     452              : 
     453              : ////////////////////////////////////////////////////////////////////////////////
     454              : /// Returns true if this contains a non-empty 'message' attribute.
     455              : 
     456            0 : bool IndiProperty::hasValidMessage() const
     457              : {
     458            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     459            0 :   return ( m_szMessage.size() != 0 );
     460            0 : }
     461              : 
     462              : ////////////////////////////////////////////////////////////////////////////////
     463              : /// Returns true if this contains a non-empty 'name' attribute.
     464              : 
     465           10 : bool IndiProperty::hasValidName() const
     466              : {
     467           10 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     468           20 :   return ( m_szName.size() != 0 );
     469           10 : }
     470              : 
     471              : ////////////////////////////////////////////////////////////////////////////////
     472              : /// Returns true if this contains a non-empty 'perm' attribute.
     473              : 
     474            0 : bool IndiProperty::hasValidPerm() const
     475              : {
     476            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     477            0 :   return ( m_tPerm != UnknownPropertyPerm );
     478            0 : }
     479              : 
     480              : ////////////////////////////////////////////////////////////////////////////////
     481              : /// Returns true if this contains a non-empty 'rule' attribute.
     482              : 
     483            0 : bool IndiProperty::hasValidRule() const
     484              : {
     485            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     486            0 :   return ( m_tRule != UnknownSwitchRule );
     487            0 : }
     488              : 
     489              : ////////////////////////////////////////////////////////////////////////////////
     490              : /// Returns true if this contains a non-empty 'state' attribute.
     491              : 
     492            0 : bool IndiProperty::hasValidState() const
     493              : {
     494            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     495            0 :   return ( m_tState != UnknownPropertyState );
     496            0 : }
     497              : 
     498              : ////////////////////////////////////////////////////////////////////////////////
     499              : /// Returns true if this contains a non-empty 'timeout' attribute.
     500              : 
     501            0 : bool IndiProperty::hasValidTimeout() const
     502              : {
     503            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     504            0 :   return ( m_xTimeout != 0.0f );
     505            0 : }
     506              : 
     507              : ////////////////////////////////////////////////////////////////////////////////
     508              : /// Returns true if this contains a non-empty 'timestamp' attribute.
     509              : 
     510            0 : bool IndiProperty::hasValidTimeStamp() const
     511              : {
     512              :   // todo: Timestamp is always valid.... this is a weak point.
     513            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     514            0 :   return true;
     515            0 : }
     516              : 
     517              : ////////////////////////////////////////////////////////////////////////////////
     518              : /// Returns true if this contains a non-empty 'version' attribute.
     519              : 
     520            0 : bool IndiProperty::hasValidVersion() const
     521              : {
     522            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     523            0 :   return ( m_szVersion.size() != 0 );
     524            0 : }
     525              : 
     526              : ////////////////////////////////////////////////////////////////////////////////
     527              : /// Returns the name of the device.
     528              : 
     529           27 : const string &IndiProperty::getDevice() const
     530              : {
     531           27 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     532           27 :   return m_szDevice;
     533           27 : }
     534              : 
     535              : ////////////////////////////////////////////////////////////////////////////////
     536              : /// Returns the BLOB enabled state.
     537              : 
     538            0 : const IndiProperty::BLOBEnableType &IndiProperty::getBLOBEnable() const
     539              : {
     540            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     541            0 :   return m_beValue;
     542            0 : }
     543              : 
     544              : ////////////////////////////////////////////////////////////////////////////////
     545              : /// Returns the value of the group attribute.
     546              : 
     547            8 : const string &IndiProperty::getGroup() const
     548              : {
     549            8 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     550            8 :   return m_szGroup;
     551            8 : }
     552              : 
     553              : ////////////////////////////////////////////////////////////////////////////////
     554              : /// Returns the value of the label attribute.
     555              : 
     556            8 : const string &IndiProperty::getLabel() const
     557              : {
     558            8 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     559            8 :   return m_szLabel;
     560            8 : }
     561              : 
     562              : ////////////////////////////////////////////////////////////////////////////////
     563              : /// Returns the value of the message attribute.
     564              : 
     565            0 : const string &IndiProperty::getMessage() const
     566              : {
     567            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     568            0 :   return m_szMessage;
     569            0 : }
     570              : 
     571              : ////////////////////////////////////////////////////////////////////////////////
     572              : /// Returns the value of the name attribute.
     573              : 
     574           30 : const string &IndiProperty::getName() const
     575              : {
     576           30 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     577           30 :   return m_szName;
     578           30 : }
     579              : 
     580              : ////////////////////////////////////////////////////////////////////////////////
     581              : /// Returns the value of the perm attribute.
     582              : 
     583            8 : const IndiProperty::PropertyPermType &IndiProperty::getPerm() const
     584              : {
     585            8 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     586            8 :   return m_tPerm;
     587            8 : }
     588              : 
     589              : ////////////////////////////////////////////////////////////////////////////////
     590              : /// Returns the rule stored in the message.
     591              : 
     592            4 : const IndiProperty::SwitchRuleType &IndiProperty::getRule() const
     593              : {
     594            4 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     595            4 :   return m_tRule;
     596            4 : }
     597              : 
     598              : ////////////////////////////////////////////////////////////////////////////////
     599              : /// Returns the state of the device.
     600              : 
     601           24 : const IndiProperty::PropertyStateType &IndiProperty::getState() const
     602              : {
     603           24 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     604           24 :   return m_tState;
     605           24 : }
     606              : 
     607              : ////////////////////////////////////////////////////////////////////////////////
     608              : /// Returns the timeout of the device.
     609              : 
     610            0 : const double &IndiProperty::getTimeout() const
     611              : {
     612            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     613            0 :   return m_xTimeout;
     614            0 : }
     615              : 
     616              : ////////////////////////////////////////////////////////////////////////////////
     617              : /// Returns the timestamp stored in the message.
     618              : 
     619            0 : const TimeStamp &IndiProperty::getTimeStamp() const
     620              : {
     621            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     622            0 :   return m_tsTimeStamp;
     623            0 : }
     624              : 
     625              : ////////////////////////////////////////////////////////////////////////////////
     626              : /// Returns the message type.
     627              : 
     628           85 : const IndiProperty::Type &IndiProperty::getType() const
     629              : {
     630           85 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     631           85 :   return m_tType;
     632           85 : }
     633              : 
     634              : ////////////////////////////////////////////////////////////////////////////////
     635              : /// Returns the version stored in the message.
     636              : 
     637            0 : const string &IndiProperty::getVersion() const
     638              : {
     639            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     640            0 :   return m_szVersion;
     641            0 : }
     642              : 
     643              : ////////////////////////////////////////////////////////////////////////////////
     644              : /// Returns whether or not this property has been requested by a client.
     645              : /// This is not managed automatically.
     646              : 
     647            0 : const bool &IndiProperty::isRequested() const
     648              : {
     649            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     650            0 :   return m_oRequested;
     651            0 : }
     652              : 
     653              : ////////////////////////////////////////////////////////////////////////////////
     654              : /// Remove all elements from this object.
     655              : 
     656            0 : void IndiProperty::clear()
     657              : {
     658            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     659            0 :   m_mapElements.clear();
     660            0 : }
     661              : 
     662              : ////////////////////////////////////////////////////////////////////////////////
     663              : 
     664            0 : void IndiProperty::setBLOBEnable( const BLOBEnableType &tValue )
     665              : {
     666            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     667            0 :   m_beValue = tValue;
     668            0 : }
     669              : 
     670              : ////////////////////////////////////////////////////////////////////////////////
     671              : 
     672         3603 : void IndiProperty::setDevice( const string &szValue )
     673              : {
     674         3603 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     675         3603 :   m_szDevice = szValue;
     676         3603 : }
     677              : 
     678              : ////////////////////////////////////////////////////////////////////////////////
     679              : 
     680           32 : void IndiProperty::setGroup( const string &szValue )
     681              : {
     682           32 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     683           32 :   m_szGroup = szValue;
     684           32 : }
     685              : 
     686              : ////////////////////////////////////////////////////////////////////////////////
     687              : 
     688           32 : void IndiProperty::setLabel( const string &szValue )
     689              : {
     690           32 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     691           32 :   m_szLabel = szValue;
     692           32 : }
     693              : 
     694              : ////////////////////////////////////////////////////////////////////////////////
     695              : 
     696           26 : void IndiProperty::setMessage( const string &szValue )
     697              : {
     698           26 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     699           26 :   m_szMessage = szValue;
     700           26 : }
     701              : 
     702              : ////////////////////////////////////////////////////////////////////////////////
     703              : 
     704         3573 : void IndiProperty::setName( const string &szValue )
     705              : {
     706         3573 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     707         3573 :   m_szName = szValue;
     708         3573 : }
     709              : 
     710              : ////////////////////////////////////////////////////////////////////////////////
     711              : 
     712          134 : void IndiProperty::setPerm( const IndiProperty::PropertyPermType &tValue )
     713              : {
     714          134 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     715          134 :   m_tPerm = tValue;
     716          134 : }
     717              : 
     718              : ////////////////////////////////////////////////////////////////////////////////
     719              : 
     720            0 : void IndiProperty::setRequested( const bool &oRequested )
     721              : {
     722            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     723            0 :   m_oRequested = oRequested;
     724            0 : }
     725              : 
     726              : ////////////////////////////////////////////////////////////////////////////////
     727              : 
     728           28 : void IndiProperty::setRule( const IndiProperty::SwitchRuleType &tValue )
     729              : {
     730           28 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     731           28 :   m_tRule = tValue;
     732           28 : }
     733              : 
     734              : ////////////////////////////////////////////////////////////////////////////////
     735              : 
     736          143 : void IndiProperty::setState( const IndiProperty::PropertyStateType &tValue )
     737              : {
     738          143 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     739          143 :   m_tState = tValue;
     740          143 : }
     741              : 
     742              : ////////////////////////////////////////////////////////////////////////////////
     743              : 
     744            0 : void IndiProperty::setTimeout( const double &xValue )
     745              : {
     746            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     747            0 :   m_xTimeout = xValue;
     748            0 : }
     749              : 
     750              : ////////////////////////////////////////////////////////////////////////////////
     751              : 
     752           56 : void IndiProperty::setTimeStamp( const TimeStamp &tsValue )
     753              : {
     754           56 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     755           56 :   m_tsTimeStamp = tsValue;
     756           56 : }
     757              : 
     758              : ////////////////////////////////////////////////////////////////////////////////
     759              : 
     760            0 : void IndiProperty::setVersion( const string &szValue )
     761              : {
     762            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     763            0 :   m_szVersion = szValue;
     764            0 : }
     765              : 
     766              : ////////////////////////////////////////////////////////////////////////////////
     767              : /// Returns the number of elements.
     768              : 
     769            4 : unsigned int IndiProperty::getNumElements() const
     770              : {
     771            4 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     772            8 :   return ( m_mapElements.size() );
     773            4 : }
     774              : 
     775              : ////////////////////////////////////////////////////////////////////////////////
     776              : /// Returns the element named szName.
     777              : /// Throws exception if name is not found.
     778              : 
     779            0 : const IndiElement& IndiProperty::at( const string& szName ) const
     780              : {
     781            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     782            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.find( szName );
     783              : 
     784            0 :   if ( itr == m_mapElements.end() )
     785            0 :     throw runtime_error( string( "Element name '" ) + szName + "' not found." );
     786              : 
     787            0 :   return itr->second;
     788            0 : }
     789              : 
     790              : ////////////////////////////////////////////////////////////////////////////////
     791              : /// Returns the element named szName.
     792              : /// Throws exception if name is not found.
     793              : 
     794            0 : IndiElement& IndiProperty::at( const string& szName )
     795              : {
     796            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     797            0 :   map<string, IndiElement>::iterator itr = m_mapElements.find( szName );
     798              : 
     799            0 :   if ( itr == m_mapElements.end() )
     800            0 :     throw runtime_error( string( "Element name '" ) + szName + "' not found." );
     801              : 
     802            0 :   return itr->second;
     803            0 : }
     804              : 
     805              : ////////////////////////////////////////////////////////////////////////////////
     806              : /// Returns the element at index uiIndex.
     807              : /// Throws exception if index is out of bounds.
     808              : 
     809            0 : const IndiElement& IndiProperty::at( const unsigned int& uiIndex ) const
     810              : {
     811            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     812              : 
     813            0 :   if ( uiIndex > m_mapElements.size() - 1 )
     814            0 :     throw Excep( ErrIndexOutOfBounds );
     815              : 
     816            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     817            0 :   std::advance( itr, uiIndex );
     818              : 
     819            0 :   return itr->second;
     820            0 : }
     821              : 
     822              : ////////////////////////////////////////////////////////////////////////////////
     823              : /// Returns the element at index uiIndex.
     824              : /// Throws exception if index is out of bounds.
     825              : 
     826            0 : IndiElement& IndiProperty::at( const unsigned int& uiIndex )
     827              : {
     828            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     829              : 
     830            0 :   if ( uiIndex > m_mapElements.size() - 1 )
     831            0 :     throw Excep( ErrIndexOutOfBounds );
     832              : 
     833            0 :   map<string, IndiElement>::iterator itr = m_mapElements.begin();
     834            0 :   std::advance( itr, uiIndex );
     835              : 
     836            0 :   return itr->second;
     837            0 : }
     838              : 
     839              : ////////////////////////////////////////////////////////////////////////////////
     840              : /// Returns the element named szName.
     841              : /// Throws exception if name is not found.
     842              : 
     843           44 : const IndiElement& IndiProperty::operator[]( const string& szName ) const
     844              : {
     845           44 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     846           44 :   map<string, IndiElement>::const_iterator itr = m_mapElements.find( szName );
     847              : 
     848           44 :   if ( itr == m_mapElements.end() )
     849            0 :     throw runtime_error( string( "Element name '" ) + szName + "' not found." );
     850              : 
     851           88 :   return itr->second;
     852           44 : }
     853              : 
     854              : ////////////////////////////////////////////////////////////////////////////////
     855              : /// Returns the element named szName.
     856              : /// Throws exception if name is not found.
     857              : 
     858          284 : IndiElement& IndiProperty::operator[]( const string& szName )
     859              : {
     860          284 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     861          284 :   map<string, IndiElement>::iterator itr = m_mapElements.find( szName );
     862              : 
     863          284 :   if ( itr == m_mapElements.end() )
     864            0 :     throw runtime_error( string( "Element name '" ) + szName + "' not found." );
     865              : 
     866          568 :   return itr->second;
     867          284 : }
     868              : 
     869              : ////////////////////////////////////////////////////////////////////////////////
     870              : /// Returns the element at an index (zero-based).
     871              : /// Throws exception if name is not found.
     872              : 
     873            0 : const IndiElement& IndiProperty::operator[]( const unsigned int& uiIndex ) const
     874              : {
     875            0 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
     876              : 
     877            0 :   if ( uiIndex > m_mapElements.size() - 1 )
     878            0 :     throw Excep( ErrIndexOutOfBounds );
     879              : 
     880            0 :   map<string, IndiElement>::const_iterator itr = m_mapElements.begin();
     881            0 :   std::advance( itr, uiIndex );
     882              : 
     883            0 :   return itr->second;
     884            0 : }
     885              : 
     886              : ////////////////////////////////////////////////////////////////////////////////
     887              : /// Returns the element at an index (zero-based).
     888              : /// Throws exception if name is not found.
     889              : 
     890            0 : IndiElement& IndiProperty::operator[]( const unsigned int& uiIndex )
     891              : {
     892            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     893              : 
     894            0 :   if ( uiIndex > m_mapElements.size() - 1 )
     895            0 :     throw Excep( ErrIndexOutOfBounds );
     896              : 
     897            0 :   map<string, IndiElement>::iterator itr = m_mapElements.begin();
     898            0 :   std::advance( itr, uiIndex );
     899              : 
     900            0 :   return itr->second;
     901            0 : }
     902              : 
     903              : ////////////////////////////////////////////////////////////////////////////////
     904              : /// Returns the entire map of elements.
     905              : 
     906            5 : const map<string, IndiElement> &IndiProperty::getElements() const
     907              : {
     908            5 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     909            5 :   return m_mapElements;
     910            5 : }
     911              : 
     912              : ////////////////////////////////////////////////////////////////////////////////
     913              : /// Sets the entire map of elements.
     914              : 
     915            0 : void IndiProperty::setElements( const map<string, IndiElement> &mapElements )
     916              : {
     917            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     918            0 :   m_mapElements = mapElements;
     919            0 : }
     920              : 
     921              : ////////////////////////////////////////////////////////////////////////////////
     922              : /// Updates the value of an element, adds it if it doesn't exist.
     923              : 
     924            0 : void IndiProperty::update( const IndiElement &ieNew )
     925              : {
     926            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     927              : 
     928              :   // Actually add it to the map, or update it.
     929            0 :   m_mapElements[ ieNew.getName() ] = ieNew;
     930              : 
     931            0 :   m_tsTimeStamp = TimeStamp::now();
     932            0 : }
     933              : 
     934              : ////////////////////////////////////////////////////////////////////////////////
     935              : /// Adds an element if it doesn't exist. If it does exist, this is a no-op.
     936              : 
     937            0 : void IndiProperty::addIfNoExist( const IndiElement &ieNew )
     938              : {
     939            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     940              : 
     941              :   map<string, IndiElement>::const_iterator itr =
     942            0 :     m_mapElements.find( ieNew.getName() );
     943              : 
     944            0 :   if ( itr == m_mapElements.end() )
     945              :   {
     946              :     // Actually add it to the map.
     947            0 :     m_mapElements[ ieNew.getName() ] = ieNew;
     948            0 :     m_tsTimeStamp = TimeStamp::now();
     949              :   }
     950            0 : }
     951              : 
     952              : ////////////////////////////////////////////////////////////////////////////////
     953              : /// Adds a new IndiElement.
     954              : /// Throws if the element already exists.
     955              : 
     956          251 : void IndiProperty::add( const IndiElement &ieNew )
     957              : {
     958          251 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     959              : 
     960              :   map<string, IndiElement>::const_iterator itr =
     961          251 :     m_mapElements.find( ieNew.getName() );
     962              : 
     963          251 :   if ( itr != m_mapElements.end() )
     964            0 :     throw Excep( ErrElementAlreadyExists );
     965              : 
     966              :   // Actually add it to the map.
     967          251 :   m_mapElements[ ieNew.getName() ] = ieNew;
     968              : 
     969          251 :   m_tsTimeStamp = TimeStamp::now();
     970          251 : }
     971              : 
     972              : ////////////////////////////////////////////////////////////////////////////////
     973              : /// Removes an element named 'szElementName'.
     974              : /// Throws if the element doesn't exist.
     975              : 
     976            0 : void IndiProperty::remove( const string &szElementName )
     977              : {
     978            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     979              : 
     980              :   map<string, IndiElement>::iterator itr =
     981            0 :     m_mapElements.find( szElementName );
     982              : 
     983            0 :   if ( itr == m_mapElements.end() )
     984            0 :     throw Excep( ErrCouldntFindElement );
     985              : 
     986              :   // Actually delete the element.
     987            0 :   m_mapElements.erase( itr );
     988            0 : }
     989              : 
     990              : ////////////////////////////////////////////////////////////////////////////////
     991              : /// Updates the value of an element named 'szElementName'.
     992              : /// Throws if the element doesn't exist.
     993              : 
     994            0 : void IndiProperty::update( const string &szElementName,
     995              :                            const IndiElement &ieUpdate )
     996              : {
     997            0 :   pcf::ReadWriteLock::AutoWLock rwAuto( &m_rwData );
     998              : 
     999              :   map<string, IndiElement>::iterator itr =
    1000            0 :     m_mapElements.find( szElementName );
    1001              : 
    1002            0 :   if ( itr == m_mapElements.end() )
    1003            0 :     throw Excep( ErrCouldntFindElement );
    1004              : 
    1005            0 :   itr->second = ieUpdate;
    1006              : 
    1007            0 :   m_tsTimeStamp = TimeStamp::now();
    1008            0 : }
    1009              : 
    1010              : ////////////////////////////////////////////////////////////////////////////////
    1011              : ///  Returns true if the element 'szElementName' exists, false otherwise.
    1012              : 
    1013          155 : bool IndiProperty::find( const string &szElementName ) const
    1014              : {
    1015          155 :   pcf::ReadWriteLock::AutoRLock rwAuto( &m_rwData );
    1016              : 
    1017              :   map<string, IndiElement>::const_iterator itr =
    1018          155 :     m_mapElements.find( szElementName );
    1019              : 
    1020          310 :   return ( itr != m_mapElements.end() );
    1021          155 : }
    1022              : 
    1023              : ////////////////////////////////////////////////////////////////////////////////
    1024              : ///  return the message concerning the error.
    1025              : /// @param nErr The error to look up the message for.
    1026              : 
    1027            0 : string IndiProperty::getErrorMsg( const int &nErr )
    1028              : {
    1029            0 :   string szMsg;
    1030            0 :   switch ( nErr )
    1031              :   {
    1032              :     //  errors defined in this class.
    1033            0 :     case ErrNone:
    1034            0 :       szMsg = "No Error";
    1035            0 :       break;
    1036            0 :     case ErrCouldntFindElement:
    1037            0 :       szMsg = "Could not find element";
    1038            0 :       break;
    1039            0 :     case ErrElementAlreadyExists:
    1040            0 :       szMsg = "Element already exists";
    1041            0 :       break;
    1042            0 :     case ErrIndexOutOfBounds:
    1043            0 :       szMsg = "Index out of bounds";
    1044            0 :       break;
    1045            0 :     default:
    1046            0 :       szMsg = "Unknown error";
    1047            0 :       break;
    1048              :   }
    1049            0 :   return szMsg;
    1050            0 : }
    1051              : 
    1052              : ////////////////////////////////////////////////////////////////////////////////
    1053              : /// Returns the enumerated type given the string type.
    1054              : 
    1055            0 : IndiProperty::BLOBEnableType IndiProperty::getBLOBEnableType( const string &szType )
    1056              : {
    1057            0 :   BLOBEnableType tType = UnknownBLOBEnable;
    1058              : 
    1059            0 :   if ( szType == "Never" )
    1060            0 :     tType = Never;
    1061            0 :   else if ( szType == "Also" )
    1062            0 :     tType = Also;
    1063            0 :   else if ( szType == "Only" )
    1064            0 :     tType = Only;
    1065              : 
    1066            0 :   return tType;
    1067              : }
    1068              : 
    1069              : ////////////////////////////////////////////////////////////////////////////////
    1070              : /// Returns the string type given the enumerated type.
    1071              : 
    1072            0 : string IndiProperty::getBLOBEnableString( const BLOBEnableType &tType )
    1073              : {
    1074            0 :   string szType = "";
    1075              : 
    1076            0 :   switch ( tType )
    1077              :   {
    1078            0 :     case UnknownBLOBEnable:
    1079            0 :       szType = "";
    1080            0 :       break;
    1081            0 :     case Never:
    1082            0 :       szType = "Never";
    1083            0 :       break;
    1084            0 :     case Also:
    1085            0 :       szType = "Also";
    1086            0 :       break;
    1087            0 :     case Only:
    1088            0 :       szType = "Only";
    1089            0 :       break;
    1090              :   }
    1091              : 
    1092            0 :   return szType;
    1093            0 : }
    1094              : 
    1095              : ////////////////////////////////////////////////////////////////////////////////
    1096              : /// Returns the enumerated type given the string type.
    1097              : 
    1098            0 : IndiProperty::PropertyStateType IndiProperty::getPropertyStateType( const string &szType )
    1099              : {
    1100            0 :   PropertyStateType tType = UnknownPropertyState;
    1101              : 
    1102            0 :   if ( szType == "Idle" )
    1103            0 :     tType = Idle;
    1104            0 :   else if ( szType == "Ok" )
    1105            0 :     tType = Ok;
    1106            0 :   else if ( szType == "Busy" )
    1107            0 :     tType = Busy;
    1108            0 :   else if ( szType == "Alert" )
    1109            0 :     tType = Alert;
    1110              : 
    1111            0 :   return tType;
    1112              : }
    1113              : 
    1114              : ////////////////////////////////////////////////////////////////////////////////
    1115              : /// Returns the string type given the enumerated type.
    1116              : 
    1117            0 : string IndiProperty::getPropertyStateString( const PropertyStateType &tType )
    1118              : {
    1119            0 :   string szType = "";
    1120              : 
    1121            0 :   switch ( tType )
    1122              :   {
    1123            0 :     case UnknownPropertyState:
    1124            0 :       szType = "";
    1125            0 :       break;
    1126            0 :     case Idle:
    1127            0 :       szType = "Idle";
    1128            0 :       break;
    1129            0 :     case Ok:
    1130            0 :       szType = "Ok";
    1131            0 :       break;
    1132            0 :     case Busy:
    1133            0 :       szType = "Busy";
    1134            0 :       break;
    1135            0 :     case Alert:
    1136            0 :       szType = "Alert";
    1137            0 :       break;
    1138              :   }
    1139              : 
    1140            0 :   return szType;
    1141            0 : }
    1142              : 
    1143              : ////////////////////////////////////////////////////////////////////////////////
    1144              : /// Returns the enumerated type given the string type.
    1145              : 
    1146            0 : IndiProperty::SwitchRuleType IndiProperty::getSwitchRuleType( const string &szType )
    1147              : {
    1148            0 :   SwitchRuleType tType = UnknownSwitchRule;
    1149              : 
    1150            0 :   if ( szType == "OneOfMany" )
    1151            0 :     tType = OneOfMany;
    1152            0 :   else if ( szType == "AtMostOne" )
    1153            0 :     tType = AtMostOne;
    1154            0 :   else if ( szType == "AnyOfMany" )
    1155            0 :     tType = AnyOfMany;
    1156              : 
    1157            0 :   return tType;
    1158              : }
    1159              : 
    1160              : ////////////////////////////////////////////////////////////////////////////////
    1161              : /// Returns the string type given the enumerated type.
    1162              : 
    1163            0 : string IndiProperty::getSwitchRuleString( const SwitchRuleType &tType )
    1164              : {
    1165            0 :   string szType = "";
    1166              : 
    1167            0 :   switch ( tType )
    1168              :   {
    1169            0 :     case OneOfMany:
    1170            0 :       szType = "OneOfMany";
    1171            0 :       break;
    1172            0 :     case AtMostOne:
    1173            0 :       szType = "AtMostOne";
    1174            0 :       break;
    1175            0 :     case AnyOfMany:
    1176            0 :       szType = "AnyOfMany";
    1177            0 :       break;
    1178            0 :     case UnknownSwitchRule:
    1179            0 :       szType = "";
    1180            0 :       break;
    1181              :   }
    1182              : 
    1183            0 :   return szType;
    1184            0 : }
    1185              : 
    1186              : ////////////////////////////////////////////////////////////////////////////////
    1187              : /// Returns the enumerated type given the string type.
    1188              : 
    1189            0 : IndiProperty::PropertyPermType IndiProperty::getPropertyPermType( const string &szType )
    1190              : {
    1191            0 :   PropertyPermType tType = UnknownPropertyPerm;
    1192              : 
    1193            0 :   if ( szType == "ro" )
    1194            0 :     tType = ReadOnly;
    1195            0 :   else if ( szType == "wo" )
    1196            0 :     tType = WriteOnly;
    1197            0 :   else if ( szType == "rw" )
    1198            0 :     tType = ReadWrite;
    1199              : 
    1200            0 :   return tType;
    1201              : }
    1202              : 
    1203              : ////////////////////////////////////////////////////////////////////////////////
    1204              : /// Returns the string type given the enumerated type.
    1205              : 
    1206            0 : string IndiProperty::getPropertyPermString( const PropertyPermType &tType )
    1207              : {
    1208            0 :   string szType = "";
    1209              : 
    1210            0 :   switch ( tType )
    1211              :   {
    1212            0 :     case UnknownPropertyPerm:
    1213            0 :       szType = "";
    1214            0 :       break;
    1215            0 :     case ReadOnly:
    1216            0 :       szType = "ro";
    1217            0 :       break;
    1218            0 :     case WriteOnly:
    1219            0 :       szType = "wo";
    1220            0 :       break;
    1221            0 :     case ReadWrite:
    1222            0 :       szType = "rw";
    1223            0 :       break;
    1224              :   }
    1225              : 
    1226            0 :   return szType;
    1227            0 : }
    1228              : 
    1229              : ////////////////////////////////////////////////////////////////////////////////
    1230              : /// Returns the string type given the enumerated type.
    1231              : 
    1232            0 : string IndiProperty::convertTypeToString( const Type &tType )
    1233              : {
    1234            0 :   string szType = "";
    1235              : 
    1236            0 :   switch ( tType )
    1237              :   {
    1238            0 :     case IndiProperty::Unknown:
    1239            0 :       szType = "";
    1240            0 :       break;
    1241            0 :     case IndiProperty::BLOB:
    1242            0 :       szType = "BLOB";
    1243            0 :       break;
    1244            0 :     case IndiProperty::Light:
    1245            0 :       szType = "Light";
    1246            0 :       break;
    1247            0 :     case IndiProperty::Number:
    1248            0 :       szType = "Number";
    1249            0 :       break;
    1250            0 :     case IndiProperty::Switch:
    1251            0 :       szType = "Switch";
    1252            0 :       break;
    1253            0 :     case IndiProperty::Text:
    1254            0 :       szType = "Text";
    1255            0 :       break;
    1256              :   }
    1257              : 
    1258            0 :   return szType;
    1259            0 : }
    1260              : 
    1261              : ////////////////////////////////////////////////////////////////////////////////
    1262              : /// Returns the enumerated type given the tag.
    1263              : 
    1264            0 : IndiProperty::Type IndiProperty::convertStringToType( const string &szTag )
    1265              : {
    1266            0 :   Type tType = IndiProperty::Unknown;
    1267              : 
    1268              :   // Define properties.
    1269            0 :   if ( szTag == "BLOB" )
    1270            0 :     tType = IndiProperty::BLOB;
    1271            0 :   else if ( szTag == "Light" )
    1272            0 :     tType = IndiProperty::Light;
    1273            0 :   else if ( szTag == "Number" )
    1274            0 :     tType = IndiProperty::Number;
    1275            0 :   else if ( szTag == "Switch" )
    1276            0 :     tType = IndiProperty::Switch;
    1277            0 :   else if ( szTag == "Text" )
    1278            0 :     tType = IndiProperty::Text;
    1279              : 
    1280            0 :   return tType;
    1281              : }
    1282              : 
    1283              : ////////////////////////////////////////////////////////////////////////////////
        

Generated by: LCOV version 2.0-1