quadEM 7-0
|
00001 /* 00002 www.sourceforge.net/projects/tinyxml 00003 Original file by Yves Berquin. 00004 00005 This software is provided 'as-is', without any express or implied 00006 warranty. In no event will the authors be held liable for any 00007 damages arising from the use of this software. 00008 00009 Permission is granted to anyone to use this software for any 00010 purpose, including commercial applications, and to alter it and 00011 redistribute it freely, subject to the following restrictions: 00012 00013 1. The origin of this software must not be misrepresented; you must 00014 not claim that you wrote the original software. If you use this 00015 software in a product, an acknowledgment in the product documentation 00016 would be appreciated but is not required. 00017 00018 2. Altered source versions must be plainly marked as such, and 00019 must not be misrepresented as being the original software. 00020 00021 3. This notice may not be removed or altered from any source 00022 distribution. 00023 */ 00024 00025 /* 00026 * THIS FILE WAS ALTERED BY Tyge Lovset, 7. April 2005. 00027 * 00028 * - completely rewritten. compact, clean, and fast implementation. 00029 * - sizeof(TiXmlString) = pointer size (4 bytes on 32-bit systems) 00030 * - fixed reserve() to work as per specification. 00031 * - fixed buggy compares operator==(), operator<(), and operator>() 00032 * - fixed operator+=() to take a const ref argument, following spec. 00033 * - added "copy" constructor with length, and most compare operators. 00034 * - added swap(), clear(), size(), capacity(), operator+(). 00035 */ 00036 00037 #ifndef TIXML_USE_STL 00038 00039 #ifndef TIXML_STRING_INCLUDED 00040 #define TIXML_STRING_INCLUDED 00041 00042 #include <assert.h> 00043 #include <string.h> 00044 #include <shareLib.h> 00045 00046 /* The support for explicit isn't that universal, and it isn't really 00047 required - it is used to check that the TiXmlString class isn't incorrectly 00048 used. Be nice to old compilers and macro it here: 00049 */ 00050 #if defined(_MSC_VER) && (_MSC_VER >= 1200 ) 00051 // Microsoft visual studio, version 6 and higher. 00052 #define TIXML_EXPLICIT explicit 00053 #elif defined(__GNUC__) && (__GNUC__ >= 3 ) 00054 // GCC version 3 and higher.s 00055 #define TIXML_EXPLICIT explicit 00056 #else 00057 #define TIXML_EXPLICIT 00058 #endif 00059 00060 00061 /* 00062 TiXmlString is an emulation of a subset of the std::string template. 00063 Its purpose is to allow compiling TinyXML on compilers with no or poor STL support. 00064 Only the member functions relevant to the TinyXML project have been implemented. 00065 The buffer allocation is made by a simplistic power of 2 like mechanism : if we increase 00066 a string and there's no more room, we allocate a buffer twice as big as we need. 00067 */ 00068 class epicsShareFunc TiXmlString 00069 { 00070 public : 00071 // The size type used 00072 typedef size_t size_type; 00073 00074 // Error value for find primitive 00075 static const size_type npos; // = -1; 00076 00077 00078 // TiXmlString empty constructor 00079 TiXmlString () : rep_(&nullrep_) 00080 { 00081 } 00082 00083 // TiXmlString copy constructor 00084 TiXmlString ( const TiXmlString & copy) : rep_(0) 00085 { 00086 init(copy.length()); 00087 memcpy(start(), copy.data(), length()); 00088 } 00089 00090 // TiXmlString constructor, based on a string 00091 TIXML_EXPLICIT TiXmlString ( const char * copy) : rep_(0) 00092 { 00093 init( static_cast<size_type>( strlen(copy) )); 00094 memcpy(start(), copy, length()); 00095 } 00096 00097 // TiXmlString constructor, based on a string 00098 TIXML_EXPLICIT TiXmlString ( const char * str, size_type len) : rep_(0) 00099 { 00100 init(len); 00101 memcpy(start(), str, len); 00102 } 00103 00104 // TiXmlString destructor 00105 ~TiXmlString () 00106 { 00107 quit(); 00108 } 00109 00110 // = operator 00111 TiXmlString& operator = (const char * copy) 00112 { 00113 return assign( copy, (size_type)strlen(copy)); 00114 } 00115 00116 // = operator 00117 TiXmlString& operator = (const TiXmlString & copy) 00118 { 00119 return assign(copy.start(), copy.length()); 00120 } 00121 00122 00123 // += operator. Maps to append 00124 TiXmlString& operator += (const char * suffix) 00125 { 00126 return append(suffix, static_cast<size_type>( strlen(suffix) )); 00127 } 00128 00129 // += operator. Maps to append 00130 TiXmlString& operator += (char single) 00131 { 00132 return append(&single, 1); 00133 } 00134 00135 // += operator. Maps to append 00136 TiXmlString& operator += (const TiXmlString & suffix) 00137 { 00138 return append(suffix.data(), suffix.length()); 00139 } 00140 00141 00142 // Convert a TiXmlString into a null-terminated char * 00143 const char * c_str () const { return rep_->str; } 00144 00145 // Convert a TiXmlString into a char * (need not be null terminated). 00146 const char * data () const { return rep_->str; } 00147 00148 // Return the length of a TiXmlString 00149 size_type length () const { return rep_->size; } 00150 00151 // Alias for length() 00152 size_type size () const { return rep_->size; } 00153 00154 // Checks if a TiXmlString is empty 00155 bool empty () const { return rep_->size == 0; } 00156 00157 // Return capacity of string 00158 size_type capacity () const { return rep_->capacity; } 00159 00160 00161 // single char extraction 00162 const char& at (size_type index) const 00163 { 00164 assert( index < length() ); 00165 return rep_->str[ index ]; 00166 } 00167 00168 // [] operator 00169 char& operator [] (size_type index) const 00170 { 00171 assert( index < length() ); 00172 return rep_->str[ index ]; 00173 } 00174 00175 // find a char in a string. Return TiXmlString::npos if not found 00176 size_type find (char lookup) const 00177 { 00178 return find(lookup, 0); 00179 } 00180 00181 // find a char in a string from an offset. Return TiXmlString::npos if not found 00182 size_type find (char tofind, size_type offset) const 00183 { 00184 if (offset >= length()) return npos; 00185 00186 for (const char* p = c_str() + offset; *p != '\0'; ++p) 00187 { 00188 if (*p == tofind) return static_cast< size_type >( p - c_str() ); 00189 } 00190 return npos; 00191 } 00192 00193 void clear () 00194 { 00195 //Lee: 00196 //The original was just too strange, though correct: 00197 // TiXmlString().swap(*this); 00198 //Instead use the quit & re-init: 00199 quit(); 00200 init(0,0); 00201 } 00202 00203 /* Function to reserve a big amount of data when we know we'll need it. Be aware that this 00204 function DOES NOT clear the content of the TiXmlString if any exists. 00205 */ 00206 void reserve (size_type cap); 00207 00208 TiXmlString& assign (const char* str, size_type len); 00209 00210 TiXmlString& append (const char* str, size_type len); 00211 00212 void swap (TiXmlString& other) 00213 { 00214 Rep* r = rep_; 00215 rep_ = other.rep_; 00216 other.rep_ = r; 00217 } 00218 00219 private: 00220 00221 void init(size_type sz) { init(sz, sz); } 00222 void set_size(size_type sz) { rep_->str[ rep_->size = sz ] = '\0'; } 00223 char* start() const { return rep_->str; } 00224 char* finish() const { return rep_->str + rep_->size; } 00225 00226 struct Rep 00227 { 00228 size_type size, capacity; 00229 char str[1]; 00230 }; 00231 00232 void init(size_type sz, size_type cap) 00233 { 00234 if (cap) 00235 { 00236 // Lee: the original form: 00237 // rep_ = static_cast<Rep*>(operator new(sizeof(Rep) + cap)); 00238 // doesn't work in some cases of new being overloaded. Switching 00239 // to the normal allocation, although use an 'int' for systems 00240 // that are overly picky about structure alignment. 00241 const size_type bytesNeeded = sizeof(Rep) + cap; 00242 const size_type intsNeeded = ( bytesNeeded + sizeof(int) - 1 ) / sizeof( int ); 00243 rep_ = reinterpret_cast<Rep*>( new int[ intsNeeded ] ); 00244 00245 rep_->str[ rep_->size = sz ] = '\0'; 00246 rep_->capacity = cap; 00247 } 00248 else 00249 { 00250 rep_ = &nullrep_; 00251 } 00252 } 00253 00254 void quit() 00255 { 00256 if (rep_ != &nullrep_) 00257 { 00258 // The rep_ is really an array of ints. (see the allocator, above). 00259 // Cast it back before delete, so the compiler won't incorrectly call destructors. 00260 delete [] ( reinterpret_cast<int*>( rep_ ) ); 00261 } 00262 } 00263 00264 Rep * rep_; 00265 static Rep nullrep_; 00266 00267 } ; 00268 00269 00270 inline bool operator == (const TiXmlString & a, const TiXmlString & b) 00271 { 00272 return ( a.length() == b.length() ) // optimization on some platforms 00273 && ( strcmp(a.c_str(), b.c_str()) == 0 ); // actual compare 00274 } 00275 inline bool operator < (const TiXmlString & a, const TiXmlString & b) 00276 { 00277 return strcmp(a.c_str(), b.c_str()) < 0; 00278 } 00279 00280 inline bool operator != (const TiXmlString & a, const TiXmlString & b) { return !(a == b); } 00281 inline bool operator > (const TiXmlString & a, const TiXmlString & b) { return b < a; } 00282 inline bool operator <= (const TiXmlString & a, const TiXmlString & b) { return !(b < a); } 00283 inline bool operator >= (const TiXmlString & a, const TiXmlString & b) { return !(a < b); } 00284 00285 inline bool operator == (const TiXmlString & a, const char* b) { return strcmp(a.c_str(), b) == 0; } 00286 inline bool operator == (const char* a, const TiXmlString & b) { return b == a; } 00287 inline bool operator != (const TiXmlString & a, const char* b) { return !(a == b); } 00288 inline bool operator != (const char* a, const TiXmlString & b) { return !(b == a); } 00289 00290 TiXmlString operator + (const TiXmlString & a, const TiXmlString & b); 00291 TiXmlString operator + (const TiXmlString & a, const char* b); 00292 TiXmlString operator + (const char* a, const TiXmlString & b); 00293 00294 00295 /* 00296 TiXmlOutStream is an emulation of std::ostream. It is based on TiXmlString. 00297 Only the operators that we need for TinyXML have been developped. 00298 */ 00299 class epicsShareFunc TiXmlOutStream : public TiXmlString 00300 { 00301 public : 00302 00303 // TiXmlOutStream << operator. 00304 TiXmlOutStream & operator << (const TiXmlString & in) 00305 { 00306 *this += in; 00307 return *this; 00308 } 00309 00310 // TiXmlOutStream << operator. 00311 TiXmlOutStream & operator << (const char * in) 00312 { 00313 *this += in; 00314 return *this; 00315 } 00316 00317 } ; 00318 00319 #endif // TIXML_STRING_INCLUDED 00320 #endif // TIXML_USE_STL