~ubuntu-branches/ubuntu/quantal/open-vm-tools/quantal-201210021442

« back to all changes in this revision

Viewing changes to vmware-user/stringxx/ubstr_t.hh

  • Committer: Bazaar Package Importer
  • Author(s): Serge Hallyn
  • Date: 2011-03-31 14:20:05 UTC
  • mfrom: (1.4.3 upstream)
  • Revision ID: james.westby@ubuntu.com-20110331142005-3n9red91p7ogkweo
Tags: 2011.03.28-387002-0ubuntu1
* Merge latest upstream git tag.  This has the unlocked_ioctl change
  needed to fix dkms build failures (LP: #727342)
* Changes in debian/rules:
  - work around a bug in toolbox/Makefile, where install-exec-hook is
    not happening.  This needs to get fixed the right way.
  - don't install 'vmware-user' which seems to no longer exist
  - move /etc/xdg into open-vm-toolbox (which should be done using .install)
* debian/open-vm-tools.init: add 'modprobe [-r] vmblock'. (LP: #332323)
* debian/rules and debian/open-vm-toolbox.lintian-overrides:
  - Make vmware-user-suid-wrapper suid-root (LP: #332323)

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*********************************************************
2
 
 * Copyright (C) 2008 VMware, Inc. All rights reserved.
3
 
 *
4
 
 * This program is free software; you can redistribute it and/or modify it
5
 
 * under the terms of the GNU Lesser General Public License as published
6
 
 * by the Free Software Foundation version 2.1 and no later version.
7
 
 *
8
 
 * This program is distributed in the hope that it will be useful, but
9
 
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
10
 
 * or FITNESS FOR A PARTICULAR PURPOSE.  See the Lesser GNU General Public
11
 
 * License for more details.
12
 
 *
13
 
 * You should have received a copy of the GNU Lesser General Public License
14
 
 * along with this program; if not, write to the Free Software Foundation, Inc.,
15
 
 * 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA.
16
 
 *
17
 
 *********************************************************/
18
 
 
19
 
/*
20
 
 * ubstr_t.hh --
21
 
 *
22
 
 *     A string wrapper for _bstr_t.  _bstr_t assumes all char* strings use
23
 
 *     the local MBCS encoding, but we want to require that char* strings be
24
 
 *     interpreted as UTF-8.
25
 
 */
26
 
 
27
 
#ifndef _WIN32
28
 
#error This file should be built on Windows only.
29
 
#endif
30
 
 
31
 
#pragma once
32
 
 
33
 
#include <algorithm>
34
 
#include <comutil.h>
35
 
#include <glibmm/refptr.h>
36
 
 
37
 
extern "C" {
38
 
#include "unicode.h"
39
 
#include "util.h"
40
 
}
41
 
 
42
 
 
43
 
#ifdef I_LOVE_BSTR_T_CLASSIC
44
 
 
45
 
typedef _bstr_t ubstr_t;
46
 
typedef _variant_t uvariant_t;
47
 
 
48
 
#else
49
 
 
50
 
class ubstr_t
51
 
{
52
 
public:
53
 
   ubstr_t();
54
 
   ubstr_t(const char *s);
55
 
   ubstr_t(const wchar_t *s);
56
 
   ubstr_t(const _variant_t& var);
57
 
   ubstr_t(BSTR bstr, bool copy);
58
 
   ubstr_t(const ubstr_t& s);
59
 
 
60
 
   ubstr_t& operator=(ubstr_t copy);
61
 
   ubstr_t& operator=(const char *s);
62
 
   ubstr_t& operator=(const wchar_t *s);
63
 
   ubstr_t& operator=(const _variant_t& var);
64
 
 
65
 
   // Wrappers around standard _bstr_t methods.
66
 
   void Assign(BSTR s);
67
 
   BSTR copy(bool copy = true) const;
68
 
 
69
 
   void Attach(BSTR s);
70
 
   BSTR Detach();
71
 
 
72
 
   BSTR *GetAddress();
73
 
   BSTR& GetBSTR();
74
 
 
75
 
   unsigned int length() const;
76
 
 
77
 
   ubstr_t& operator+=(const ubstr_t& s);
78
 
   ubstr_t operator+(const ubstr_t& s) const;
79
 
   ubstr_t operator+(const char *s) const;
80
 
   ubstr_t operator+(const wchar_t *s) const;
81
 
 
82
 
   bool operator!() const;
83
 
   bool operator==(const ubstr_t& s) const;
84
 
   bool operator!=(const ubstr_t& s) const;
85
 
   bool operator<(const ubstr_t& s) const;
86
 
   bool operator>(const ubstr_t& s) const;
87
 
   bool operator<=(const ubstr_t& s) const;
88
 
   bool operator>=(const ubstr_t& s) const;
89
 
 
90
 
   operator const wchar_t*() const;
91
 
   operator wchar_t*() const; // XXX: Get rid of this.
92
 
   operator const char*() const;
93
 
#ifndef I_HATE_NON_CONST_BSTR_T_CASTS
94
 
   operator char*() const; // XXX: Get rid of this.
95
 
#endif
96
 
 
97
 
   /*
98
 
    * _variant_t is implicitly constructible from a _bstr_t.  Since we can't
99
 
    * add a constructor to _variant_t, instead provide an implicit conversion
100
 
    * from ubstr_t to _variant_t.
101
 
    */
102
 
   operator _variant_t() const;
103
 
 
104
 
   void swap(ubstr_t& s);
105
 
 
106
 
private:
107
 
   class UTF8Data
108
 
   {
109
 
   public:
110
 
      // Takes ownership of the input string.
111
 
      UTF8Data(char *utf8String = NULL) // IN/OUT: May be NULL
112
 
         : mUTF8String(utf8String),
113
 
           mRefCount(1)
114
 
      {
115
 
      }
116
 
 
117
 
      // For Glib::RefPtr.
118
 
      void reference()
119
 
      {
120
 
         ++mRefCount;
121
 
      }
122
 
 
123
 
      // For Glib::RefPtr.
124
 
      void unreference()
125
 
      {
126
 
         --mRefCount;
127
 
         if (mRefCount == 0) {
128
 
            delete this;
129
 
         }
130
 
      }
131
 
 
132
 
      // Takes ownership of the input string.
133
 
      void Set(char *utf8String) // IN/OUT: May be NULL.
134
 
      {
135
 
         free(mUTF8String);
136
 
         mUTF8String = utf8String;
137
 
      }
138
 
 
139
 
      char *Get()
140
 
      {
141
 
         return mUTF8String;
142
 
      }
143
 
 
144
 
   private:
145
 
      // Only destructible via unreference().
146
 
      ~UTF8Data()
147
 
      {
148
 
         free(mUTF8String);
149
 
      }
150
 
 
151
 
      char *mUTF8String;
152
 
      unsigned int mRefCount;
153
 
 
154
 
   private:
155
 
      // Intentionally unimplemented.
156
 
      UTF8Data(const UTF8Data&);
157
 
      UTF8Data& operator=(const UTF8Data&);
158
 
   };
159
 
 
160
 
   char *GetUTF8Cache() const;
161
 
   void InvalidateCache();
162
 
 
163
 
   /*
164
 
    * Anything that mutates mBstr (all non-const methods) must call
165
 
    * InvalidateCache().
166
 
    */
167
 
   _bstr_t mBstr;
168
 
 
169
 
   // mUTF8 is allocated and initialized lazily.
170
 
   mutable Glib::RefPtr<UTF8Data> mUTF8;
171
 
};
172
 
 
173
 
 
174
 
/*
175
 
 * _variant_t does string conversions too, so we also need to wrap that.
176
 
 * Since _variant_t doesn't keep a cached version of the locally-encoded
177
 
 * MBCS string and since we don't use _variant_t nearly as much as _bstr_t,
178
 
 * substitutability isn't as much of a concern, so we can use inheritance.
179
 
 */
180
 
class uvariant_t
181
 
   : public _variant_t
182
 
{
183
 
public:
184
 
   /*
185
 
    * Wrappers around standard _variant_t constructors.  Unfortunately we
186
 
    * have to wrap all the constructors since they aren't inherited.
187
 
    */
188
 
   uvariant_t() : _variant_t() { }
189
 
   uvariant_t(const VARIANT& var) : _variant_t(var) { }
190
 
   uvariant_t(const VARIANT *var) : _variant_t(var) { }
191
 
   uvariant_t(const _variant_t& var) : _variant_t(var) { }
192
 
   uvariant_t(VARIANT& var, bool copy) : _variant_t(var, copy) { }
193
 
   uvariant_t(short i, VARTYPE vt = VT_I2) : _variant_t(i, vt) { }
194
 
   uvariant_t(long i, VARTYPE vt = VT_I4) : _variant_t(i, vt) { }
195
 
   uvariant_t(float f) : _variant_t(f) { }
196
 
   uvariant_t(double d, VARTYPE vt = VT_R8) : _variant_t(d, vt) { }
197
 
   uvariant_t(const CY& cy) : _variant_t(cy) { }
198
 
   uvariant_t(const _bstr_t& s) : _variant_t(s) { }
199
 
   uvariant_t(const wchar_t *s) : _variant_t(s) { }
200
 
   uvariant_t(IDispatch *dispatch, bool addRef = true) : _variant_t(dispatch, addRef) { }
201
 
   uvariant_t(bool b) : _variant_t(b) { }
202
 
   uvariant_t(IUnknown *unknown, bool addRef = true) : _variant_t(unknown, addRef) { }
203
 
   uvariant_t(const DECIMAL& dec) : _variant_t(dec) { }
204
 
   uvariant_t(BYTE i) : _variant_t(i) { }
205
 
   uvariant_t(char c) : _variant_t(c) { }
206
 
   uvariant_t(unsigned short i) : _variant_t(i) { }
207
 
   uvariant_t(unsigned long i) : _variant_t(i) { }
208
 
   uvariant_t(int i) : _variant_t(i) { }
209
 
   uvariant_t(unsigned int i) : _variant_t(i) { }
210
 
#if _WIN32_WINNT >= 0x0501
211
 
   uvariant_t(__int64 i) : _variant_t(i) { }
212
 
   uvariant_t(unsigned __int64 i) : _variant_t(i) { }
213
 
#endif
214
 
 
215
 
   // Override the _variant_t constructor that assumes locally-encoded strings.
216
 
   uvariant_t(const char *s) : _variant_t(ubstr_t(s)) { }
217
 
 
218
 
   // Provide conversion from our ubstr_t wrapper.
219
 
   uvariant_t(const ubstr_t& s) : _variant_t(s) { }
220
 
};
221
 
 
222
 
 
223
 
/*
224
 
 *-----------------------------------------------------------------------------
225
 
 *
226
 
 * ubstr_t::ubstr_t --
227
 
 *
228
 
 *      ubstr_t constructors.
229
 
 *
230
 
 * Results:
231
 
 *      None.
232
 
 *
233
 
 * Side effects:
234
 
 *      None.
235
 
 *
236
 
 *-----------------------------------------------------------------------------
237
 
 */
238
 
 
239
 
inline
240
 
ubstr_t::ubstr_t()
241
 
   : mBstr(),
242
 
     mUTF8()
243
 
{
244
 
}
245
 
 
246
 
 
247
 
inline
248
 
ubstr_t::ubstr_t(const char *s) // IN: A UTF-8-encoded string.
249
 
   : mBstr(),
250
 
     mUTF8()
251
 
{
252
 
   if (s != NULL) {
253
 
      // Since we already have the UTF-8 version of the string, cache it now.
254
 
      mUTF8 = Glib::RefPtr<UTF8Data>(new UTF8Data(Util_SafeStrdup(s)));
255
 
      utf16_t *utf16Str = Unicode_GetAllocUTF16(s);
256
 
      try {
257
 
         mBstr = utf16Str;
258
 
         free(utf16Str);
259
 
      } catch (...) {
260
 
         free(utf16Str);
261
 
         throw;
262
 
      }
263
 
   }
264
 
}
265
 
 
266
 
 
267
 
inline
268
 
ubstr_t::ubstr_t(const wchar_t *s) // IN
269
 
   : mBstr(s),
270
 
     mUTF8()
271
 
{
272
 
}
273
 
 
274
 
 
275
 
inline
276
 
ubstr_t::ubstr_t(const _variant_t& var) // IN
277
 
   : mBstr(var),
278
 
     mUTF8()
279
 
{
280
 
}
281
 
 
282
 
 
283
 
inline
284
 
ubstr_t::ubstr_t(BSTR bstr, // IN
285
 
                 bool copy) // IN
286
 
   : mBstr(bstr, copy),
287
 
     mUTF8()
288
 
{
289
 
}
290
 
 
291
 
 
292
 
inline
293
 
ubstr_t::ubstr_t(const ubstr_t& s) // IN
294
 
   : mBstr(s.mBstr),
295
 
     mUTF8(s.mUTF8)
296
 
{
297
 
   if (static_cast<wchar_t *>(mBstr) != NULL && !mUTF8) {
298
 
      mUTF8 = s.mUTF8 = Glib::RefPtr<UTF8Data>(new UTF8Data());
299
 
   }
300
 
}
301
 
 
302
 
 
303
 
/*
304
 
 *-----------------------------------------------------------------------------
305
 
 *
306
 
 * ubstr_t::operator= --
307
 
 *
308
 
 *      ubstr_t assignment operators.
309
 
 *
310
 
 * Results:
311
 
 *      None.
312
 
 *
313
 
 * Side effects:
314
 
 *      None.
315
 
 *
316
 
 *-----------------------------------------------------------------------------
317
 
 */
318
 
 
319
 
inline ubstr_t&
320
 
ubstr_t::operator=(ubstr_t copy) // IN
321
 
{
322
 
   swap(copy);
323
 
   return *this;
324
 
}
325
 
 
326
 
 
327
 
inline ubstr_t&
328
 
ubstr_t::operator=(const char *s) // IN: A UTF-8-encoded string.
329
 
{
330
 
   return operator=(ubstr_t(s));
331
 
}
332
 
 
333
 
 
334
 
inline ubstr_t&
335
 
ubstr_t::operator=(const wchar_t *s) // IN
336
 
{
337
 
   return operator=(ubstr_t(s));
338
 
}
339
 
 
340
 
 
341
 
inline ubstr_t&
342
 
ubstr_t::operator=(const _variant_t& var) // IN
343
 
{
344
 
   return operator=(ubstr_t(var));
345
 
}
346
 
 
347
 
 
348
 
 
349
 
/*
350
 
 *-----------------------------------------------------------------------------
351
 
 *
352
 
 * ubstr_t::Assign --
353
 
 *
354
 
 *      Wrapper around _bstr_t::Assign.
355
 
 *
356
 
 * Results:
357
 
 *      None.
358
 
 *
359
 
 * Side effects:
360
 
 *      None.
361
 
 *
362
 
 *-----------------------------------------------------------------------------
363
 
 */
364
 
 
365
 
inline void
366
 
ubstr_t::Assign(BSTR s) // IN
367
 
{
368
 
   InvalidateCache();
369
 
   mBstr.Assign(s);
370
 
}
371
 
 
372
 
 
373
 
/*
374
 
 *-----------------------------------------------------------------------------
375
 
 *
376
 
 * ubstr_t::copy --
377
 
 *
378
 
 *      Wrapper around _bstr_t::copy.
379
 
 *
380
 
 * Results:
381
 
 *      A copy of the underlying BSTR.
382
 
 *
383
 
 * Side effects:
384
 
 *      None.
385
 
 *
386
 
 *-----------------------------------------------------------------------------
387
 
 */
388
 
 
389
 
inline BSTR
390
 
ubstr_t::copy(bool copy) // IN/OPT
391
 
   const
392
 
{
393
 
   return mBstr.copy(copy);
394
 
}
395
 
 
396
 
 
397
 
/*
398
 
 *-----------------------------------------------------------------------------
399
 
 *
400
 
 * ubstr_t::Attach --
401
 
 *
402
 
 *      Wrapper around _bstr_t::Attach.
403
 
 *
404
 
 * Results:
405
 
 *      None.
406
 
 *
407
 
 * Side effects:
408
 
 *      Invalidates the UTF-8 cache.
409
 
 *
410
 
 *-----------------------------------------------------------------------------
411
 
 */
412
 
 
413
 
inline void
414
 
ubstr_t::Attach(BSTR s) // IN
415
 
{
416
 
   InvalidateCache();
417
 
   mBstr.Attach(s);
418
 
}
419
 
 
420
 
 
421
 
/*
422
 
 *-----------------------------------------------------------------------------
423
 
 *
424
 
 * ubstr_t::Detach --
425
 
 *
426
 
 *      Wrapper around _bstr_t::Detach.
427
 
 *
428
 
 * Results:
429
 
 *      The underlying BSTR, which is no longer managed.
430
 
 *
431
 
 * Side effects:
432
 
 *      Invalidates the UTF-8 cache.
433
 
 *
434
 
 *-----------------------------------------------------------------------------
435
 
 */
436
 
 
437
 
inline BSTR
438
 
ubstr_t::Detach()
439
 
{
440
 
   InvalidateCache();
441
 
   return mBstr.Detach();
442
 
}
443
 
 
444
 
 
445
 
/*
446
 
 *-----------------------------------------------------------------------------
447
 
 *
448
 
 * ubstr_t::GetAddress --
449
 
 *
450
 
 *      Wrapper around _bstr_t::GetAddress.
451
 
 *
452
 
 * Results:
453
 
 *      A pointer to the underlying BSTR.
454
 
 *
455
 
 * Side effects:
456
 
 *      Invalidates the UTF-8 cache.
457
 
 *
458
 
 *-----------------------------------------------------------------------------
459
 
 */
460
 
 
461
 
inline BSTR *
462
 
ubstr_t::GetAddress()
463
 
{
464
 
   /*
465
 
    * We don't know if the underlying BSTR will be modified via the returned
466
 
    * pointer.  We can only assume it will.
467
 
    */
468
 
   InvalidateCache();
469
 
   return mBstr.GetAddress();
470
 
}
471
 
 
472
 
 
473
 
/*
474
 
 *-----------------------------------------------------------------------------
475
 
 *
476
 
 * ubstr_t::GetBSTR --
477
 
 *
478
 
 *      Wrapper around _bstr_t::GetBSTR.
479
 
 *
480
 
 * Results:
481
 
 *      A reference to the underlying BSTR.
482
 
 *
483
 
 * Side effects:
484
 
 *      Invalidates the UTF-8 cache.
485
 
 *
486
 
 *-----------------------------------------------------------------------------
487
 
 */
488
 
 
489
 
inline BSTR&
490
 
ubstr_t::GetBSTR()
491
 
{
492
 
   /*
493
 
    * We don't know if the underlying BSTR will be modified via the returned
494
 
    * reference.  We can only assume it will.
495
 
    */
496
 
   InvalidateCache();
497
 
   return mBstr.GetBSTR();
498
 
}
499
 
 
500
 
 
501
 
/*
502
 
 *-----------------------------------------------------------------------------
503
 
 *
504
 
 * ubstr_t::length --
505
 
 *
506
 
 *      Wrapper around _bstr_t::length.
507
 
 *
508
 
 * Results:
509
 
 *      The length of the string, in TCHARs.
510
 
 *
511
 
 * Side effects:
512
 
 *      None.
513
 
 *
514
 
 *-----------------------------------------------------------------------------
515
 
 */
516
 
 
517
 
inline unsigned int
518
 
ubstr_t::length()
519
 
   const
520
 
{
521
 
   return mBstr.length();
522
 
}
523
 
 
524
 
 
525
 
/*
526
 
 *-----------------------------------------------------------------------------
527
 
 *
528
 
 * ubstr_t::operator+= --
529
 
 *
530
 
 *      Mutating concatenation operator.
531
 
 *
532
 
 * Results:
533
 
 *      A reference to this ubstr_t object.
534
 
 *
535
 
 * Side effects:
536
 
 *      Invalidates the UTF-8 cache.
537
 
 *
538
 
 *-----------------------------------------------------------------------------
539
 
 */
540
 
 
541
 
inline ubstr_t&
542
 
ubstr_t::operator+=(const ubstr_t& s) // IN
543
 
{
544
 
   InvalidateCache();
545
 
   mBstr += s.mBstr;
546
 
   return *this;
547
 
}
548
 
 
549
 
 
550
 
/*
551
 
 *-----------------------------------------------------------------------------
552
 
 *
553
 
 * ubstr_t::operator+ --
554
 
 *
555
 
 *      Concatenation operators.
556
 
 *
557
 
 * Results:
558
 
 *      A copy of the concatenated string.
559
 
 *
560
 
 * Side effects:
561
 
 *      None.
562
 
 *
563
 
 *-----------------------------------------------------------------------------
564
 
 */
565
 
 
566
 
inline ubstr_t
567
 
ubstr_t::operator+(const ubstr_t& s) // IN
568
 
   const
569
 
{
570
 
   ubstr_t copy(*this);
571
 
   copy += s;
572
 
   return copy;
573
 
}
574
 
 
575
 
 
576
 
inline ubstr_t
577
 
ubstr_t::operator+(const char *s) // IN
578
 
   const
579
 
{
580
 
   return operator+(ubstr_t(s));
581
 
}
582
 
 
583
 
 
584
 
inline ubstr_t
585
 
ubstr_t::operator+(const wchar_t *s) // IN
586
 
   const
587
 
{
588
 
   return operator+(ubstr_t(s));
589
 
}
590
 
 
591
 
 
592
 
/*
593
 
 *-----------------------------------------------------------------------------
594
 
 *
595
 
 * ubstr_t::operator! --
596
 
 *
597
 
 *      Wrapper around _bstr_t::operator!.
598
 
 *
599
 
 * Results:
600
 
 *      true if the underlying _bstr_t is NULL, false otherwise.
601
 
 *
602
 
 * Side effects:
603
 
 *      None.
604
 
 *
605
 
 *-----------------------------------------------------------------------------
606
 
 */
607
 
 
608
 
inline bool
609
 
ubstr_t::operator!()
610
 
   const
611
 
{
612
 
   return !mBstr;
613
 
}
614
 
 
615
 
 
616
 
/*
617
 
 *-----------------------------------------------------------------------------
618
 
 *
619
 
 * ubstr_t::operator== --
620
 
 * ubstr_t::operator!= --
621
 
 * ubstr_t::operator< --
622
 
 * ubstr_t::operator> --
623
 
 * ubstr_t::operator<= --
624
 
 * ubstr_t::operator>= --
625
 
 *
626
 
 *      Wrappers around _bstr_t's comparison operators.
627
 
 *
628
 
 * Results:
629
 
 *      true if the comparisons are hold, false otherwise.
630
 
 *
631
 
 * Side effects:
632
 
 *      None.
633
 
 *
634
 
 *-----------------------------------------------------------------------------
635
 
 */
636
 
 
637
 
inline bool
638
 
ubstr_t::operator==(const ubstr_t& s) // IN
639
 
   const
640
 
{
641
 
   return mBstr == s.mBstr;
642
 
}
643
 
 
644
 
 
645
 
inline bool
646
 
ubstr_t::operator!=(const ubstr_t& s) // IN
647
 
   const
648
 
{
649
 
   return mBstr != s.mBstr;
650
 
}
651
 
 
652
 
 
653
 
inline bool
654
 
ubstr_t::operator<(const ubstr_t& s) // IN
655
 
   const
656
 
{
657
 
   return mBstr < s.mBstr;
658
 
}
659
 
 
660
 
 
661
 
inline bool
662
 
ubstr_t::operator>(const ubstr_t& s) // IN
663
 
   const
664
 
{
665
 
   return mBstr > s.mBstr;
666
 
}
667
 
 
668
 
 
669
 
inline bool
670
 
ubstr_t::operator<=(const ubstr_t& s) // IN
671
 
   const
672
 
{
673
 
   return mBstr <= s.mBstr;
674
 
}
675
 
 
676
 
 
677
 
inline bool
678
 
ubstr_t::operator>=(const ubstr_t& s) // IN
679
 
   const
680
 
{
681
 
   return mBstr >= s.mBstr;
682
 
}
683
 
 
684
 
 
685
 
/*
686
 
 *-----------------------------------------------------------------------------
687
 
 *
688
 
 * ubstr_t::operator const wchar_t* --
689
 
 * ubstr_t::operator wchar_t* --
690
 
 *
691
 
 *      Wrappers around _bstr_t's cast operators.
692
 
 *
693
 
 * Results:
694
 
 *      A pointer to the underlying UTF-16 string.
695
 
 *
696
 
 * Side effects:
697
 
 *      None.
698
 
 *
699
 
 *-----------------------------------------------------------------------------
700
 
 */
701
 
 
702
 
inline
703
 
ubstr_t::operator const wchar_t*()
704
 
   const
705
 
{
706
 
   return static_cast<const wchar_t *>(mBstr);
707
 
}
708
 
 
709
 
 
710
 
inline
711
 
ubstr_t::operator wchar_t*()
712
 
   const
713
 
{
714
 
   return static_cast<wchar_t *>(mBstr);
715
 
}
716
 
 
717
 
 
718
 
/*
719
 
 *-----------------------------------------------------------------------------
720
 
 *
721
 
 * ubstr_t::operator const char_t* --
722
 
 * ubstr_t::operator char_t* --
723
 
 *
724
 
 *      Cast operators to UTF-8 strings.
725
 
 *
726
 
 * Results:
727
 
 *      A pointer to a UTF-8 string.
728
 
 *
729
 
 * Side effects:
730
 
 *      Might initializes the UTF-8 cache.
731
 
 *
732
 
 *-----------------------------------------------------------------------------
733
 
 */
734
 
 
735
 
inline
736
 
ubstr_t::operator const char*()
737
 
   const
738
 
{
739
 
   return GetUTF8Cache();
740
 
}
741
 
 
742
 
 
743
 
#ifndef I_HATE_NON_CONST_BSTR_T_CASTS
744
 
inline
745
 
ubstr_t::operator char*()
746
 
   const
747
 
{
748
 
   return GetUTF8Cache();
749
 
}
750
 
#endif
751
 
 
752
 
 
753
 
/*
754
 
 *-----------------------------------------------------------------------------
755
 
 *
756
 
 * ubstr_t::operator _variant_t --
757
 
 *
758
 
 *      Cast operator to _variant_t.
759
 
 *
760
 
 * Results:
761
 
 *      A _variant_t equivalent to this ubstr_t object.
762
 
 *
763
 
 * Side effects:
764
 
 *      None.
765
 
 *
766
 
 *-----------------------------------------------------------------------------
767
 
 */
768
 
 
769
 
inline
770
 
ubstr_t::operator _variant_t()
771
 
   const
772
 
{
773
 
   return static_cast<const wchar_t *>(mBstr);
774
 
}
775
 
 
776
 
 
777
 
/*
778
 
 *-----------------------------------------------------------------------------
779
 
 *
780
 
 * ubstr_t::swap --
781
 
 *
782
 
 *      Swaps this ubstr_t object with another.
783
 
 *
784
 
 * Results:
785
 
 *      None.
786
 
 *
787
 
 * Side effects:
788
 
 *      None.
789
 
 *
790
 
 *-----------------------------------------------------------------------------
791
 
 */
792
 
 
793
 
inline void
794
 
ubstr_t::swap(ubstr_t& s) // IN/OUT
795
 
{
796
 
   std::swap(mBstr, s.mBstr);
797
 
   mUTF8.swap(s.mUTF8);
798
 
}
799
 
 
800
 
 
801
 
/*
802
 
 *-----------------------------------------------------------------------------
803
 
 *
804
 
 * ubstr_t::GetUTF8Cache --
805
 
 *
806
 
 *      Retrieves the UTF-8 cache, initializing it if necessary.
807
 
 *
808
 
 * Results:
809
 
 *      The cached UTF-8 string.
810
 
 *
811
 
 * Side effects:
812
 
 *      None.
813
 
 *
814
 
 *-----------------------------------------------------------------------------
815
 
 */
816
 
 
817
 
inline char *
818
 
ubstr_t::GetUTF8Cache()
819
 
   const
820
 
{
821
 
   if (static_cast<wchar_t *>(mBstr) == NULL) {
822
 
      // Nothing to do.
823
 
      return NULL;
824
 
   }
825
 
 
826
 
   char *utf8Str = NULL;
827
 
   try {
828
 
      if (!mUTF8) {
829
 
         mUTF8 = Glib::RefPtr<UTF8Data>(new UTF8Data());
830
 
      }
831
 
 
832
 
      if (mUTF8->Get() == NULL) {
833
 
         utf8Str = Unicode_AllocWithUTF16(static_cast<wchar_t *>(mBstr));
834
 
         mUTF8->Set(utf8Str);
835
 
      }
836
 
   } catch (...) {
837
 
      free(utf8Str);
838
 
      throw;
839
 
   }
840
 
 
841
 
   return mUTF8->Get();
842
 
}
843
 
 
844
 
 
845
 
/*
846
 
 *-----------------------------------------------------------------------------
847
 
 *
848
 
 * ubstr_t::InvalidateCache --
849
 
 *
850
 
 *      Clears the UTF-8 cache.
851
 
 *
852
 
 * Results:
853
 
 *      None.
854
 
 *
855
 
 * Side effects:
856
 
 *      None.
857
 
 *
858
 
 *-----------------------------------------------------------------------------
859
 
 */
860
 
 
861
 
inline void
862
 
ubstr_t::InvalidateCache()
863
 
{
864
 
   mUTF8.clear();
865
 
}
866
 
 
867
 
 
868
 
/*
869
 
 *-----------------------------------------------------------------------------
870
 
 *
871
 
 * operator+ --
872
 
 *
873
 
 *      Non-member concatenation operators.
874
 
 *
875
 
 * Results:
876
 
 *      A copy of the concatenated string.
877
 
 *
878
 
 * Side effects:
879
 
 *      None.
880
 
 *
881
 
 *-----------------------------------------------------------------------------
882
 
 */
883
 
 
884
 
inline ubstr_t
885
 
operator+(const char *s1,    // IN: A UTF-8-encoded sting.
886
 
          const ubstr_t& s2) // IN
887
 
{
888
 
   return ubstr_t(s1) + s2;
889
 
}
890
 
 
891
 
 
892
 
inline ubstr_t
893
 
operator+(const wchar_t *s1, // IN
894
 
          const ubstr_t& s2) // IN
895
 
{
896
 
   return ubstr_t(s1) + s2;
897
 
}
898
 
 
899
 
 
900
 
/*
901
 
 * These are not part of the _bstr_t interface but are provided to catch
902
 
 * misuse.  They are intentionally unimplemented to avoid a maintenance
903
 
 * burden, and they intentionally return nothing so that accidental usage
904
 
 * normally results in compile-time errors instead of link-time ones.
905
 
 */
906
 
 
907
 
void operator==(const char *s1, const ubstr_t& s2);
908
 
void operator!=(const char *s1, const ubstr_t& s2);
909
 
void operator<(const char *s1, const ubstr_t& s2);
910
 
void operator>(const char *s1, const ubstr_t& s2);
911
 
void operator<=(const char *s1, const ubstr_t& s2);
912
 
void operator>=(const char *s1, const ubstr_t& s2);
913
 
 
914
 
void operator==(const WCHAR *s1, const ubstr_t& s2);
915
 
void operator!=(const WCHAR *s1, const ubstr_t& s2);
916
 
void operator<(const WCHAR *s1, const ubstr_t& s2);
917
 
void operator>(const WCHAR *s1, const ubstr_t& s2);
918
 
void operator<=(const WCHAR *s1, const ubstr_t& s2);
919
 
void operator>=(const WCHAR *s1, const ubstr_t& s2);
920
 
 
921
 
 
922
 
#endif // I_LOVE_BSTR_T_CLASSIC