Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

165 lines
5.5 KiB

  1. //=--------------------------------------------------------------------------=
  2. // Unknown.H
  3. //=--------------------------------------------------------------------------=
  4. // Copyright 1995-1996 Microsoft Corporation. All Rights Reserved.
  5. //
  6. // THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
  7. // ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
  8. // THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
  9. // PARTICULAR PURPOSE.
  10. //=--------------------------------------------------------------------------=
  11. //
  12. // a class definition for an IUnknown super-class that will support
  13. // aggregation.
  14. //
  15. #ifndef _UNKNOWN_H_
  16. //=--------------------------------------------------------------------------=
  17. // UNKNOWNOBJECTINFO
  18. //
  19. // if you want a simple co-creatable object, with no other guarantees about
  20. // it, then you need to put the following entry in the global table of objects.
  21. // other object types that are more complex, such as automation objects, and
  22. // controls, will also use this information...
  23. //
  24. typedef struct {
  25. const CLSID *rclsid; // CLSID of your object. ONLY USE IF YOU'RE CoCreatable!
  26. LPCSTR pszObjectName; // Name of your object. ONLY USE IF YOU'RE CoCreatable!
  27. IUnknown *(*pfnCreate)(IUnknown *); // pointer to creation fn. ONLY USE IF YOU'RE CoCreatable!
  28. } UNKNOWNOBJECTINFO;
  29. #define NAMEOFOBJECT(index) (((UNKNOWNOBJECTINFO *)(g_ObjectInfo[(index)]).pInfo)->pszObjectName)
  30. #define CLSIDOFOBJECT(index) (*(((UNKNOWNOBJECTINFO *)(g_ObjectInfo[(index)]).pInfo)->rclsid))
  31. #define CREATEFNOFOBJECT(index) (((UNKNOWNOBJECTINFO *)(g_ObjectInfo[(index)]).pInfo)->pfnCreate)
  32. #ifndef INITOBJECTS
  33. #define DEFINE_UNKNOWNOBJECT(name, clsid, objname, fn) \
  34. extern UNKNOWNOBJECTINFO name##Object \
  35. #else
  36. #define DEFINE_UNKNOWNOBJECT(name, clsid, objname, fn) \
  37. UNKNOWNOBJECTINFO name##Object = { clsid, objname, fn } \
  38. #endif // INITOBJECTS
  39. //=--------------------------------------------------------------------------=
  40. // DECLARE_STANDARD_UNKNOWN
  41. //
  42. // All objects that are going to inherit from CUnknown for their IUnknown
  43. // implementation should put this in their class declaration instead of the
  44. // three IUnknown methods.
  45. //
  46. #define DECLARE_STANDARD_UNKNOWN() \
  47. STDMETHOD(QueryInterface)(REFIID riid, void **ppvObjOut) { \
  48. return ExternalQueryInterface(riid, ppvObjOut); \
  49. } \
  50. STDMETHOD_(ULONG, AddRef)(void) { \
  51. return ExternalAddRef(); \
  52. } \
  53. STDMETHOD_(ULONG, Release)(void) { \
  54. return ExternalRelease(); \
  55. } \
  56. // global variable where we store the current lock count on our DLL. This resides
  57. // in InProcServer.Cpp
  58. //
  59. extern LONG g_cLocks;
  60. //=--------------------------------------------------------------------------=
  61. // this class doesn't inherit from IUnknown since people inheriting from it
  62. // are going to do so, and just delegate their IUnknown calls to the External*
  63. // member functions on this object. the internal private unknown object does
  64. // need to inherit from IUnknown, since it will be used directly as an IUnknown
  65. // object.
  66. //
  67. class CUnknownObject {
  68. public:
  69. CUnknownObject(IUnknown *pUnkOuter, void *pvInterface)
  70. : m_pvInterface(pvInterface),
  71. m_pUnkOuter((pUnkOuter) ? pUnkOuter : &m_UnkPrivate)
  72. { InterlockedIncrement(&g_cLocks); }
  73. virtual ~CUnknownObject() {
  74. #if DBG==1
  75. if ( 0 != g_cLocks )
  76. {
  77. DebugBreak();
  78. }
  79. #endif
  80. InterlockedDecrement(&g_cLocks);
  81. }
  82. // these are all protected so that classes that inherit from this can
  83. // at get at them.
  84. //
  85. protected:
  86. // IUnknown methods. these just delegate to the controlling
  87. // unknown.
  88. //
  89. HRESULT ExternalQueryInterface(REFIID riid, void **ppvObjOut) {
  90. return m_pUnkOuter->QueryInterface(riid, ppvObjOut);
  91. }
  92. ULONG ExternalAddRef(void) {
  93. return m_pUnkOuter->AddRef();
  94. }
  95. ULONG ExternalRelease(void) {
  96. return m_pUnkOuter->Release();
  97. }
  98. // people should use this during creation to return their private
  99. // unknown
  100. //
  101. inline IUnknown *PrivateUnknown (void) {
  102. return &m_UnkPrivate;
  103. }
  104. virtual HRESULT InternalQueryInterface(REFIID riid, void **ppvObjOut);
  105. IUnknown *m_pUnkOuter; // outer controlling Unknown
  106. void *m_pvInterface; // the real interface we're working with.
  107. private:
  108. // the inner, private unknown implementation is for the aggregator
  109. // to control the lifetime of this object, and for those cases where
  110. // this object isn't aggregated.
  111. //
  112. class CPrivateUnknownObject : public IUnknown {
  113. public:
  114. STDMETHOD(QueryInterface)(REFIID riid, void **ppvObjOut);
  115. STDMETHOD_(ULONG, AddRef)(void);
  116. STDMETHOD_(ULONG, Release)(void);
  117. // constructor is remarkably trivial
  118. //
  119. CPrivateUnknownObject() : m_cRef(1) {}
  120. private:
  121. CUnknownObject *m_pMainUnknown();
  122. ULONG m_cRef;
  123. } m_UnkPrivate;
  124. // so they can reference themselves in CUnknownObject from pMainUnknown()
  125. //
  126. friend class CPrivateUnknownObject;
  127. // by overriding this, people inheriting from this unknown can implement
  128. // additional interfaces. declared as private here so they have to use their
  129. // own version.
  130. //
  131. };
  132. #define _UNKNOWN_H_
  133. #endif // _UNKNOWN_H_
  134.