Source code of Windows XP (NT5)
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.

259 lines
9.6 KiB

  1. ///////////////////////////////////////////////////////////////////////////////////
  2. //
  3. // Microsoft WMIOLE DB Provider
  4. // (C) Copyright 1999 Microsoft Corporation. All Rights Reserved.
  5. //
  6. // @module CSRCROW.H | CRowset base object and contained interface
  7. //
  8. //
  9. ///////////////////////////////////////////////////////////////////////////////////
  10. #ifndef _CSRCROW_H_
  11. #define _CSRCROW_H_
  12. #include "rowset.h"
  13. typedef DWORD BOOKMARK;
  14. ///////////////////////////////////////////////////////////////////////////////////
  15. //
  16. // Rowset object for rowsets built from structures in memory.
  17. //
  18. ///////////////////////////////////////////////////////////////////////////////////
  19. class CRowsetInMem : public CRowset
  20. {
  21. public:
  22. CRowsetInMem(LPUNKNOWN pUnkOuter, LONG cCursorRowCount, PCDBSESSION p);
  23. ~CRowsetInMem();
  24. STDMETHODIMP InstantiateDataObj(void); // Instantiate Utility Objects which provided data retrieval related methods.
  25. STDMETHODIMP GetRowsIntoInternalBuffer( ULONG cRows, ULONG *pcRowsObtained, PROWBUFF rgrowbuff );
  26. inline void Restart(void){ m_iCurrentRow = 0;} // Sets the column (we examine) / row (we produce) to start with.
  27. inline void PositionToEnd(void){m_iCurrentRow = m_cRows + 1;} // Positions to the end of the rowset
  28. inline HRESULT FetchByBookmark( BOOKMARK bookmark, LONG irow, DWORD *pcrow, DWORD dwRowsetSize, PROWBUFF rgrowbuff );
  29. inline HRESULT FetchRelative( LONG irow, DWORD *pcrow, DWORD dwRowsetSize, PROWBUFF rgrowbuff );
  30. inline HRESULT GetPosition( BOOKMARK dwBookmark, ULONG *pulPosition );
  31. inline HRESULT PositionToBookmark( BOOKMARK dwBookmark ); // Position to a row in the rowset using a bookmark
  32. protected:
  33. LONG m_iCurrentRow;
  34. };
  35. ///////////////////////////////////////////////////////////////////////////////////
  36. class CColumnsRowset : public CRowsetInMem
  37. {
  38. public:
  39. CColumnsRowset( LPUNKNOWN pUnkOuter,DBCOLUMNINFO *pDBCOLUMNINFO);
  40. ~CColumnsRowset();
  41. STDMETHODIMP Init( DBCOLUMNINFO pDBCOLUMNINFO, // IN | Source row metadata
  42. ULONG cOptColumns, // IN | Count of optional columns
  43. const DBID rgOptColumns[], // IN | array of optional columns
  44. PCUTILPROP *pCRowsetProps, // IN | Rowset properties for this rowset.
  45. DWORD dwStatusFlags, // IN | flags providing additional info obtained at Execute time
  46. CQuery *pstmt, // IN | Statement Handle Node
  47. IUnknown *pParentObj, // IN | Object that instantiated the rowset
  48. CDBSession *pCDBSession, // IN | ptr to parent Session object
  49. CCommand *pcmd ); // IN | ptr to parent Command object
  50. public:
  51. enum eColumns // Enumeration for the columns This is expected to match the order of the static arrays.
  52. {
  53. ecol_IDName=1,
  54. ecol_Guid,
  55. ecol_Propid,
  56. ecol_Name,
  57. ecol_Number,
  58. ecol_Type,
  59. ecol_TypeInfo,
  60. ecol_ColumnSize,
  61. ecol_Precision,
  62. ecol_Scale,
  63. ecol_Flags,
  64. // optional columns
  65. ecol_BaseCatalogName,
  66. ecol_BaseColumnName,
  67. ecol_BaseSchemaName,
  68. ecol_BaseTableName,
  69. ecol_DateTimePrecision,
  70. ecol_IsAutoIncrement,
  71. ecol_IsCaseSensitive,
  72. ecol_IsSearchable,
  73. ecol_OctetLength,
  74. ecol_KeyColumn,
  75. ecol_NUM = ecol_KeyColumn, // Index of last element
  76. ecol_NUM_REQD = ecol_Flags, // Index of last required element
  77. ecol_NUM_OPT = ecol_KeyColumn, // Index of last optional element
  78. };
  79. inline static const DBID *GetColumnId(ULONG ecol){ return sm_rgpColumnID[ecol]; }
  80. protected:
  81. STDMETHODIMP GetRows( ULONG cRows, // IN | count of rows requested
  82. ULONG *pcRowsObtained, // OUT | count of rows obtained
  83. PROWBUFF rgrowbuff ); // IN | buffer for multiple rows
  84. private:
  85. static const DBID * sm_rgpColumnID[]; // DBIDs for all columns
  86. DWORD *m_rgEcol; // Array of eColumns for the columns we expose. It includes all required columns + only the requested optional columns.
  87. DBCOLUMNINFO m_SrcMetadata; //Row metadata that is the source for the IColumnsRowset
  88. CExtBuffer m_extSrcNamePool; //Name pool for the row metadata
  89. };
  90. //////////////////////////////////////////////////////////////////////////////////////////////////////////
  91. class CSourcesRowset : public CRowsetInMem
  92. {
  93. public:
  94. CSourcesRowset(LPUNKNOWN pUnkOuter, CGenericArray* pdynNames);
  95. ~CSourcesRowset() {}
  96. enum eColumns // Enumeration for the columns.This is expected to match the order of the static arrays.
  97. {
  98. ecol_Sources_Name=1,
  99. ecol_Sources_Parsename,
  100. ecol_Sources_Description,
  101. ecol_Type,
  102. ecol_Is_Parent,
  103. ecol_NUM = ecol_Is_Parent, // Index of last element
  104. };
  105. protected:
  106. // Get several rows into the internal buffer.
  107. STDMETHODIMP GetRows( ULONG cRows, // IN | count of rows requested
  108. ULONG *pcRowsObtained, // OUT | count of rows obtained
  109. PROWBUFF rgrowbuff // IN | buffer for multiple rows
  110. );
  111. private:
  112. typedef DWORD DBSOURCETYPE;
  113. enum DDBSOURCETYPEENUM{ DBSOURCETYPE_DATASOURCE = 1, DBSOURCETYPE_ENUMERATOR =2 };
  114. CGenericArray *m_pdynNames;
  115. CQuery *m_pstmt;
  116. };
  117. typedef CSourcesRowset *PCSOURCESROWSET;
  118. //////////////////////////////////////////////////////////////////////////////////////////////////////////
  119. class CImpISequentialStream : public ISequentialStream //@base public | ISequentialStream
  120. {
  121. private:
  122. CCriticalSection m_cs;
  123. PCROWSET m_pCRowset; // Pointer to parent rowset object.
  124. ULONG m_cRef; // Reference count
  125. DWORD m_dwStatus; // Status flags
  126. PROWBUFF m_prowbuff; // rowbuffer associated with this BLOB.
  127. HROW m_hrow; // hrow for the rowbuffer
  128. LONG m_cbLength; // Length of the BLOB data
  129. LONG m_cbRead; // # of bytes read
  130. WORD m_iColumn; // Column ordinal
  131. public:
  132. CImpISequentialStream(PCROWSET pCRowset);
  133. ~CImpISequentialStream();
  134. STDMETHODIMP FInit(DWORD dwFlags, PROWBUFF prowbuff, HROW hrow, WORD iColumn, LONG cbLength = 0);
  135. WORD WGetCol(void) const { return m_iColumn; }
  136. // Zombie out the object
  137. STDMETHODIMP_(void) MakeZombie (void);
  138. // Object's base IUnknown
  139. // Request an Interface
  140. STDMETHODIMP QueryInterface(REFIID, LPVOID *);
  141. // Increments the Reference count
  142. STDMETHODIMP_(ULONG) AddRef(void);
  143. // Decrements the Reference count
  144. STDMETHODIMP_(ULONG) Release(void);
  145. // Read Chunks
  146. STDMETHODIMP Read(void* pBuffer, ULONG cb, ULONG* pcb);
  147. // Write Chunks
  148. STDMETHODIMP Write(const void* pBuffer, ULONG cb, ULONG* pcb);
  149. };
  150. ////////////////////////////////////////////////////////////////////////////////////////////////////////////////
  151. //
  152. // Fetches the specified rowset of data from the result set and returns the cached data in row buffers.
  153. //
  154. ////////////////////////////////////////////////////////////////////////////////////////////////////////////////
  155. inline HRESULT CRowsetInMem::FetchByBookmark(BOOKMARK bookmark, // IN | bookmark
  156. LONG irow, // IN | row to fetch or bookmark
  157. DWORD *pcrow, // OUT| # rows actually fetched (optional)
  158. DWORD dwRowsetSize, // IN | size of the rowset
  159. PROWBUFF rgrowbuff ) // IN | row buffers to use (optional)
  160. {
  161. if (bookmark){
  162. // need to adjust irow
  163. irow += bookmark;
  164. if (irow < 1){
  165. dwRowsetSize = dwRowsetSize + irow - 1;
  166. if (dwRowsetSize > 0)
  167. irow = 1;
  168. else
  169. return DB_S_ENDOFROWSET;
  170. }
  171. }
  172. else{
  173. return DB_S_ENDOFROWSET;
  174. }
  175. m_iCurrentRow = irow;
  176. return GetRowsIntoInternalBuffer(dwRowsetSize, pcrow, rgrowbuff);
  177. }
  178. ////////////////////////////////////////////////////////////////////////////////////////////////////////////////
  179. inline HRESULT CRowsetInMem::FetchRelative( LONG irow, // IN | row to fetch or bookmark
  180. DWORD *pcrow, // OUT| # rows actually fetched (optional)
  181. DWORD dwRowsetSize, // IN | size of the rowset
  182. PROWBUFF rgrowbuff ) // IN | row buffers to use (optional)
  183. {
  184. if ((irow < -1 && LONG(irow+m_iCurrentRow) < 0) ||(irow > 1 && ULONG(irow+m_iCurrentRow) > ULONG(m_cRows+1)))
  185. return DB_E_BADSTARTPOSITION;
  186. m_iCurrentRow += irow;
  187. if (m_iCurrentRow < 1){
  188. dwRowsetSize = dwRowsetSize + m_iCurrentRow - 1;
  189. if (dwRowsetSize > 0)
  190. m_iCurrentRow = 1;
  191. else
  192. return DB_S_ENDOFROWSET;
  193. }
  194. return GetRowsIntoInternalBuffer(dwRowsetSize, pcrow, rgrowbuff);
  195. }
  196. ////////////////////////////////////////////////////////////////////////////////////////////////////////////////
  197. inline HRESULT CRowsetInMem::GetPosition( BOOKMARK dwBookmark, // IN | a bookmark
  198. ULONG *pulPosition ) // OUT | the bookmark's position in the rowset
  199. {
  200. if (dwBookmark == 0 || dwBookmark > BOOKMARK(m_cRows)){
  201. return DB_E_BADBOOKMARK;
  202. }
  203. *pulPosition = dwBookmark;
  204. return S_OK;
  205. }
  206. ////////////////////////////////////////////////////////////////////////////////////////////////////////////////
  207. inline HRESULT CRowsetInMem::PositionToBookmark( BOOKMARK dwBookmark )
  208. {
  209. if (dwBookmark == 0 || dwBookmark > BOOKMARK(m_cRows)){
  210. return DB_E_BADBOOKMARK;
  211. }
  212. m_iCurrentRow = dwBookmark;
  213. return S_OK;
  214. }
  215. #endif