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.

421 lines
9.6 KiB

  1. //+-------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1992 - 1994
  5. //
  6. // File: keylist.hxx
  7. //
  8. // Contents:
  9. //
  10. // History: 17-Feb-1994 KyleP Created
  11. //
  12. //--------------------------------------------------------------------------
  13. #pragma once
  14. #include "partn.hxx"
  15. #include "sort.hxx"
  16. #include "pindex.hxx"
  17. #include "pcomp.hxx"
  18. class CKeyComp;
  19. class CKeyDeComp;
  20. class CRKeyHash;
  21. #ifdef KEYLIST_ENABLED
  22. //+---------------------------------------------------------------------------
  23. //
  24. // Class: CKeyList (wl)
  25. //
  26. // Purpose: Convert between key id and key. Enumeration of keys later
  27. //
  28. // History: 29-Oct-93 w-PatG Created.
  29. // 17-Feb-94 KyleP Initial version
  30. //
  31. // Notes: The keylist is composed of three main parts: a directory,
  32. // a [content] index, and a hash table. The index is a
  33. // minimal version of the standard content index. No wid or
  34. // occurrence information is stored and property ids are treated
  35. // as key ids. maxWid is treated as maxKeyId. New key ids
  36. // are allocated sequentially.
  37. //
  38. //----------------------------------------------------------------------------
  39. const LONGLONG eSigKeyList = 0x205453494c59454bi64; // "KEYLIST"
  40. class CKeyList : public CIndex
  41. {
  42. DECLARE_UNWIND
  43. public:
  44. CKeyList();
  45. CKeyList( PStorage & storage,
  46. WORKID objectId,
  47. INDEXID iid,
  48. KEYID kidMax );
  49. //
  50. // From CIndex
  51. //
  52. virtual ~CKeyList();
  53. virtual unsigned Size () const;
  54. virtual void Remove();
  55. virtual CKeyCursor * QueryCursor();
  56. //
  57. // From CQueriable
  58. //
  59. virtual COccCursor * QueryCursor( const CKey * pkey,
  60. BOOL isRange,
  61. ULONG & cMaxNodes );
  62. virtual COccCursor * QueryRangeCursor( const CKey * pkeyBegin,
  63. const CKey * pkeyEnd,
  64. ULONG & cMaxNodes );
  65. virtual COccCursor * QuerySynCursor( CKeyArray & keyArr,
  66. BOOL isRange,
  67. ULONG & cMaxNodes );
  68. //
  69. // Bookeeping functions
  70. //
  71. WORKID ObjectId() const { return _pPhysIndex->ObjectId(); }
  72. INDEXID GetNextIid ();
  73. ULONG MaxKeyIdInUse() const { return _widMax; }
  74. void FillRecord( CIndexRecord& record ) const;
  75. //
  76. // Translation
  77. //
  78. KEYID KeyToId( const CKey * pkey );
  79. BOOL IdToKey( KEYID ulKid, CKey & rkey );
  80. protected:
  81. inline CKeyList ( PStorage & storage, WORKID objectid,
  82. INDEXID id, WORKID widMax, int dummy );
  83. void Close();
  84. const LONGLONG _sigKeyList;
  85. PStorage * const _pstorage;
  86. CPhysIndex * _pPhysIndex;
  87. CPhysHash * _pPhysHash;
  88. PDirectory * _pDir;
  89. SStorageObject _obj;
  90. };
  91. //+---------------------------------------------------------------------------
  92. //
  93. // Class: CWKeyList (wl)
  94. //
  95. // Purpose: Writeable version of keylist
  96. //
  97. // History: 17-Feb-94 KyleP Initial version
  98. //
  99. //----------------------------------------------------------------------------
  100. const LONGLONG eSigWKeyList = 0x5453494c59454b57i64; // "WKEYLIST"
  101. class CWKeyList : public CKeyList
  102. {
  103. DECLARE_UNWIND
  104. public:
  105. CWKeyList( PStorage & storage,
  106. WORKID objectid,
  107. INDEXID iid,
  108. unsigned size,
  109. CKeyList * pOldKeyList );
  110. CWKeyList( PStorage & storage,
  111. WORKID objectid,
  112. INDEXID iid,
  113. CKeyList * pOldKeyList,
  114. CKeyBuf & splitKey,
  115. WORKID widMax
  116. );
  117. virtual ~CWKeyList();
  118. KEYID PutKey( CKeyBuf const * pkey, BitOffset & bitOff );
  119. void Flush() { _pPhysIndex->Flush(); }
  120. void Done( BOOL & fAbort );
  121. private:
  122. inline int Compare( CKeyBuf const * pk1, CKeyBuf const * pk2 );
  123. void BuildHash( BOOL & fAbort );
  124. ULONG GetKeyId() { return ++_widMax; }
  125. void RestoreDirectory( CKeyBuf & splitKey,
  126. BitOffset & beginBitOff,
  127. BitOffset & endBitOff
  128. );
  129. const LONGLONG _sigWKeyList; //
  130. CKeyCursor * _pOldKeyCursor;
  131. CKeyComp * _pKeyComp; // Key compressor
  132. ULONG _ulPage; // Last page written to directory
  133. CKeyBuf _keyLast; // Last key written.
  134. };
  135. //+-------------------------------------------------------------------------
  136. //
  137. // Method: CKeyList::CKeyList
  138. //
  139. // Synopsis: Ctor for derived classes. Only initializes CIndex
  140. //
  141. // Arguments: [id] -- Index id
  142. // [widMax] -- Max workid (keyid)
  143. //
  144. // Returns:
  145. //
  146. // History: 17-Feb-1994 KyleP Created
  147. //
  148. //--------------------------------------------------------------------------
  149. inline CKeyList::CKeyList ( PStorage & storage, WORKID objectId,
  150. INDEXID id, WORKID widMax, int )
  151. : CIndex( id, widMax, FALSE ),
  152. _sigKeyList(eSigKeyList),
  153. _pstorage ( &storage ),
  154. _pDir (0),
  155. _pPhysIndex(0),
  156. _pPhysHash(0),
  157. _obj ( storage.QueryObject(objectId) )
  158. {
  159. END_CONSTRUCTION( CKeyList );
  160. }
  161. //+-------------------------------------------------------------------------
  162. //
  163. // Method: CWKeyList::Compare
  164. //
  165. // Synopsis: Compare two keys, sans 'type byte' (first byte of key)
  166. //
  167. // Arguments: [pk1] -- First key
  168. // [pk2] -- Second key
  169. //
  170. // Returns: < 0, 0, > 0 if pk1 < pk2, pk1 == pk2, pk1 > pk2
  171. //
  172. // History: 17-Feb-1994 KyleP Created
  173. //
  174. //--------------------------------------------------------------------------
  175. inline int CWKeyList::Compare( CKeyBuf const * pk1, CKeyBuf const * pk2 )
  176. {
  177. Win4Assert( pk1 != 0 );
  178. Win4Assert( pk2 != 0 );
  179. Win4Assert( pk2->Count() > 1 );
  180. unsigned long mincb = __min(pk1->Count(), pk2->Count()-1 );
  181. int diff = memcmp( pk1->GetBuf(), pk2->GetBuf()+1, mincb);
  182. if (diff == 0)
  183. { // this->buf == key.buf
  184. diff = pk1->Count() - (pk2->Count()-1);
  185. }
  186. return(diff);
  187. }
  188. //+---------------------------------------------------------------------------
  189. //
  190. // Class: SKeyList
  191. //
  192. // Purpose: Smart Pointer to key list
  193. //
  194. // History: 28-Oct-93 w-PatG Stolen from BartoszM
  195. // 17-Feb-94 KyleP Initial version
  196. //
  197. //----------------------------------------------------------------------------
  198. class SKeyList : INHERIT_UNWIND
  199. {
  200. DECLARE_UNWIND
  201. public:
  202. SKeyList ( CKeyList * pKeyList ) : _pKeyList(pKeyList)
  203. {
  204. END_CONSTRUCTION( SKeyList );
  205. }
  206. ~SKeyList () { delete _pKeyList; }
  207. CKeyList* operator-> () { return _pKeyList; }
  208. CKeyList * Transfer()
  209. {
  210. CKeyList * temp = _pKeyList;
  211. _pKeyList = 0;
  212. return( temp );
  213. }
  214. private:
  215. CKeyList * _pKeyList;
  216. };
  217. //+--------------------------------------------------------------------------
  218. //
  219. // Class: CKeyListCursor
  220. //
  221. // Purpose: Smart pointer to a keylist key cursor
  222. //
  223. // History: 17-Jun-94 dlee Created
  224. //
  225. //---------------------------------------------------------------------------
  226. class CKeyListCursor : INHERIT_UNWIND
  227. {
  228. DECLARE_UNWIND
  229. public:
  230. CKeyListCursor(CKeyList *pKeyList) : _pCursor(0)
  231. {
  232. _pCursor = pKeyList->QueryCursor();
  233. END_CONSTRUCTION(CKeyListCursor);
  234. }
  235. ~CKeyListCursor() { delete _pCursor; }
  236. CKeyCursor* operator->() { return(_pCursor); }
  237. private:
  238. CKeyCursor *_pCursor;
  239. };
  240. #else // !KEYLIST_ENABLED
  241. //+---------------------------------------------------------------------------
  242. //
  243. // Class: CKeyList
  244. //
  245. // Purpose: A simple key list that just tracks the number of keys
  246. // in the index.
  247. //
  248. // History: 3-12-96 srikants Created
  249. //
  250. // Notes:
  251. //
  252. //----------------------------------------------------------------------------
  253. class CKeyList : public CIndex
  254. {
  255. INLINE_UNWIND( CKeyList )
  256. public:
  257. CKeyList();
  258. CKeyList( KEYID kidMax, INDEXID iid );
  259. KEYID MaxKeyIdInUse() const { return MaxWorkId(); }
  260. void SetMaxKeyIdInUse( KEYID kidMax )
  261. {
  262. SetMaxWorkId( kidMax );
  263. }
  264. void AddKey()
  265. {
  266. _widMax++;
  267. }
  268. INDEXID GetNextIid ();
  269. void FillRecord( CIndexRecord& record ) const;
  270. WORKID ObjectId() const { return 0; }
  271. private:
  272. //
  273. // From CIndex
  274. //
  275. virtual unsigned Size () const { return 0; }
  276. virtual void Remove()
  277. {
  278. }
  279. virtual CKeyCursor * QueryCursor()
  280. {
  281. return 0;
  282. }
  283. //
  284. // From CQueriable
  285. //
  286. virtual COccCursor * QueryCursor( CKey const * pkey,
  287. BOOL isRange,
  288. ULONG & cMaxNodes )
  289. {
  290. return 0;
  291. }
  292. virtual COccCursor * QueryRangeCursor( const CKey * pkeyBegin,
  293. const CKey * pkeyEnd,
  294. ULONG & cMaxNodes )
  295. {
  296. return 0;
  297. }
  298. virtual COccCursor * QuerySynCursor( CKeyArray & keyArr,
  299. BOOL isRange,
  300. ULONG & cMaxNodes )
  301. {
  302. return 0;
  303. }
  304. private:
  305. int _iDummy1;
  306. };
  307. class CWKeyList : public CKeyList
  308. {
  309. INLINE_UNWIND( CWKeyList )
  310. public:
  311. CWKeyList( KEYID kidMax, INDEXID iid ) : CKeyList( kidMax, iid )
  312. {
  313. END_CONSTRUCTION( CWKeyList );
  314. }
  315. private:
  316. int _iDummy2;
  317. };
  318. #endif // !KEYLIST_ENABLED