scoped_variant.h 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. // Copyright (c) 2011 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef BASE_WIN_SCOPED_VARIANT_H_
  5. #define BASE_WIN_SCOPED_VARIANT_H_
  6. #include <windows.h>
  7. #include <oleauto.h>
  8. #include <stdint.h>
  9. #include "base/base_export.h"
  10. #include "base/macros.h"
  11. namespace base {
  12. namespace win {
  13. // Scoped VARIANT class for automatically freeing a COM VARIANT at the
  14. // end of a scope. Additionally provides a few functions to make the
  15. // encapsulated VARIANT easier to use.
  16. // Instead of inheriting from VARIANT, we take the containment approach
  17. // in order to have more control over the usage of the variant and guard
  18. // against memory leaks.
  19. class BASE_EXPORT ScopedVariant {
  20. public:
  21. // Declaration of a global variant variable that's always VT_EMPTY
  22. static const VARIANT kEmptyVariant;
  23. // Default constructor.
  24. ScopedVariant() {
  25. // This is equivalent to what VariantInit does, but less code.
  26. var_.vt = VT_EMPTY;
  27. }
  28. // Constructor to create a new VT_BSTR VARIANT.
  29. // NOTE: Do not pass a BSTR to this constructor expecting ownership to
  30. // be transferred
  31. explicit ScopedVariant(const wchar_t* str);
  32. // Creates a new VT_BSTR variant of a specified length.
  33. ScopedVariant(const wchar_t* str, UINT length);
  34. // Creates a new integral type variant and assigns the value to
  35. // VARIANT.lVal (32 bit sized field).
  36. explicit ScopedVariant(long value, VARTYPE vt = VT_I4);
  37. // Creates a new integral type variant for the int type and assigns the value
  38. // to VARIANT.lVal (32 bit sized field).
  39. explicit ScopedVariant(int value);
  40. // Creates a new boolean (VT_BOOL) variant and assigns the value to
  41. // VARIANT.boolVal.
  42. explicit ScopedVariant(bool value);
  43. // Creates a new double-precision type variant. |vt| must be either VT_R8
  44. // or VT_DATE.
  45. explicit ScopedVariant(double value, VARTYPE vt = VT_R8);
  46. // VT_DISPATCH
  47. explicit ScopedVariant(IDispatch* dispatch);
  48. // VT_UNKNOWN
  49. explicit ScopedVariant(IUnknown* unknown);
  50. // SAFEARRAY
  51. explicit ScopedVariant(SAFEARRAY* safearray);
  52. // Copies the variant.
  53. explicit ScopedVariant(const VARIANT& var);
  54. // Moves the wrapped variant into another ScopedVariant.
  55. ScopedVariant(ScopedVariant&& var);
  56. ~ScopedVariant();
  57. inline VARTYPE type() const { return var_.vt; }
  58. // Give ScopedVariant ownership over an already allocated VARIANT.
  59. void Reset(const VARIANT& var = kEmptyVariant);
  60. // Releases ownership of the VARIANT to the caller.
  61. VARIANT Release();
  62. // Swap two ScopedVariant's.
  63. void Swap(ScopedVariant& var);
  64. // Returns a copy of the variant.
  65. VARIANT Copy() const;
  66. // The return value is 0 if the variants are equal, 1 if this object is
  67. // greater than |other|, -1 if it is smaller.
  68. // Comparison with an array VARIANT is not supported.
  69. // 1. VT_NULL and VT_EMPTY is always considered less-than any other VARTYPE.
  70. // 2. If both VARIANTS have either VT_UNKNOWN or VT_DISPATCH even if the
  71. // VARTYPEs do not match, the address of its IID_IUnknown is compared to
  72. // guarantee a logical ordering even though it is not a meaningful order.
  73. // e.g. (a.Compare(b) != b.Compare(a)) unless (a == b).
  74. // 3. If the VARTYPEs do not match, then the value of the VARTYPE is compared.
  75. // 4. Comparing VT_BSTR values is a lexicographical comparison of the contents
  76. // of the BSTR, taking into account |ignore_case|.
  77. // 5. Otherwise returns the lexicographical comparison of the values held by
  78. // the two VARIANTS that share the same VARTYPE.
  79. int Compare(const VARIANT& other, bool ignore_case = false) const;
  80. // Retrieves the pointer address.
  81. // Used to receive a VARIANT as an out argument (and take ownership).
  82. // The function DCHECKs on the current value being empty/null.
  83. // Usage: GetVariant(var.receive());
  84. VARIANT* Receive();
  85. void Set(const wchar_t* str);
  86. // Setters for simple types.
  87. void Set(int8_t i8);
  88. void Set(uint8_t ui8);
  89. void Set(int16_t i16);
  90. void Set(uint16_t ui16);
  91. void Set(int32_t i32);
  92. void Set(uint32_t ui32);
  93. void Set(int64_t i64);
  94. void Set(uint64_t ui64);
  95. void Set(float r32);
  96. void Set(double r64);
  97. void Set(bool b);
  98. // Creates a copy of |var| and assigns as this instance's value.
  99. // Note that this is different from the Reset() method that's used to
  100. // free the current value and assume ownership.
  101. void Set(const VARIANT& var);
  102. // COM object setters
  103. void Set(IDispatch* disp);
  104. void Set(IUnknown* unk);
  105. // SAFEARRAY support
  106. void Set(SAFEARRAY* array);
  107. // Special setter for DATE since DATE is a double and we already have
  108. // a setter for double.
  109. void SetDate(DATE date);
  110. // Allows const access to the contained variant without DCHECKs etc.
  111. // This support is necessary for the V_XYZ (e.g. V_BSTR) set of macros to
  112. // work properly but still doesn't allow modifications since we want control
  113. // over that.
  114. const VARIANT* ptr() const { return &var_; }
  115. // Moves the ScopedVariant to another instance.
  116. ScopedVariant& operator=(ScopedVariant&& var);
  117. // Like other scoped classes (e.g. scoped_refptr, ScopedBstr,
  118. // Microsoft::WRL::ComPtr) we support the assignment operator for the type we
  119. // wrap.
  120. ScopedVariant& operator=(const VARIANT& var);
  121. // A hack to pass a pointer to the variant where the accepting
  122. // function treats the variant as an input-only, read-only value
  123. // but the function prototype requires a non const variant pointer.
  124. // There's no DCHECK or anything here. Callers must know what they're doing.
  125. VARIANT* AsInput() const {
  126. // The nature of this function is const, so we declare
  127. // it as such and cast away the constness here.
  128. return const_cast<VARIANT*>(&var_);
  129. }
  130. // Allows the ScopedVariant instance to be passed to functions either by value
  131. // or by const reference.
  132. operator const VARIANT&() const { return var_; }
  133. // Used as a debug check to see if we're leaking anything.
  134. static bool IsLeakableVarType(VARTYPE vt);
  135. protected:
  136. VARIANT var_;
  137. private:
  138. // Comparison operators for ScopedVariant are not supported at this point.
  139. // Use the Compare method instead.
  140. bool operator==(const ScopedVariant& var) const;
  141. bool operator!=(const ScopedVariant& var) const;
  142. DISALLOW_COPY_AND_ASSIGN(ScopedVariant);
  143. };
  144. } // namespace win
  145. } // namespace base
  146. #endif // BASE_WIN_SCOPED_VARIANT_H_