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.

324 lines
7.8 KiB

  1. // Copyright (c) 1996-1999 Microsoft Corporation
  2. // Not currently implemented
  3. #include "pch.cxx"
  4. #pragma hdrstop
  5. #include "trkwks.hxx"
  6. #ifdef VOL_REPL
  7. void
  8. CPersistentVolumeMap::Initialize()
  9. {
  10. InitializeCriticalSection(&_cs);
  11. _fInitializeCalled = TRUE;
  12. }
  13. void
  14. CPersistentVolumeMap::UnInitialize()
  15. {
  16. if (IsOpen())
  17. CloseFile();
  18. CVolumeMap::UnInitialize();
  19. if (_fInitializeCalled)
  20. {
  21. DeleteCriticalSection(&_cs);
  22. _fInitializeCalled = FALSE;
  23. }
  24. }
  25. CFILETIME
  26. CPersistentVolumeMap::GetLastUpdateTime( )
  27. {
  28. CFILETIME cft(0);
  29. EnterCriticalSection(&_cs);
  30. __try
  31. {
  32. if (!IsOpen())
  33. {
  34. Load( );
  35. }
  36. cft = _cft;
  37. }
  38. __finally
  39. {
  40. LeaveCriticalSection(&_cs);
  41. }
  42. return(cft);
  43. }
  44. void
  45. CPersistentVolumeMap::CopyTo(DWORD * pcVolumes, VolumeMapEntry ** ppVolumeChanges)
  46. {
  47. EnterCriticalSection(&_cs);
  48. __try
  49. {
  50. if (!IsOpen())
  51. {
  52. Load( ); // BUGBUG: we may want to close this file after a period and free the map
  53. }
  54. CVolumeMap VolMap;
  55. CVolumeMap::CopyTo( &VolMap );
  56. VolMap.MoveTo( pcVolumes, ppVolumeChanges );
  57. }
  58. __finally
  59. {
  60. LeaveCriticalSection(&_cs);
  61. }
  62. }
  63. BOOL
  64. CPersistentVolumeMap::FindVolume( const CVolumeId & volume, CMachineId * pmcid )
  65. {
  66. ULONG i;
  67. EnterCriticalSection(&_cs);
  68. __try
  69. {
  70. if (!IsOpen())
  71. {
  72. Load( ); // BUGBUG: we may want to close this file after a period
  73. }
  74. for (i=0; i < _cVolumeMapEntries; i++)
  75. {
  76. if (_pVolumeMapEntries[i].volume == volume)
  77. {
  78. *pmcid = _pVolumeMapEntries[i].machine;
  79. break;
  80. }
  81. }
  82. }
  83. __finally
  84. {
  85. LeaveCriticalSection(&_cs);
  86. }
  87. return( i != _cVolumeMapEntries );
  88. }
  89. void
  90. CPersistentVolumeMap::Merge( CVolumeMap * pOther )
  91. {
  92. EnterCriticalSection(&_cs);
  93. __try
  94. {
  95. if (!IsOpen())
  96. {
  97. Load( );
  98. }
  99. _fMergeDirtiedMap |= CVolumeMap::Merge( pOther );
  100. }
  101. __finally
  102. {
  103. LeaveCriticalSection(&_cs);
  104. }
  105. }
  106. void
  107. CPersistentVolumeMap::SetLastUpdateTime( const CFILETIME & cft )
  108. {
  109. _cft = cft;
  110. Save();
  111. }
  112. // format:
  113. // DWORD Version
  114. // DWORD cVolumeMapEntries
  115. // CFILETIME time of last query on DC
  116. // VolumeMapEntry[cVolumeMapEntries]
  117. // CFILETIME time of last query on DC
  118. void
  119. CPersistentVolumeMap::Load()
  120. {
  121. TCHAR tsz[MAX_PATH+1];
  122. DWORD cch = ExpandEnvironmentStrings( TEXT("%systemroot%\\system32\\volumes.trk"),
  123. tsz,
  124. ELEMENTS(tsz) );
  125. if (cch >= ELEMENTS(tsz))
  126. {
  127. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::Load path too long")));
  128. TrkRaiseException(TRK_E_PATH_TOO_LONG);
  129. }
  130. TrkAssert(!IsOpen());
  131. RobustlyCreateFile(tsz);
  132. // after RobustlyCreateFile has succeeded without an exception we know that
  133. // OpenExistingFile has just returned OK (even after recreating the file.)
  134. TrkLog((TRKDBG_VOLMAP | TRKDBG_VOLTAB_RESTORE,
  135. TEXT("CPersistentVolumeMap::Load() - _cftFirstChange = %s"),
  136. CDebugString(_cft)._tsz));
  137. }
  138. void
  139. CPersistentVolumeMap::Save()
  140. {
  141. TrkAssert(IsOpen());
  142. DWORD Version = PVM_VERSION;
  143. DWORD cbWritten;
  144. if (0 != SetFilePointer(0, NULL, FILE_BEGIN) ||
  145. !WriteFile(&Version, sizeof(Version), &cbWritten) ||
  146. cbWritten != sizeof(Version) ||
  147. !WriteFile(&_cVolumeMapEntries, sizeof(_cVolumeMapEntries), &cbWritten) ||
  148. cbWritten != sizeof(_cVolumeMapEntries) ||
  149. // the following part of the header is read in Load()
  150. !WriteFile(&_cft, sizeof(_cft), &cbWritten) ||
  151. cbWritten != sizeof(_cft))
  152. {
  153. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::Save() failed")));
  154. TrkRaiseLastError();
  155. }
  156. if (_fMergeDirtiedMap)
  157. {
  158. TrkLog((TRKDBG_VOLMAP | TRKDBG_VOLTAB_RESTORE,
  159. TEXT("CPersistentVolumeMap::Save() - writing map data, _cftFirstChange = %s"),
  160. CDebugString(_cft)._tsz));
  161. if (!WriteFile(_pVolumeMapEntries, _cVolumeMapEntries * sizeof(VolumeMapEntry), &cbWritten) ||
  162. cbWritten != _cVolumeMapEntries * sizeof(VolumeMapEntry))
  163. {
  164. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::Save() failed 2")));
  165. TrkRaiseLastError();
  166. }
  167. }
  168. else
  169. {
  170. TrkLog((TRKDBG_VOLMAP | TRKDBG_VOLTAB_RESTORE,
  171. TEXT("CPersistentVolumeMap::Save() - seeking past map data, _cftFirstChange = %s"),
  172. CDebugString(_cft)._tsz));
  173. if (!SetFilePointer(_cVolumeMapEntries * sizeof(VolumeMapEntry), NULL, FILE_CURRENT))
  174. {
  175. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::Save() failed 3")));
  176. TrkRaiseLastError();
  177. }
  178. }
  179. if (!WriteFile(&_cft, sizeof(_cft), &cbWritten) ||
  180. cbWritten != sizeof(_cft) )
  181. {
  182. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::Save() failed 4")));
  183. TrkRaiseLastError();
  184. }
  185. _fMergeDirtiedMap = FALSE;
  186. }
  187. // BUGBUG P2: checksum, header alignment
  188. RCF_RESULT
  189. CPersistentVolumeMap::OpenExistingFile( const TCHAR * ptszFile )
  190. {
  191. RCF_RESULT r;
  192. DWORD cVolumeMapEntries;
  193. DWORD Version;
  194. NTSTATUS status;
  195. status = OpenExistingSecureFile(ptszFile);
  196. if ( NT_SUCCESS(status) )
  197. {
  198. TrkAssert(IsOpen());
  199. DWORD cbRead;
  200. r = CORRUPT;
  201. if (ReadFile(&Version, sizeof(Version), &cbRead) &&
  202. cbRead == sizeof(Version) &&
  203. Version == PVM_VERSION &&
  204. ReadFile(&cVolumeMapEntries, sizeof(cVolumeMapEntries), &cbRead) &&
  205. cbRead == sizeof(cVolumeMapEntries) &&
  206. cVolumeMapEntries < 100000 &&
  207. GetFileSize() == sizeof(Version) +
  208. sizeof(cVolumeMapEntries) +
  209. sizeof(CFILETIME) +
  210. cVolumeMapEntries * sizeof(VolumeMapEntry) +
  211. sizeof(CFILETIME) )
  212. {
  213. CFILETIME cft1, cft2;
  214. SetSize(cVolumeMapEntries);
  215. if ( ReadFile( &cft1, sizeof(cft1), &cbRead ) &&
  216. cbRead == sizeof(cft1) &&
  217. (_cVolumeMapEntries == 0 ||
  218. ( ReadFile(_pVolumeMapEntries, _cVolumeMapEntries * sizeof(VolumeMapEntry), &cbRead) &&
  219. cbRead == _cVolumeMapEntries * sizeof(VolumeMapEntry) ) ) &&
  220. ReadFile( &cft2, sizeof(cft2), &cbRead ) &&
  221. cbRead == sizeof(cft2) &&
  222. memcmp(&cft1, &cft2, sizeof(cft1)) == 0)
  223. {
  224. _cft = cft1;
  225. r = OK;
  226. }
  227. }
  228. if (r != OK)
  229. {
  230. CloseFile();
  231. }
  232. }
  233. else
  234. if (status != STATUS_OBJECT_NAME_NOT_FOUND)
  235. {
  236. TrkLog((TRKDBG_ERROR, TEXT("CPersistentVolumeMap::OpenExistingFile() failed %08x"), status));
  237. TrkRaiseNtStatus(status);
  238. }
  239. else
  240. {
  241. r = NOT_FOUND;
  242. }
  243. TrkLog((TRKDBG_VOLMAP | TRKDBG_VOLTAB_RESTORE,
  244. TEXT("CPersistentVolumeMap::OpenExistingFile() -> %s"),
  245. (r == NOT_FOUND ? TEXT("NOT_FOUND") : r == OK ? TEXT("OK") : r == CORRUPT ? TEXT("CORRUPT") : TEXT("unknown"))));
  246. return (r);
  247. }
  248. // BUGBUG P1: CPersistentVolumeMap::UnInitialize
  249. void
  250. CPersistentVolumeMap::CreateAlwaysFile( const TCHAR * ptszFile )
  251. {
  252. NTSTATUS status = CreateAlwaysSecureFile(ptszFile);
  253. if( !NT_SUCCESS(status) )
  254. TrkRaiseNtStatus( status );
  255. CVolumeMap::SetSize(0);
  256. _cft = CFILETIME(0);
  257. Save();
  258. CloseFile();
  259. }
  260. #endif