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.

407 lines
9.8 KiB

  1. //+---------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1992 - 1998.
  5. //
  6. // File: mmstrm.hxx
  7. //
  8. // Contents: Memory Mapped Stream
  9. //
  10. // Classes: CMmStream, CMmStreamBuf
  11. //
  12. // History: 10-Mar-93 BartoszM Created
  13. //
  14. //----------------------------------------------------------------------------
  15. #pragma once
  16. #include <pmmstrm.hxx>
  17. #include <driveinf.hxx>
  18. //+---------------------------------------------------------------------------
  19. //
  20. // Class: CMmStream
  21. //
  22. // Purpose: Memory Mapped Stream
  23. //
  24. // History: 10-Mar-93 BartoszM Created
  25. // 18-Mar-98 KitmanH Added a protected member
  26. // _fIsReadOnly
  27. // 26-Oct-98 KLam Added _cMegToLeaveOnDisk
  28. // Added CDriveInfo smart pointer
  29. //
  30. //----------------------------------------------------------------------------
  31. class CMmStream: public PMmStream
  32. {
  33. friend class CMmStreamBuf;
  34. friend class CDupStream;
  35. public:
  36. CMmStream( ULONG cbDiskSpaceToLeave = CI_MIN_DISK_SPACE_TO_LEAVE_DEFAULT,
  37. BOOL fIsReadOnly = FALSE );
  38. BOOL Ok() { return _hFile != INVALID_HANDLE_VALUE; }
  39. virtual ~CMmStream();
  40. void OpenExclusive ( WCHAR* wcsPath, BOOL fReadOnly);
  41. void Open ( const WCHAR* wcsPath,
  42. ULONG modeAccess,
  43. ULONG modeShare,
  44. ULONG modeCreate,
  45. ULONG modeAttribute = FILE_ATTRIBUTE_NORMAL,
  46. BOOL fSparse = FALSE );
  47. void Close();
  48. void SetSize ( PStorage& storage,
  49. ULONG newSizeLow,
  50. ULONG newSizeHigh=0 );
  51. BOOL isEmpty() { return _sizeHigh == 0 && _sizeLow == 0; }
  52. ULONG SizeLow() { return _sizeLow; }
  53. ULONG SizeHigh() { return _sizeHigh; }
  54. LONGLONG Size()
  55. {
  56. return llfromuls( _sizeLow, _sizeHigh );
  57. }
  58. BOOL isWritable() { return _fWrite; }
  59. void MapAll ( CMmStreamBuf& sbuf );
  60. void Map ( CMmStreamBuf& sbuf,
  61. ULONG cb = 0,
  62. ULONG offLow = 0,
  63. ULONG offHigh = 0,
  64. BOOL fMapForWrite = FALSE );
  65. void Unmap ( CMmStreamBuf& sbuf );
  66. void Flush ( CMmStreamBuf& sbuf, ULONG cb, BOOL fThrowOnFailure = TRUE );
  67. void FlushMetaData( BOOL fThrowOnFailure = TRUE );
  68. BOOL FStatusFileNotFound()
  69. {
  70. return _status == STATUS_OBJECT_NAME_NOT_FOUND
  71. || _status == STATUS_OBJECT_PATH_NOT_FOUND;
  72. }
  73. NTSTATUS GetStatus() const { return _status; }
  74. ULONG ShrinkFromFront( ULONG firstPage, ULONG numPages );
  75. #if CIDBG == 1
  76. WCHAR const * GetPath() { return _xwcPath.Get(); }
  77. #endif
  78. void InitFIsReadOnly( BOOL fIsReadOnly ) { _fIsReadOnly = fIsReadOnly; }
  79. void Read( void * pvBuffer, ULONGLONG oStart, DWORD cbToRead, DWORD & cbRead );
  80. void Write( void * pvBuffer, ULONGLONG oStart, DWORD cbToWrite );
  81. protected:
  82. HANDLE _hFile;
  83. HANDLE _hMap;
  84. ULONG _sizeLow;
  85. ULONG _sizeHigh;
  86. BOOL _fWrite;
  87. BOOL _fSparse;
  88. NTSTATUS _status;
  89. unsigned _cMap;
  90. BOOL _fIsReadOnly;
  91. ULONG _cMegToLeaveOnDisk;
  92. XPtr<CDriveInfo> _xDriveInfo;
  93. #if CIDBG == 1
  94. XGrowable<WCHAR> _xwcPath;
  95. #endif // CIDBG == 1
  96. };
  97. //+---------------------------------------------------------------------------
  98. //
  99. // Class: CLockingMmStream
  100. //
  101. // Purpose: Memory Mapped Stream with reader/writer locking
  102. //
  103. // History: 13-Nov-97 dlee Created
  104. // 27-Oct-98 KLam Added cbDiskSpaceToLeave
  105. //
  106. //----------------------------------------------------------------------------
  107. class CLockingMmStream: public PMmStream
  108. {
  109. public:
  110. CLockingMmStream( ULONG cbDiskSpaceToLeave )
  111. : _cRef( 0 ),
  112. _mmStream( cbDiskSpaceToLeave )
  113. {}
  114. ~CLockingMmStream()
  115. {
  116. Win4Assert( 0 == _cRef );
  117. CWriteAccess lock( _rwLock );
  118. }
  119. void Open ( const WCHAR* wcsPath,
  120. ULONG modeAccess,
  121. ULONG modeShare,
  122. ULONG modeCreate,
  123. ULONG modeAttribute = FILE_ATTRIBUTE_NORMAL,
  124. BOOL fSparse = FALSE )
  125. {
  126. CWriteAccess lock( _rwLock );
  127. _mmStream.Open( wcsPath, modeAccess, modeShare, modeCreate,
  128. modeAttribute, fSparse );
  129. }
  130. BOOL Ok() { return _mmStream.Ok(); }
  131. void Close()
  132. {
  133. CWriteAccess lock( _rwLock );
  134. Win4Assert( 0 == _cRef );
  135. _mmStream.Close();
  136. }
  137. void SetSize ( PStorage & storage,
  138. ULONG newSizeLow,
  139. ULONG newSizeHigh=0 )
  140. {
  141. CWriteAccess lock( _rwLock );
  142. _mmStream.SetSize( storage, newSizeLow, newSizeHigh );
  143. }
  144. BOOL isEmpty()
  145. {
  146. CReadAccess lock( _rwLock );
  147. return _mmStream.isEmpty();
  148. }
  149. ULONG SizeLow()
  150. {
  151. CReadAccess lock( _rwLock );
  152. return _mmStream.SizeLow();
  153. }
  154. ULONG SizeHigh()
  155. {
  156. CReadAccess lock( _rwLock );
  157. return _mmStream.SizeHigh();
  158. }
  159. LONGLONG Size()
  160. {
  161. return _mmStream.Size();
  162. }
  163. BOOL isWritable()
  164. {
  165. CReadAccess lock( _rwLock );
  166. return _mmStream.isWritable();
  167. }
  168. void MapAll ( CMmStreamBuf& sbuf )
  169. {
  170. CWriteAccess lock( _rwLock );
  171. _mmStream.MapAll( sbuf );
  172. }
  173. void Map ( CMmStreamBuf& sbuf,
  174. ULONG cb = 0,
  175. ULONG offLow = 0,
  176. ULONG offHigh = 0,
  177. BOOL fMapForWrite = FALSE )
  178. {
  179. CWriteAccess lock( _rwLock );
  180. _mmStream.Map( sbuf, cb, offLow, offHigh, fMapForWrite );
  181. }
  182. void Unmap ( CMmStreamBuf& sbuf )
  183. {
  184. CReadAccess lock( _rwLock );
  185. _mmStream.Unmap( sbuf );
  186. }
  187. void Flush ( CMmStreamBuf& sbuf, ULONG cb, BOOL fThrowOnFailure = TRUE )
  188. {
  189. CReadAccess lock( _rwLock );
  190. _mmStream.Flush( sbuf, cb, fThrowOnFailure );
  191. }
  192. void FlushMetaData( BOOL fThrowOnFailure = TRUE )
  193. {
  194. CReadAccess lock( _rwLock );
  195. _mmStream.FlushMetaData( fThrowOnFailure );
  196. }
  197. ULONG ShrinkFromFront( ULONG firstPage, ULONG numPages )
  198. {
  199. CWriteAccess lock( _rwLock );
  200. return _mmStream.ShrinkFromFront( firstPage, numPages );
  201. }
  202. #if CIDBG == 1
  203. WCHAR const * GetPath() { return _mmStream.GetPath(); }
  204. #endif
  205. void RefCount( CDupStream * p ) { _cRef++; }
  206. void UnRefCount( CDupStream * p ) { _cRef--; }
  207. void Read( void * pvBuffer, ULONGLONG oStart, DWORD cbToRead, DWORD & cbRead )
  208. {
  209. CWriteAccess lock( _rwLock );
  210. _mmStream.Read( pvBuffer, oStart, cbToRead, cbRead );
  211. }
  212. void Write( void * pvBuffer, ULONGLONG oStart, DWORD cbToWrite )
  213. {
  214. CWriteAccess lock( _rwLock );
  215. _mmStream.Write( pvBuffer, oStart, cbToWrite );
  216. }
  217. private:
  218. unsigned _cRef;
  219. CReadWriteAccess _rwLock;
  220. CMmStream _mmStream;
  221. };
  222. //+---------------------------------------------------------------------------
  223. //
  224. // Class: CDupMmStream
  225. //
  226. // Purpose: Duplicates an existing stream, so multiple storages can
  227. // share 1 stream.
  228. //
  229. // History: 13-Nov-97 dlee Created
  230. //
  231. //----------------------------------------------------------------------------
  232. class CDupStream: public PMmStream
  233. {
  234. public:
  235. CDupStream( CLockingMmStream & mmStream ) : _mmStream(mmStream)
  236. {
  237. _mmStream.RefCount( this );
  238. }
  239. ~CDupStream()
  240. {
  241. _mmStream.UnRefCount( this );
  242. }
  243. BOOL Ok() { return _mmStream.Ok(); }
  244. void Close()
  245. {
  246. Win4Assert( !"Must Not Be Called" );
  247. }
  248. void SetSize ( PStorage& storage,
  249. ULONG newSizeLow,
  250. ULONG newSizeHigh=0 )
  251. {
  252. _mmStream.SetSize( storage, newSizeLow, newSizeHigh );
  253. }
  254. BOOL isEmpty()
  255. {
  256. return _mmStream.isEmpty();
  257. }
  258. ULONG SizeLow()
  259. {
  260. return _mmStream.SizeLow();
  261. }
  262. ULONG SizeHigh()
  263. {
  264. return _mmStream.SizeHigh();
  265. }
  266. LONGLONG Size()
  267. {
  268. return llfromuls( _mmStream.SizeLow(), _mmStream.SizeHigh() );
  269. }
  270. BOOL isWritable()
  271. {
  272. return _mmStream.isWritable();
  273. }
  274. void MapAll ( CMmStreamBuf& sbuf )
  275. {
  276. _mmStream.MapAll( sbuf );
  277. }
  278. void Map ( CMmStreamBuf& sbuf,
  279. ULONG cb = 0,
  280. ULONG offLow = 0,
  281. ULONG offHigh = 0,
  282. BOOL fMapForWrite = FALSE )
  283. {
  284. _mmStream.Map( sbuf, cb, offLow, offHigh, fMapForWrite );
  285. }
  286. void Unmap ( CMmStreamBuf& sbuf )
  287. {
  288. _mmStream.Unmap( sbuf );
  289. }
  290. void Flush ( CMmStreamBuf& sbuf, ULONG cb, BOOL fThrowOnFailure = TRUE )
  291. {
  292. _mmStream.Flush( sbuf, cb, fThrowOnFailure );
  293. }
  294. void FlushMetaData ( BOOL fThrowOnFailure = TRUE )
  295. {
  296. _mmStream.FlushMetaData( fThrowOnFailure );
  297. }
  298. ULONG ShrinkFromFront( ULONG firstPage, ULONG numPages )
  299. {
  300. Win4Assert( "!Must not be called" );
  301. return(0);
  302. }
  303. PMmStream * DupStream()
  304. {
  305. Win4Assert( !"Must not be called" );
  306. return(0);
  307. }
  308. void Read( void * pvBuffer, ULONGLONG oStart, DWORD cbToRead, DWORD & cbRead )
  309. {
  310. _mmStream.Read( pvBuffer, oStart, cbToRead, cbRead );
  311. }
  312. void Write( void * pvBuffer, ULONGLONG oStart, DWORD cbToWrite )
  313. {
  314. _mmStream.Write( pvBuffer, oStart, cbToWrite );
  315. }
  316. #if CIDBG == 1
  317. WCHAR const * GetPath() { return _mmStream.GetPath(); }
  318. #endif
  319. private:
  320. CLockingMmStream & _mmStream;
  321. };