• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2010 Marshall A. Greenblatt. All rights reserved.
2 //
3 // Redistribution and use in source and binary forms, with or without
4 // modification, are permitted provided that the following conditions are
5 // met:
6 //
7 //    * Redistributions of source code must retain the above copyright
8 // notice, this list of conditions and the following disclaimer.
9 //    * Redistributions in binary form must reproduce the above
10 // copyright notice, this list of conditions and the following disclaimer
11 // in the documentation and/or other materials provided with the
12 // distribution.
13 //    * Neither the name of Google Inc. nor the name Chromium Embedded
14 // Framework nor the names of its contributors may be used to endorse
15 // or promote products derived from this software without specific prior
16 // written permission.
17 //
18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 
30 #ifndef CEF_INCLUDE_INTERNAL_CEF_STRING_WRAPPERS_H_
31 #define CEF_INCLUDE_INTERNAL_CEF_STRING_WRAPPERS_H_
32 #pragma once
33 
34 #include <memory.h>
35 #include <string>
36 
37 #include "include/internal/cef_string_types.h"
38 
39 #if defined(USING_CHROMIUM_INCLUDES)
40 #include "base/files/file_path.h"
41 #endif
42 
43 ///
44 // Traits implementation for wide character strings.
45 ///
46 struct CefStringTraitsWide {
47   typedef wchar_t char_type;
48   typedef cef_string_wide_t struct_type;
49   typedef cef_string_userfree_wide_t userfree_struct_type;
50 
clearCefStringTraitsWide51   static inline void clear(struct_type* s) { cef_string_wide_clear(s); }
setCefStringTraitsWide52   static inline int set(const char_type* src,
53                         size_t src_size,
54                         struct_type* output,
55                         int copy) {
56     return cef_string_wide_set(src, src_size, output, copy);
57   }
compareCefStringTraitsWide58   static inline int compare(const struct_type* s1, const struct_type* s2) {
59     return cef_string_wide_cmp(s1, s2);
60   }
userfree_allocCefStringTraitsWide61   static inline userfree_struct_type userfree_alloc() {
62     return cef_string_userfree_wide_alloc();
63   }
userfree_freeCefStringTraitsWide64   static inline void userfree_free(userfree_struct_type ufs) {
65     return cef_string_userfree_wide_free(ufs);
66   }
67 
68   // Conversion methods.
from_asciiCefStringTraitsWide69   static inline bool from_ascii(const char* str, size_t len, struct_type* s) {
70     return cef_string_ascii_to_wide(str, len, s) ? true : false;
71   }
to_stringCefStringTraitsWide72   static inline std::string to_string(const struct_type* s) {
73     cef_string_utf8_t cstr;
74     memset(&cstr, 0, sizeof(cstr));
75     cef_string_wide_to_utf8(s->str, s->length, &cstr);
76     std::string str;
77     if (cstr.length > 0)
78       str = std::string(cstr.str, cstr.length);
79     cef_string_utf8_clear(&cstr);
80     return str;
81   }
from_stringCefStringTraitsWide82   static inline bool from_string(const std::string::value_type* data,
83                                  size_t length,
84                                  struct_type* s) {
85     return cef_string_utf8_to_wide(data, length, s) ? true : false;
86   }
from_stringCefStringTraitsWide87   static inline bool from_string(const std::string& str, struct_type* s) {
88     return from_string(str.data(), str.length(), s);
89   }
to_wstringCefStringTraitsWide90   static inline std::wstring to_wstring(const struct_type* s) {
91     return std::wstring(s->str, s->length);
92   }
from_wstringCefStringTraitsWide93   static inline bool from_wstring(const std::wstring::value_type* data,
94                                   size_t length,
95                                   struct_type* s) {
96     return cef_string_wide_set(data, length, s, true) ? true : false;
97   }
from_wstringCefStringTraitsWide98   static inline bool from_wstring(const std::wstring& str, struct_type* s) {
99     return from_wstring(str.data(), str.length(), s);
100   }
101 #if defined(WCHAR_T_IS_UTF32)
to_string16CefStringTraitsWide102   static inline std::u16string to_string16(const struct_type* s) {
103     cef_string_utf16_t cstr;
104     memset(&cstr, 0, sizeof(cstr));
105     cef_string_wide_to_utf16(s->str, s->length, &cstr);
106     std::u16string str;
107     if (cstr.length > 0) {
108       str = std::u16string(
109           reinterpret_cast<std::u16string::value_type*>(cstr.str), cstr.length);
110     }
111     cef_string_utf16_clear(&cstr);
112     return str;
113   }
from_string16CefStringTraitsWide114   static inline bool from_string16(const std::u16string::value_type* data,
115                                    size_t length,
116                                    struct_type* s) {
117     return cef_string_utf16_to_wide(reinterpret_cast<const char16*>(data),
118                                     length, s)
119                ? true
120                : false;
121   }
122 #else   // WCHAR_T_IS_UTF32
to_string16CefStringTraitsWide123   static inline std::u16string to_string16(const struct_type* s) {
124     return std::u16string(
125         reinterpret_cast<const std::u16string::value_type*>(s->str), s->length);
126   }
from_string16CefStringTraitsWide127   static inline bool from_string16(const std::u16string::value_type* data,
128                                    size_t length,
129                                    struct_type* s) {
130     return cef_string_wide_set(reinterpret_cast<const wchar_t*>(data), length,
131                                s, true)
132                ? true
133                : false;
134   }
135 #endif  // WCHAR_T_IS_UTF32
from_string16CefStringTraitsWide136   static inline bool from_string16(const std::u16string& str, struct_type* s) {
137     return from_string16(str.data(), str.length(), s);
138   }
139 };
140 
141 ///
142 // Traits implementation for utf8 character strings.
143 ///
144 struct CefStringTraitsUTF8 {
145   typedef char char_type;
146   typedef cef_string_utf8_t struct_type;
147   typedef cef_string_userfree_utf8_t userfree_struct_type;
148 
clearCefStringTraitsUTF8149   static inline void clear(struct_type* s) { cef_string_utf8_clear(s); }
setCefStringTraitsUTF8150   static inline int set(const char_type* src,
151                         size_t src_size,
152                         struct_type* output,
153                         int copy) {
154     return cef_string_utf8_set(src, src_size, output, copy);
155   }
compareCefStringTraitsUTF8156   static inline int compare(const struct_type* s1, const struct_type* s2) {
157     return cef_string_utf8_cmp(s1, s2);
158   }
userfree_allocCefStringTraitsUTF8159   static inline userfree_struct_type userfree_alloc() {
160     return cef_string_userfree_utf8_alloc();
161   }
userfree_freeCefStringTraitsUTF8162   static inline void userfree_free(userfree_struct_type ufs) {
163     return cef_string_userfree_utf8_free(ufs);
164   }
165 
166   // Conversion methods.
from_asciiCefStringTraitsUTF8167   static inline bool from_ascii(const char* str, size_t len, struct_type* s) {
168     return cef_string_utf8_copy(str, len, s) ? true : false;
169   }
to_stringCefStringTraitsUTF8170   static inline std::string to_string(const struct_type* s) {
171     return std::string(s->str, s->length);
172   }
from_stringCefStringTraitsUTF8173   static inline bool from_string(const std::string::value_type* data,
174                                  size_t length,
175                                  struct_type* s) {
176     return cef_string_utf8_copy(data, length, s) ? true : false;
177   }
from_stringCefStringTraitsUTF8178   static inline bool from_string(const std::string& str, struct_type* s) {
179     return from_string(str.c_str(), str.length(), s);
180   }
to_wstringCefStringTraitsUTF8181   static inline std::wstring to_wstring(const struct_type* s) {
182     cef_string_wide_t cstr;
183     memset(&cstr, 0, sizeof(cstr));
184     cef_string_utf8_to_wide(s->str, s->length, &cstr);
185     std::wstring str;
186     if (cstr.length > 0)
187       str = std::wstring(cstr.str, cstr.length);
188     cef_string_wide_clear(&cstr);
189     return str;
190   }
from_wstringCefStringTraitsUTF8191   static inline bool from_wstring(const std::wstring::value_type* data,
192                                   size_t length,
193                                   struct_type* s) {
194     return cef_string_wide_to_utf8(data, length, s) ? true : false;
195   }
from_wstringCefStringTraitsUTF8196   static inline bool from_wstring(const std::wstring& str, struct_type* s) {
197     return from_wstring(str.data(), str.length(), s);
198   }
to_string16CefStringTraitsUTF8199   static inline std::u16string to_string16(const struct_type* s) {
200     cef_string_utf16_t cstr;
201     memset(&cstr, 0, sizeof(cstr));
202     cef_string_utf8_to_utf16(s->str, s->length, &cstr);
203     std::u16string str;
204     if (cstr.length > 0) {
205       str = std::u16string(
206           reinterpret_cast<std::u16string::value_type*>(cstr.str), cstr.length);
207     }
208     cef_string_utf16_clear(&cstr);
209     return str;
210   }
from_string16CefStringTraitsUTF8211   static inline bool from_string16(const std::u16string::value_type* data,
212                                    size_t length,
213                                    struct_type* s) {
214     return cef_string_utf16_to_utf8(reinterpret_cast<const char16*>(data),
215                                     length, s)
216                ? true
217                : false;
218   }
from_string16CefStringTraitsUTF8219   static inline bool from_string16(const std::u16string& str, struct_type* s) {
220     return from_string16(str.data(), str.length(), s);
221   }
222 };
223 
224 ///
225 // Traits implementation for utf16 character strings.
226 ///
227 struct CefStringTraitsUTF16 {
228   typedef char16 char_type;
229   typedef cef_string_utf16_t struct_type;
230   typedef cef_string_userfree_utf16_t userfree_struct_type;
231 
clearCefStringTraitsUTF16232   static inline void clear(struct_type* s) { cef_string_utf16_clear(s); }
setCefStringTraitsUTF16233   static inline int set(const char_type* src,
234                         size_t src_size,
235                         struct_type* output,
236                         int copy) {
237     return cef_string_utf16_set(src, src_size, output, copy);
238   }
compareCefStringTraitsUTF16239   static inline int compare(const struct_type* s1, const struct_type* s2) {
240     return cef_string_utf16_cmp(s1, s2);
241   }
userfree_allocCefStringTraitsUTF16242   static inline userfree_struct_type userfree_alloc() {
243     return cef_string_userfree_utf16_alloc();
244   }
userfree_freeCefStringTraitsUTF16245   static inline void userfree_free(userfree_struct_type ufs) {
246     return cef_string_userfree_utf16_free(ufs);
247   }
248 
249   // Conversion methods.
from_asciiCefStringTraitsUTF16250   static inline bool from_ascii(const char* str, size_t len, struct_type* s) {
251     return cef_string_ascii_to_utf16(str, len, s) ? true : false;
252   }
to_stringCefStringTraitsUTF16253   static inline std::string to_string(const struct_type* s) {
254     cef_string_utf8_t cstr;
255     memset(&cstr, 0, sizeof(cstr));
256     cef_string_utf16_to_utf8(s->str, s->length, &cstr);
257     std::string str;
258     if (cstr.length > 0)
259       str = std::string(cstr.str, cstr.length);
260     cef_string_utf8_clear(&cstr);
261     return str;
262   }
from_stringCefStringTraitsUTF16263   static inline bool from_string(const std::string::value_type* data,
264                                  size_t length,
265                                  struct_type* s) {
266     return cef_string_utf8_to_utf16(data, length, s) ? true : false;
267   }
from_stringCefStringTraitsUTF16268   static inline bool from_string(const std::string& str, struct_type* s) {
269     return from_string(str.data(), str.length(), s);
270   }
271 #if defined(WCHAR_T_IS_UTF32)
to_wstringCefStringTraitsUTF16272   static inline std::wstring to_wstring(const struct_type* s) {
273     cef_string_wide_t cstr;
274     memset(&cstr, 0, sizeof(cstr));
275     cef_string_utf16_to_wide(s->str, s->length, &cstr);
276     std::wstring str;
277     if (cstr.length > 0)
278       str = std::wstring(cstr.str, cstr.length);
279     cef_string_wide_clear(&cstr);
280     return str;
281   }
from_wstringCefStringTraitsUTF16282   static inline bool from_wstring(const std::wstring::value_type* data,
283                                   size_t length,
284                                   struct_type* s) {
285     return cef_string_wide_to_utf16(data, length, s) ? true : false;
286   }
287 #else   // WCHAR_T_IS_UTF32
to_wstringCefStringTraitsUTF16288   static inline std::wstring to_wstring(const struct_type* s) {
289     return std::wstring(s->str, s->length);
290   }
from_wstringCefStringTraitsUTF16291   static inline bool from_wstring(const std::wstring::value_type* data,
292                                   size_t length,
293                                   struct_type* s) {
294     return cef_string_utf16_set(data, length, s, true) ? true : false;
295   }
296 #endif  // WCHAR_T_IS_UTF32
from_wstringCefStringTraitsUTF16297   static inline bool from_wstring(const std::wstring& str, struct_type* s) {
298     return from_wstring(str.data(), str.length(), s);
299   }
to_string16CefStringTraitsUTF16300   static inline std::u16string to_string16(const struct_type* s) {
301     return std::u16string(
302         reinterpret_cast<const std::u16string::value_type*>(s->str), s->length);
303   }
from_string16CefStringTraitsUTF16304   static inline bool from_string16(const std::u16string::value_type* data,
305                                    size_t length,
306                                    struct_type* s) {
307     return cef_string_utf16_set(reinterpret_cast<const char16*>(data), length,
308                                 s, true)
309                ? true
310                : false;
311   }
from_string16CefStringTraitsUTF16312   static inline bool from_string16(const std::u16string& str, struct_type* s) {
313     return from_string16(str.data(), str.length(), s);
314   }
315 };
316 
317 ///
318 // CEF string classes can convert between all supported string types. For
319 // example, the CefStringWide class uses wchar_t as the underlying character
320 // type and provides two approaches for converting data to/from a UTF8 string
321 // (std::string).
322 // <p>
323 // 1. Implicit conversion using the assignment operator overload.
324 // <pre>
325 //   CefStringWide aCefString;
326 //   std::string aUTF8String;
327 //   aCefString = aUTF8String; // Assign std::string to CefStringWide
328 //   aUTF8String = aCefString; // Assign CefStringWide to std::string
329 // </pre>
330 // 2. Explicit conversion using the FromString/ToString methods.
331 // <pre>
332 //   CefStringWide aCefString;
333 //   std::string aUTF8String;
334 //   aCefString.FromString(aUTF8String); // Assign std::string to CefStringWide
335 //   aUTF8String = aCefString.ToString(); // Assign CefStringWide to std::string
336 // </pre>
337 // Conversion will only occur if the assigned value is a different string type.
338 // Assigning a std::string to a CefStringUTF8, for example, will copy the data
339 // without performing a conversion.
340 // </p>
341 // CEF string classes are safe for reading from multiple threads but not for
342 // modification. It is the user's responsibility to provide synchronization if
343 // modifying CEF strings from multiple threads.
344 ///
345 template <class traits>
346 class CefStringBase {
347  public:
348   typedef typename traits::char_type char_type;
349   typedef typename traits::struct_type struct_type;
350   typedef typename traits::userfree_struct_type userfree_struct_type;
351 
352   ///
353   // Default constructor.
354   ///
CefStringBase()355   CefStringBase() : string_(NULL), owner_(false) {}
356 
357   ///
358   // Create a new string from an existing string. Data will always be copied.
359   ///
CefStringBase(const CefStringBase & str)360   CefStringBase(const CefStringBase& str) : string_(NULL), owner_(false) {
361     FromString(str.c_str(), str.length(), true);
362   }
363 
364   ///
365   // Create a new string from an existing std::string. Data will be always
366   // copied. Translation will occur if necessary based on the underlying string
367   // type.
368   ///
CefStringBase(const std::string & src)369   CefStringBase(const std::string& src) : string_(NULL), owner_(false) {
370     FromString(src);
371   }
372   CefStringBase(const char* src, size_t length = 0)
string_(NULL)373       : string_(NULL), owner_(false) {
374     if (src)
375       FromString(src, length);
376   }
377 
378   ///
379   // Create a new string from an existing std::wstring. Data will be always
380   // copied. Translation will occur if necessary based on the underlying string
381   // type.
382   ///
CefStringBase(const std::wstring & src)383   CefStringBase(const std::wstring& src) : string_(NULL), owner_(false) {
384     FromWString(src);
385   }
386   CefStringBase(const wchar_t* src, size_t length = 0)
string_(NULL)387       : string_(NULL), owner_(false) {
388     if (src)
389       FromWString(src, length);
390   }
391 
392   ///
393   // Create a new string from an existing string16. Data will be always
394   // copied. Translation will occur if necessary based on the underlying string
395   // type.
396   ///
CefStringBase(const std::u16string & src)397   CefStringBase(const std::u16string& src) : string_(NULL), owner_(false) {
398     FromString16(src);
399   }
400   CefStringBase(const std::u16string::value_type* src, size_t length = 0)
string_(NULL)401       : string_(NULL), owner_(false) {
402     if (src)
403       FromString16(src, length);
404   }
405 #if defined(WCHAR_T_IS_UTF32)
406   CefStringBase(const char16* src, size_t length = 0)
string_(NULL)407       : string_(NULL), owner_(false) {
408     if (src) {
409       FromString16(reinterpret_cast<const std::u16string::value_type*>(src),
410                    length);
411     }
412   }
413 #endif  // WCHAR_T_IS_UTF32
414 
415   ///
416   // Create a new string from an existing character array. If |copy| is true
417   // this class will copy the data. Otherwise, this class will reference the
418   // existing data. Referenced data must exist for the lifetime of this class
419   // and will not be freed by this class.
420   ///
CefStringBase(const char_type * src,size_t src_len,bool copy)421   CefStringBase(const char_type* src, size_t src_len, bool copy)
422       : string_(NULL), owner_(false) {
423     if (src && src_len > 0)
424       FromString(src, src_len, copy);
425   }
426 
427   ///
428   // Create a new string referencing an existing string structure without taking
429   // ownership. Referenced structures must exist for the lifetime of this class
430   // and will not be freed by this class.
431   ///
CefStringBase(const struct_type * src)432   CefStringBase(const struct_type* src) : string_(NULL), owner_(false) {
433     if (!src)
434       return;
435     // Reference the existing structure without taking ownership.
436     Attach(const_cast<struct_type*>(src), false);
437   }
438 
~CefStringBase()439   virtual ~CefStringBase() { ClearAndFree(); }
440 
441   // The following methods are named for compatibility with the standard library
442   // string template types.
443 
444   ///
445   // Return a read-only pointer to the string data.
446   ///
c_str()447   const char_type* c_str() const { return (string_ ? string_->str : NULL); }
448 
449   ///
450   // Return the length of the string data.
451   ///
length()452   size_t length() const { return (string_ ? string_->length : 0); }
453 
454   ///
455   // Return the length of the string data.
456   ///
size()457   inline size_t size() const { return length(); }
458 
459   ///
460   // Returns true if the string is empty.
461   ///
empty()462   bool empty() const { return (string_ == NULL || string_->length == 0); }
463 
464   ///
465   // Compare this string to the specified string.
466   ///
compare(const CefStringBase & str)467   int compare(const CefStringBase& str) const {
468     if (empty() && str.empty())
469       return 0;
470     if (empty())
471       return -1;
472     if (str.empty())
473       return 1;
474     return traits::compare(string_, str.GetStruct());
475   }
476 
477   ///
478   // Clear the string data.
479   ///
clear()480   void clear() {
481     if (string_)
482       traits::clear(string_);
483   }
484 
485   ///
486   // Swap this string's contents with the specified string.
487   ///
swap(CefStringBase & str)488   void swap(CefStringBase& str) {
489     struct_type* tmp_string = string_;
490     bool tmp_owner = owner_;
491     string_ = str.string_;
492     owner_ = str.owner_;
493     str.string_ = tmp_string;
494     str.owner_ = tmp_owner;
495   }
496 
497   // The following methods are unique to CEF string template types.
498 
499   ///
500   // Returns true if this class owns the underlying string structure.
501   ///
IsOwner()502   bool IsOwner() const { return owner_; }
503 
504   ///
505   // Returns a read-only pointer to the underlying string structure. May return
506   // NULL if no structure is currently allocated.
507   ///
GetStruct()508   const struct_type* GetStruct() const { return string_; }
509 
510   ///
511   // Returns a writable pointer to the underlying string structure. Will never
512   // return NULL.
513   ///
GetWritableStruct()514   struct_type* GetWritableStruct() {
515     AllocIfNeeded();
516     return string_;
517   }
518 
519   ///
520   // Clear the state of this class. The underlying string structure and data
521   // will be freed if this class owns the structure.
522   ///
ClearAndFree()523   void ClearAndFree() {
524     if (!string_)
525       return;
526     if (owner_) {
527       clear();
528       delete string_;
529     }
530     string_ = NULL;
531     owner_ = false;
532   }
533 
534   ///
535   // Attach to the specified string structure. If |owner| is true this class
536   // will take ownership of the structure.
537   ///
Attach(struct_type * str,bool owner)538   void Attach(struct_type* str, bool owner) {
539     // Free the previous structure and data, if any.
540     ClearAndFree();
541 
542     string_ = str;
543     owner_ = owner;
544   }
545 
546   ///
547   // Take ownership of the specified userfree structure's string data. The
548   // userfree structure itself will be freed. Only use this method with userfree
549   // structures.
550   ///
AttachToUserFree(userfree_struct_type str)551   void AttachToUserFree(userfree_struct_type str) {
552     // Free the previous structure and data, if any.
553     ClearAndFree();
554 
555     if (!str)
556       return;
557 
558     AllocIfNeeded();
559     owner_ = true;
560     memcpy(string_, str, sizeof(struct_type));
561 
562     // Free the |str| structure but not the data.
563     memset(str, 0, sizeof(struct_type));
564     traits::userfree_free(str);
565   }
566 
567   ///
568   // Detach from the underlying string structure. To avoid memory leaks only use
569   // this method if you already hold a pointer to the underlying string
570   // structure.
571   ///
Detach()572   void Detach() {
573     string_ = NULL;
574     owner_ = false;
575   }
576 
577   ///
578   // Create a userfree structure and give it ownership of this class' string
579   // data. This class will be disassociated from the data. May return NULL if
580   // this string class currently contains no data.
581   ///
DetachToUserFree()582   userfree_struct_type DetachToUserFree() {
583     if (empty())
584       return NULL;
585 
586     userfree_struct_type str = traits::userfree_alloc();
587     memcpy(str, string_, sizeof(struct_type));
588 
589     // Free this class' structure but not the data.
590     memset(string_, 0, sizeof(struct_type));
591     ClearAndFree();
592 
593     return str;
594   }
595 
596   ///
597   // Set this string's data to the specified character array. If |copy| is true
598   // this class will copy the data. Otherwise, this class will reference the
599   // existing data. Referenced data must exist for the lifetime of this class
600   // and will not be freed by this class.
601   ///
FromString(const char_type * src,size_t src_len,bool copy)602   bool FromString(const char_type* src, size_t src_len, bool copy) {
603     if (src == NULL || src_len == 0) {
604       clear();
605       return true;
606     }
607     AllocIfNeeded();
608     return traits::set(src, src_len, string_, copy) ? true : false;
609   }
610 
611   ///
612   // Set this string's data from an existing ASCII string. Data will be always
613   // copied. Translation will occur if necessary based on the underlying string
614   // type.
615   ///
FromASCII(const char * str)616   bool FromASCII(const char* str) {
617     size_t len = str ? strlen(str) : 0;
618     if (len == 0) {
619       clear();
620       return true;
621     }
622     AllocIfNeeded();
623     return traits::from_ascii(str, len, string_);
624   }
625 
626   ///
627   // Return this string's data as a std::string. Translation will occur if
628   // necessary based on the underlying string type.
629   ///
ToString()630   std::string ToString() const {
631     if (empty())
632       return std::string();
633     return traits::to_string(string_);
634   }
635 
636   ///
637   // Set this string's data from an existing std::string. Data will be always
638   // copied. Translation will occur if necessary based on the underlying string
639   // type.
640   ///
FromString(const std::string & str)641   bool FromString(const std::string& str) {
642     if (str.empty()) {
643       clear();
644       return true;
645     }
646     AllocIfNeeded();
647     return traits::from_string(str, string_);
648   }
649 
650   ///
651   // Set this string's data from existing |data| and optional |length|. Data
652   // will be always copied. Translation will occur if necessary based on the
653   // underlying string type.
654   ///
655   bool FromString(const std::string::value_type* data, size_t length = 0) {
656     if (data && length == 0) {
657       length = std::char_traits<std::string::value_type>::length(data);
658     }
659     if (!data || length == 0) {
660       clear();
661       return true;
662     }
663     AllocIfNeeded();
664     return traits::from_string(data, length, string_);
665   }
666 
667   ///
668   // Return this string's data as a std::wstring. Translation will occur if
669   // necessary based on the underlying string type.
670   ///
ToWString()671   std::wstring ToWString() const {
672     if (empty())
673       return std::wstring();
674     return traits::to_wstring(string_);
675   }
676 
677   ///
678   // Set this string's data from an existing std::wstring. Data will be always
679   // copied. Translation will occur if necessary based on the underlying string
680   // type.
681   ///
FromWString(const std::wstring & str)682   bool FromWString(const std::wstring& str) {
683     if (str.empty()) {
684       clear();
685       return true;
686     }
687     AllocIfNeeded();
688     return traits::from_wstring(str, string_);
689   }
690 
691   ///
692   // Set this string's data from existing |data| and optional |length|. Data
693   // will be always copied. Translation will occur if necessary based on the
694   // underlying string type.
695   ///
696   bool FromWString(const std::wstring::value_type* data, size_t length = 0) {
697     if (data && length == 0) {
698       length = std::char_traits<std::wstring::value_type>::length(data);
699     }
700     if (!data || length == 0) {
701       clear();
702       return true;
703     }
704     AllocIfNeeded();
705     return traits::from_wstring(data, length, string_);
706   }
707   ///
708   // Return this string's data as a string16. Translation will occur if
709   // necessary based on the underlying string type.
710   ///
ToString16()711   std::u16string ToString16() const {
712     if (empty())
713       return std::u16string();
714     return traits::to_string16(string_);
715   }
716 
717   ///
718   // Set this string's data from an existing string16. Data will be always
719   // copied. Translation will occur if necessary based on the underlying string
720   // type.
721   ///
FromString16(const std::u16string & str)722   bool FromString16(const std::u16string& str) {
723     if (str.empty()) {
724       clear();
725       return true;
726     }
727     AllocIfNeeded();
728     return traits::from_string16(str, string_);
729   }
730 
731   ///
732   // Set this string's data from existing |data| and optional |length|. Data
733   // will be always copied. Translation will occur if necessary based on the
734   // underlying string type.
735   ///
736   bool FromString16(const std::u16string::value_type* data, size_t length = 0) {
737     if (data && length == 0) {
738       length = std::char_traits<std::u16string::value_type>::length(data);
739     }
740     if (!data || length == 0) {
741       clear();
742       return true;
743     }
744     AllocIfNeeded();
745     return traits::from_string16(data, length, string_);
746   }
747 
748   ///
749   // Comparison operator overloads.
750   ///
751   bool operator<(const CefStringBase& str) const { return (compare(str) < 0); }
752   bool operator<=(const CefStringBase& str) const {
753     return (compare(str) <= 0);
754   }
755   bool operator>(const CefStringBase& str) const { return (compare(str) > 0); }
756   bool operator>=(const CefStringBase& str) const {
757     return (compare(str) >= 0);
758   }
759   bool operator==(const CefStringBase& str) const {
760     return (compare(str) == 0);
761   }
762   bool operator!=(const CefStringBase& str) const {
763     return (compare(str) != 0);
764   }
765 
766   ///
767   // Assignment operator overloads.
768   ///
769   CefStringBase& operator=(const CefStringBase& str) {
770     FromString(str.c_str(), str.length(), true);
771     return *this;
772   }
string()773   operator std::string() const { return ToString(); }
774   CefStringBase& operator=(const std::string& str) {
775     FromString(str);
776     return *this;
777   }
778   CefStringBase& operator=(const std::string::value_type* str) {
779     FromString(str);
780     return *this;
781   }
wstring()782   operator std::wstring() const { return ToWString(); }
783   CefStringBase& operator=(const std::wstring& str) {
784     FromWString(str);
785     return *this;
786   }
787   CefStringBase& operator=(const std::wstring::value_type* str) {
788     FromWString(str);
789     return *this;
790   }
u16string()791   operator std::u16string() const { return ToString16(); }
792   CefStringBase& operator=(const std::u16string& str) {
793     FromString16(str);
794     return *this;
795   }
796   CefStringBase& operator=(const std::u16string::value_type* str) {
797     FromString16(str);
798     return *this;
799   }
800 #if defined(WCHAR_T_IS_UTF32)
801   CefStringBase& operator=(const char16* str) {
802     FromString16(reinterpret_cast<const std::u16string::value_type*>(str));
803     return *this;
804   }
805 #endif  // WCHAR_T_IS_UTF32
806 #if defined(USING_CHROMIUM_INCLUDES)
807   // The base::FilePath constructor is marked as explicit so provide the
808   // conversion here for convenience.
FilePath()809   operator base::FilePath() const {
810 #if defined(OS_WIN)
811     return base::FilePath(ToWString());
812 #else
813     return base::FilePath(ToString());
814 #endif
815   }
816 #endif  // USING_CHROMIUM_INCLUDES
817 
818  private:
819   // Allocate the string structure if it doesn't already exist.
AllocIfNeeded()820   void AllocIfNeeded() {
821     if (string_ == NULL) {
822       string_ = new struct_type;
823       memset(string_, 0, sizeof(struct_type));
824       owner_ = true;
825     }
826   }
827 
828   struct_type* string_;
829   bool owner_;
830 };
831 
832 typedef CefStringBase<CefStringTraitsWide> CefStringWide;
833 typedef CefStringBase<CefStringTraitsUTF8> CefStringUTF8;
834 typedef CefStringBase<CefStringTraitsUTF16> CefStringUTF16;
835 
836 #endif  // CEF_INCLUDE_INTERNAL_CEF_STRING_WRAPPERS_H_
837