str.hpp

Go to the documentation of this file.
00001 /* $Id: str.hpp 21594 2010-12-22 11:24:38Z alberth $ */
00002 
00003 /*
00004  * This file is part of OpenTTD.
00005  * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
00006  * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
00007  * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
00008  */
00009 
00012 #ifndef STR_HPP
00013 #define STR_HPP
00014 
00015 #include <errno.h>
00016 #include <stdarg.h>
00017 #include "blob.hpp"
00018 #include "../string_func.h"
00019 
00021 struct CStrA : public CBlobT<char>
00022 {
00023   typedef CBlobT<char> base;                    
00024 
00026   FORCEINLINE CStrA()
00027   {
00028   }
00029 
00031   FORCEINLINE CStrA(const CStrA &src) : base(src)
00032   {
00033     base::FixTail();
00034   }
00035 
00037   FORCEINLINE CStrA(const OnTransfer& ot)
00038     : base(ot)
00039   {
00040   }
00041 
00043   FORCEINLINE char *GrowSizeNC(uint count)
00044   {
00045     char *ret = base::GrowSizeNC(count);
00046     base::FixTail();
00047     return ret;
00048   }
00049 
00051   FORCEINLINE void AppendStr(const char *str)
00052   {
00053     if (!StrEmpty(str)) {
00054       base::AppendRaw(str, strlen(str));
00055       base::FixTail();
00056     }
00057   }
00058 
00060   FORCEINLINE void Append(const CStrA &src)
00061   {
00062     if (src.Length() > 0) {
00063       base::AppendRaw(src);
00064       base::FixTail();
00065     }
00066   }
00067 
00069   FORCEINLINE CStrA &operator = (const char *src)
00070   {
00071     base::Clear();
00072     AppendStr(src);
00073     return *this;
00074   }
00075 
00077   FORCEINLINE CStrA &operator = (const CStrA &src)
00078   {
00079     if (&src != this) {
00080       base::Clear();
00081       base::AppendRaw(src.Data(), src.Size());
00082       base::FixTail();
00083     }
00084     return *this;
00085   }
00086 
00088   FORCEINLINE bool operator < (const CStrA &other) const
00089   {
00090     return strcmp(base::Data(), other.Data()) < 0;
00091   }
00092 
00094   int AddFormatL(const char *format, va_list args)
00095   {
00096     size_t addSize = max<size_t>(strlen(format), 16);
00097     addSize += addSize / 2;
00098     int ret;
00099     int err = 0;
00100     for (;;) {
00101       char *buf = MakeFreeSpace(addSize);
00102       ret = vsnprintf(buf, base::GetReserve(), format, args);
00103       if (ret >= (int)base::GetReserve()) {
00104         /* Greater return than given count means needed buffer size. */
00105         addSize = ret + 1;
00106         continue;
00107       }
00108       if (ret >= 0) {
00109         /* success */
00110         break;
00111       }
00112       err = errno;
00113       if (err != ERANGE && err != ENOENT && err != 0) {
00114         /* some strange failure */
00115         break;
00116       }
00117       /* small buffer (M$ implementation) */
00118       addSize *= 2;
00119     }
00120     if (ret > 0) {
00121       GrowSizeNC(ret);
00122     } else {
00123       base::FixTail();
00124     }
00125     return ret;
00126   }
00127 
00129   int CDECL WARN_FORMAT(2, 3) AddFormat(const char *format, ...)
00130   {
00131     va_list args;
00132     va_start(args, format);
00133     int ret = AddFormatL(format, args);
00134     va_end(args);
00135     return ret;
00136   }
00137 
00139   int CDECL WARN_FORMAT(2, 3) Format(const char *format, ...)
00140   {
00141     base::Free();
00142     va_list args;
00143     va_start(args, format);
00144     int ret = AddFormatL(format, args);
00145     va_end(args);
00146     return ret;
00147   }
00148 };
00149 
00150 #endif /* STR_HPP */

Generated on Fri Dec 31 17:15:32 2010 for OpenTTD by  doxygen 1.6.1