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.

897 lines
25 KiB

  1. /******************************************************************************
  2. Copyright (c) 2000 Microsoft Corporation
  3. Module Name:
  4. Session.cpp
  5. Abstract:
  6. This file contains the implementation of the MPCSession class,
  7. that describes the state of a transfer.
  8. Revision History:
  9. Davide Massarenti (Dmassare) 04/20/99
  10. created
  11. ******************************************************************************/
  12. #include "stdafx.h"
  13. #define BUFFER_SIZE_FILECOPY (512)
  14. static void EncodeBuffer( /*[in]*/ LPWSTR rgBufOut ,
  15. /*[in]*/ LPCWSTR rgBufIn ,
  16. /*[in]*/ DWORD iSize )
  17. {
  18. int iLen;
  19. WCHAR c;
  20. iLen = wcslen( rgBufOut );
  21. iSize -= iLen + 1;
  22. rgBufOut += iLen;
  23. while(iSize > 0 && (c = *rgBufIn++))
  24. {
  25. if(_istalnum( c ))
  26. {
  27. if(iSize > 1)
  28. {
  29. *rgBufOut = c;
  30. rgBufOut += 1;
  31. iSize -= 1;
  32. }
  33. }
  34. else
  35. {
  36. if(iSize > 3)
  37. {
  38. swprintf( rgBufOut, L"%%%02x", (int)c );
  39. rgBufOut += 3;
  40. iSize -= 3;
  41. }
  42. }
  43. }
  44. *rgBufOut = 0;
  45. }
  46. //////////////////////////////////////////////////////////////////////
  47. //////////////////////////////////////////////////////////////////////
  48. //
  49. // Construction/Destruction
  50. //
  51. //////////////////////////////////////////////////////////////////////
  52. //////////////////////////////////////////////////////////////////////
  53. MPCSession::MPCSession( /*[in]*/ MPCClient* mpccParent ) : m_SelfCOM( this )
  54. {
  55. __ULT_FUNC_ENTRY("MPCSession::MPCSession");
  56. // MPCSessionCOMWrapper m_SelfCOM;
  57. m_mpccParent = mpccParent; // MPCClient* m_mpccParent;
  58. m_dwID = 0; // DWORD m_dwID;
  59. //
  60. // MPC::wstring m_szJobID;
  61. // MPC::wstring m_szProviderID;
  62. // MPC::wstring m_szUsername;
  63. //
  64. m_dwTotalSize = 0; // DWORD m_dwTotalSize;
  65. m_dwOriginalSize = 0; // DWORD m_dwOriginalSize;
  66. m_dwCRC = 0; // DWORD m_dwCRC;
  67. m_fCompressed = false; // bool m_fCompressed;
  68. //
  69. m_dwCurrentSize = 0; // DWORD m_dwCurrentSize;
  70. // SYSTEMTIME m_stLastModified;
  71. m_fCommitted = false; // bool m_fCommitted;
  72. //
  73. m_dwProviderData = 0; // DWORD m_dwProviderData;
  74. //
  75. m_fDirty = false; // mutable bool m_fDirty;
  76. }
  77. MPCSession::MPCSession( /*[in]*/ MPCClient* mpccParent ,
  78. /*[in]*/ const UploadLibrary::ClientRequest_OpenSession& crosReq ,
  79. /*[in]*/ DWORD dwID ) : m_SelfCOM( this )
  80. {
  81. __ULT_FUNC_ENTRY("MPCSession::MPCSession");
  82. // MPCSessionCOMWrapper m_SelfCOM;
  83. m_mpccParent = mpccParent; // MPCClient* m_mpccParent;
  84. m_dwID = dwID; // DWORD m_dwID;
  85. //
  86. m_szJobID = crosReq.szJobID; // MPC::wstring m_szJobID;
  87. m_szProviderID = crosReq.szProviderID; // MPC::wstring m_szProviderID;
  88. m_szUsername = crosReq.szUsername; // MPC::wstring m_szUsername;
  89. //
  90. m_dwTotalSize = crosReq.dwSize; // DWORD m_dwTotalSize;
  91. m_dwOriginalSize = crosReq.dwSizeOriginal; // DWORD m_dwOriginalSize;
  92. m_dwCRC = crosReq.dwCRC; // DWORD m_dwCRC;
  93. m_fCompressed = crosReq.fCompressed; // bool m_fCompressed;
  94. //
  95. m_dwCurrentSize = 0; // DWORD m_dwCurrentSize;
  96. m_fCommitted = false; // SYSTEMTIME m_stLastModified;
  97. ::GetSystemTime( &m_stLastModified ); // bool m_fCommitted;
  98. //
  99. m_dwProviderData = 0; // DWORD m_dwProviderData;
  100. //
  101. m_fDirty = true; // mutable bool m_fDirty;
  102. }
  103. MPCSession::MPCSession( /*[in]*/ const MPCSession& sess ) : m_SelfCOM( this )
  104. {
  105. __ULT_FUNC_ENTRY("MPCSession::MPCSession");
  106. // MPCSessionCOMWrapper m_SelfCOM;
  107. m_mpccParent = sess.m_mpccParent; // MPCClient* m_mpccParent;
  108. m_dwID = sess.m_dwID; // DWORD m_dwID;
  109. //
  110. m_szJobID = sess.m_szJobID; // MPC::wstring m_szJobID;
  111. m_szProviderID = sess.m_szProviderID; // MPC::wstring m_szProviderID;
  112. m_szUsername = sess.m_szUsername; // MPC::wstring m_szUsername;
  113. //
  114. m_dwTotalSize = sess.m_dwTotalSize; // DWORD m_dwTotalSize;
  115. m_dwOriginalSize = sess.m_dwOriginalSize; // DWORD m_dwOriginalSize;
  116. m_dwCRC = sess.m_dwCRC; // DWORD m_dwCRC;
  117. m_fCompressed = sess.m_fCompressed; // bool m_fCompressed;
  118. //
  119. m_dwCurrentSize = sess.m_dwCurrentSize; // DWORD m_dwCurrentSize;
  120. m_stLastModified = sess.m_stLastModified; // SYSTEMTIME m_stLastModified;
  121. m_fCommitted = sess.m_fCommitted; // bool m_fCommitted;
  122. //
  123. m_dwProviderData = sess.m_dwProviderData; // DWORD m_dwProviderData;
  124. //
  125. m_fDirty = sess.m_fDirty; // mutable bool m_fDirty;
  126. }
  127. MPCSession::~MPCSession()
  128. {
  129. __ULT_FUNC_ENTRY("MPCSession::~MPCSession");
  130. }
  131. MPCClient* MPCSession::GetClient() { return m_mpccParent; }
  132. IULSession* MPCSession::COM() { return &m_SelfCOM; }
  133. //////////////////////////////////////////////////////////////////////
  134. // Persistence
  135. //////////////////////////////////////////////////////////////////////
  136. bool MPCSession::IsDirty() const
  137. {
  138. __ULT_FUNC_ENTRY("MPCSession::IsDirty");
  139. bool fRes = m_fDirty;
  140. __ULT_FUNC_EXIT(fRes);
  141. }
  142. HRESULT MPCSession::Load( /*[in]*/ MPC::Serializer& streamIn )
  143. {
  144. __ULT_FUNC_ENTRY("MPCSession::Load");
  145. HRESULT hr;
  146. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwID );
  147. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_szJobID );
  148. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_szProviderID );
  149. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_szUsername );
  150. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwTotalSize );
  151. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwOriginalSize);
  152. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwCRC );
  153. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_fCompressed );
  154. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwCurrentSize );
  155. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_stLastModified);
  156. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_fCommitted );
  157. __MPC_EXIT_IF_METHOD_FAILS(hr, streamIn >> m_dwProviderData);
  158. m_fDirty = false;
  159. hr = S_OK;
  160. __ULT_FUNC_CLEANUP;
  161. __ULT_FUNC_EXIT(hr);
  162. }
  163. HRESULT MPCSession::Save( /*[in]*/ MPC::Serializer& streamOut ) const
  164. {
  165. __ULT_FUNC_ENTRY("MPCSession::Save");
  166. HRESULT hr;
  167. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwID );
  168. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_szJobID );
  169. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_szProviderID );
  170. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_szUsername );
  171. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwTotalSize );
  172. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwOriginalSize);
  173. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwCRC );
  174. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_fCompressed );
  175. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwCurrentSize );
  176. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_stLastModified);
  177. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_fCommitted );
  178. __MPC_EXIT_IF_METHOD_FAILS(hr, streamOut << m_dwProviderData);
  179. m_fDirty = false;
  180. hr = S_OK;
  181. __ULT_FUNC_CLEANUP;
  182. __ULT_FUNC_EXIT(hr);
  183. }
  184. //////////////////////////////////////////////////////////////////////
  185. // Operators
  186. //////////////////////////////////////////////////////////////////////
  187. bool MPCSession::operator==( /*[in]*/ const MPC::wstring& rhs )
  188. {
  189. __ULT_FUNC_ENTRY("MPCSession::operator==");
  190. bool fRes = (m_szJobID == rhs);
  191. __ULT_FUNC_EXIT(fRes);
  192. }
  193. bool MPCSession::MatchRequest( /*[in]*/ const UploadLibrary::ClientRequest_OpenSession& crosReq )
  194. {
  195. __ULT_FUNC_ENTRY("MPCSession::MatchRequest");
  196. bool fRes = false;
  197. if(m_szProviderID == crosReq.szProviderID &&
  198. m_szUsername == crosReq.szUsername &&
  199. m_dwTotalSize == crosReq.dwSize &&
  200. m_dwOriginalSize == crosReq.dwSizeOriginal &&
  201. m_dwCRC == crosReq.dwCRC &&
  202. m_fCompressed == crosReq.fCompressed )
  203. {
  204. fRes = true;
  205. }
  206. return fRes;
  207. }
  208. bool MPCSession::get_Committed() const
  209. {
  210. bool fRes = m_fCommitted;
  211. return fRes;
  212. }
  213. HRESULT MPCSession::put_Committed( /*[in]*/ bool fState, /*[in]*/ bool fMove )
  214. {
  215. __ULT_FUNC_ENTRY("MPCSession::put_Committed");
  216. HRESULT hr;
  217. if(fState)
  218. {
  219. if(fMove)
  220. {
  221. CISAPIprovider* isapiProvider;
  222. bool fFound;
  223. __MPC_EXIT_IF_METHOD_FAILS(hr, GetProvider( isapiProvider, fFound ));
  224. if(fFound)
  225. {
  226. MPC::wstring szFileDst;
  227. __MPC_EXIT_IF_METHOD_FAILS(hr, SelectFinalLocation( isapiProvider, szFileDst, fFound ));
  228. if(fFound == false)
  229. {
  230. __MPC_SET_ERROR_AND_EXIT(hr, E_FAIL);
  231. }
  232. __MPC_EXIT_IF_METHOD_FAILS(hr, MoveToFinalLocation( szFileDst ));
  233. }
  234. //
  235. // Make sure we get rid of the file.
  236. //
  237. (void)RemoveFile();
  238. }
  239. }
  240. m_fCommitted = fState;
  241. m_fDirty = true;
  242. hr = S_OK;
  243. __ULT_FUNC_CLEANUP;
  244. __ULT_FUNC_EXIT(hr);
  245. }
  246. /////////////////////////////////////////////////////////////////////////////
  247. void MPCSession::get_JobID( MPC::wstring& szJobID ) const
  248. {
  249. szJobID = m_szJobID;
  250. }
  251. void MPCSession::get_LastModified( SYSTEMTIME& stLastModified ) const
  252. {
  253. stLastModified = m_stLastModified;
  254. }
  255. void MPCSession::get_LastModified( double& dblLastModified ) const
  256. {
  257. ::SystemTimeToVariantTime( const_cast<SYSTEMTIME*>(&m_stLastModified), &dblLastModified );
  258. }
  259. void MPCSession::get_CurrentSize( DWORD& dwCurrentSize ) const
  260. {
  261. dwCurrentSize = m_dwCurrentSize;
  262. }
  263. void MPCSession::get_TotalSize( DWORD& dwTotalSize ) const
  264. {
  265. dwTotalSize = m_dwTotalSize;
  266. }
  267. //////////////////////////////////////////////////////////////////////
  268. // Methods
  269. //////////////////////////////////////////////////////////////////////
  270. /////////////////////////////////////////////////////////////////////////////
  271. //
  272. // Method Name : MPCSession::GetProvider
  273. //
  274. // Parameters : CISAPIprovider*& isapiProvider : provider of current session.
  275. // bool& fFound : true if provider exists.
  276. //
  277. // Return : HRESULT : S_OK on success, failed otherwise.
  278. //
  279. // Synopsis :
  280. //
  281. //
  282. /////////////////////////////////////////////////////////////////////////////
  283. HRESULT MPCSession::GetProvider( /*[out]*/ CISAPIprovider*& isapiProvider ,
  284. /*[out]*/ bool& fFound )
  285. {
  286. __ULT_FUNC_ENTRY("MPCSession::GetProvider");
  287. HRESULT hr;
  288. CISAPIinstance* isapiInstance;
  289. MPC::wstring szURL;
  290. isapiProvider = NULL;
  291. __MPC_EXIT_IF_METHOD_FAILS(hr, m_mpccParent->GetInstance( isapiInstance, fFound ));
  292. if(fFound)
  293. {
  294. __MPC_EXIT_IF_METHOD_FAILS(hr, isapiInstance->get_URL( szURL ));
  295. __MPC_EXIT_IF_METHOD_FAILS(hr, Config_GetProvider( szURL, m_szProviderID, isapiProvider, fFound ));
  296. }
  297. hr = S_OK;
  298. __ULT_FUNC_CLEANUP;
  299. __ULT_FUNC_EXIT(hr);
  300. }
  301. /////////////////////////////////////////////////////////////////////////////
  302. //
  303. // Method Name : MPCSession::SelectFinalLocation
  304. //
  305. // Parameters : CISAPIprovider* isapiProvider : provider of current session.
  306. // MPC::wstring& szFileDst : Output file directory
  307. // bool& fFound : true if successful.
  308. //
  309. // Return : HRESULT : S_OK on success, failed otherwise.
  310. //
  311. // Synopsis :
  312. //
  313. //
  314. /////////////////////////////////////////////////////////////////////////////
  315. HRESULT MPCSession::SelectFinalLocation( /*[in] */ CISAPIprovider* isapiProvider ,
  316. /*[out]*/ MPC::wstring& szFileDst ,
  317. /*[out]*/ bool& fFound )
  318. {
  319. __ULT_FUNC_ENTRY("MPCSession::SelectFinalLocation");
  320. HRESULT hr;
  321. CISAPIprovider::PathIter itBegin;
  322. CISAPIprovider::PathIter itEnd;
  323. fFound = false;
  324. __MPC_EXIT_IF_METHOD_FAILS(hr, isapiProvider->GetLocations( itBegin, itEnd ));
  325. if(itBegin != itEnd)
  326. {
  327. WCHAR rgBuf[MAX_PATH+1];
  328. MPC::wstring szID;
  329. __MPC_EXIT_IF_METHOD_FAILS(hr, m_mpccParent->FormatID( szID ));
  330. wcsncpy ( rgBuf, L"U_" , MAX_PATH );
  331. EncodeBuffer( rgBuf, m_szProviderID.c_str(), MAX_PATH );
  332. wcsncat ( rgBuf, L"_" , MAX_PATH );
  333. wcsncat ( rgBuf, szID .c_str(), MAX_PATH );
  334. wcsncat ( rgBuf, L"_" , MAX_PATH );
  335. EncodeBuffer( rgBuf, m_szJobID .c_str(), MAX_PATH );
  336. wcsncat ( rgBuf, L"_" , MAX_PATH );
  337. EncodeBuffer( rgBuf, m_szUsername .c_str(), MAX_PATH );
  338. szFileDst = *itBegin;
  339. szFileDst.append( L"\\" );
  340. szFileDst.append( rgBuf );
  341. fFound = true;
  342. }
  343. hr = S_OK;
  344. __ULT_FUNC_CLEANUP;
  345. __ULT_FUNC_EXIT(hr);
  346. }
  347. /////////////////////////////////////////////////////////////////////////////
  348. //
  349. // Method Name : MPCSession::MoveToFinalLocation
  350. //
  351. // Parameters : MPC::wstring& szFileDst : Output file name
  352. //
  353. // Return : HRESULT : S_OK on success, failed otherwise.
  354. //
  355. // Synopsis :
  356. //
  357. //
  358. /////////////////////////////////////////////////////////////////////////////
  359. HRESULT MPCSession::MoveToFinalLocation( /*[in]*/ const MPC::wstring& szFileDst )
  360. {
  361. __ULT_FUNC_ENTRY("MPCSession::MoveToFinalLocation");
  362. HRESULT hr;
  363. ULONG dwRes;
  364. MPC::wstring szFileSrc;
  365. MPC::wstring szFileSrcUncompressed;
  366. bool fEnough;
  367. __MPC_EXIT_IF_METHOD_FAILS(hr, GetFileName( szFileSrc ));
  368. __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::MakeDir( szFileDst ) );
  369. //
  370. // Check for space in the final destination.
  371. //
  372. __MPC_EXIT_IF_METHOD_FAILS(hr, ::Util_CheckDiskSpace( szFileDst, m_dwOriginalSize + DISKSPACE_SAFETYMARGIN, fEnough ));
  373. if(fEnough == false)
  374. {
  375. __MPC_SET_WIN32_ERROR_AND_EXIT(hr, ERROR_DISK_FULL );
  376. }
  377. if(m_fCompressed)
  378. {
  379. //
  380. // Check for space in the queue directory.
  381. //
  382. __MPC_EXIT_IF_METHOD_FAILS(hr, ::Util_CheckDiskSpace( szFileSrc, m_dwOriginalSize + DISKSPACE_SAFETYMARGIN, fEnough ));
  383. if(fEnough == false)
  384. {
  385. __MPC_SET_WIN32_ERROR_AND_EXIT(hr, ERROR_DISK_FULL );
  386. }
  387. szFileSrcUncompressed = szFileSrc;
  388. szFileSrcUncompressed.append( L"_decomp" );
  389. __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::DecompressFromCabinet( szFileSrc.c_str(), szFileSrcUncompressed.c_str(), L"PAYLOAD" ));
  390. __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::MoveFile( szFileSrcUncompressed, szFileDst ));
  391. }
  392. else
  393. {
  394. __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::MoveFile( szFileSrc, szFileDst ));
  395. }
  396. hr = S_OK;
  397. __ULT_FUNC_CLEANUP;
  398. if(szFileSrcUncompressed.length() != 0)
  399. {
  400. (void)MPC::DeleteFile( szFileSrcUncompressed );
  401. }
  402. //
  403. // Create entry in the Event Log.
  404. //
  405. {
  406. MPC::wstring szURL; (void)m_mpccParent->GetInstance( szURL );
  407. MPC::wstring szID; (void)m_mpccParent->FormatID ( szID );
  408. WCHAR rgSize[16]; (void)swprintf( rgSize, L"%d", m_dwOriginalSize );
  409. if(SUCCEEDED(hr))
  410. {
  411. #ifdef DEBUG
  412. (void)g_NTEvents.LogEvent( EVENTLOG_INFORMATION_TYPE, PCHUL_SUCCESS_COMPLETEJOB,
  413. szURL .c_str(), // %1 = SERVER
  414. szID .c_str(), // %2 = CLIENT
  415. m_szProviderID.c_str(), // %3 = PROVIDER
  416. rgSize , // %4 = BYTES
  417. szFileDst .c_str(), // %5 = DESTINATION
  418. NULL );
  419. #endif
  420. }
  421. else
  422. {
  423. (void)g_NTEvents.LogEvent( EVENTLOG_ERROR_TYPE, PCHUL_ERR_FINALCOPY,
  424. szURL .c_str(), // %1 = SERVER
  425. szID .c_str(), // %2 = CLIENT
  426. m_szProviderID.c_str(), // %3 = PROVIDER
  427. rgSize , // %4 = BYTES
  428. szFileDst .c_str(), // %5 = DESTINATION
  429. NULL );
  430. }
  431. }
  432. __ULT_FUNC_EXIT(hr);
  433. }
  434. /////////////////////////////////////////////////////////////////////////////
  435. HRESULT MPCSession::GetFileName( /*[out]*/ MPC::wstring& szFile )
  436. {
  437. __ULT_FUNC_ENTRY("MPCSession::GetFileName");
  438. HRESULT hr;
  439. WCHAR rgBuf[32];
  440. __MPC_EXIT_IF_METHOD_FAILS(hr, m_mpccParent->BuildClientPath( szFile ));
  441. //
  442. // The filename for the Data File is "<ID>-<SEQ>.img"
  443. //
  444. swprintf( rgBuf, SESSION_CONST__IMG_FORMAT, m_dwID ); szFile.append( rgBuf );
  445. hr = S_OK;
  446. __ULT_FUNC_CLEANUP;
  447. __ULT_FUNC_EXIT(hr);
  448. }
  449. HRESULT MPCSession::RemoveFile()
  450. {
  451. __ULT_FUNC_ENTRY("MPCSession::RemoveFile");
  452. HRESULT hr;
  453. MPC::wstring szFile;
  454. __MPC_EXIT_IF_METHOD_FAILS(hr, GetFileName( szFile ));
  455. (void)MPC::DeleteFile( szFile );
  456. hr = S_OK;
  457. __ULT_FUNC_CLEANUP;
  458. __ULT_FUNC_EXIT(hr);
  459. }
  460. HRESULT MPCSession::OpenFile( /*[out]*/ HANDLE& hfFile ,
  461. /*[in] */ DWORD dwMinimumFreeSpace ,
  462. /*[in] */ bool fSeek )
  463. {
  464. __ULT_FUNC_ENTRY("MPCSession::OpenFile");
  465. HRESULT hr;
  466. MPC::wstring szFile;
  467. __MPC_EXIT_IF_METHOD_FAILS(hr, GetFileName( szFile ));
  468. //
  469. // Check if enough free space is available.
  470. //
  471. if(dwMinimumFreeSpace)
  472. {
  473. bool fEnough;
  474. __MPC_EXIT_IF_METHOD_FAILS(hr, ::Util_CheckDiskSpace( szFile, dwMinimumFreeSpace, fEnough ));
  475. if(fEnough == false)
  476. {
  477. __MPC_SET_WIN32_ERROR_AND_EXIT(hr, ERROR_DISK_FULL );
  478. }
  479. }
  480. //
  481. // Ensure the directory exists.
  482. //
  483. __MPC_EXIT_IF_METHOD_FAILS(hr, MPC::MakeDir( szFile ) );
  484. __MPC_EXIT_IF_INVALID_HANDLE__CLEAN(hr, hfFile, ::CreateFileW( szFile.c_str(), GENERIC_WRITE | GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL ));
  485. if(fSeek)
  486. {
  487. //
  488. // Move to the correct Last Written position.
  489. //
  490. ::SetFilePointer( hfFile, m_dwCurrentSize, NULL, FILE_BEGIN );
  491. //
  492. // If current position differs from wanted position, truncate to zero the file.
  493. //
  494. if(::SetFilePointer( hfFile, 0, NULL, FILE_CURRENT ) != m_dwCurrentSize)
  495. {
  496. ::SetFilePointer( hfFile, 0, NULL, FILE_BEGIN );
  497. ::SetEndOfFile ( hfFile );
  498. m_dwCurrentSize = 0;
  499. m_fDirty = true;
  500. }
  501. }
  502. hr = S_OK;
  503. __ULT_FUNC_CLEANUP;
  504. __ULT_FUNC_EXIT(hr);
  505. }
  506. HRESULT MPCSession::Validate( /*[in] */ bool fCheckFile ,
  507. /*[out]*/ bool& fPassed )
  508. {
  509. __ULT_FUNC_ENTRY("MPCSession::Validate");
  510. HRESULT hr;
  511. HANDLE hfFile = NULL;
  512. CISAPIprovider* isapiProvider;
  513. bool fFound;
  514. fPassed = false;
  515. //
  516. // If the related provider doesn't exist, validation fails.
  517. //
  518. __MPC_EXIT_IF_METHOD_FAILS(hr, GetProvider( isapiProvider, fFound ));
  519. if(fFound == false)
  520. {
  521. __MPC_SET_ERROR_AND_EXIT(hr, S_OK);
  522. }
  523. if(m_fCommitted == true)
  524. {
  525. fPassed = true;
  526. __MPC_SET_ERROR_AND_EXIT(hr, S_OK);
  527. }
  528. /////////////////////////////////////////////////////////
  529. //
  530. // If we reach this point, the session is still not committed.
  531. //
  532. if(fCheckFile)
  533. {
  534. __MPC_EXIT_IF_METHOD_FAILS(hr, OpenFile( hfFile ));
  535. //
  536. // All the bytes have been received, so try to commit the job (deferred due to low disk probably).
  537. //
  538. if(m_dwCurrentSize >= m_dwTotalSize)
  539. {
  540. //
  541. // Ignore result, if it fails the session won't be committed.
  542. //
  543. (void)put_Committed( true, true );
  544. }
  545. }
  546. fPassed = true;
  547. hr = S_OK;
  548. __ULT_FUNC_CLEANUP;
  549. if(hfFile) ::CloseHandle( hfFile );
  550. __ULT_FUNC_EXIT(hr);
  551. }
  552. HRESULT MPCSession::CheckUser( /*[in] */ const MPC::wstring& szUser ,
  553. /*[out]*/ bool& fMatch )
  554. {
  555. __ULT_FUNC_ENTRY("MPCSession::CheckUser");
  556. HRESULT hr;
  557. CISAPIprovider* isapiProvider;
  558. BOOL fAuthenticated;
  559. bool fFound;
  560. fMatch = false;
  561. //
  562. // If the related provider doesn't exist, validation fails.
  563. //
  564. __MPC_EXIT_IF_METHOD_FAILS(hr, GetProvider( isapiProvider, fFound ));
  565. if(fFound == false)
  566. {
  567. __MPC_SET_ERROR_AND_EXIT(hr, S_OK);
  568. }
  569. __MPC_EXIT_IF_METHOD_FAILS(hr, isapiProvider->get_Authenticated( fAuthenticated ));
  570. if(fAuthenticated)
  571. {
  572. if(m_szUsername != szUser)
  573. {
  574. __MPC_SET_ERROR_AND_EXIT(hr, S_OK);
  575. }
  576. }
  577. fMatch = true; // User check is positive.
  578. hr = S_OK;
  579. __ULT_FUNC_CLEANUP;
  580. __ULT_FUNC_EXIT(hr);
  581. }
  582. /////////////////////////////////////////////////////////////////////////////
  583. HRESULT MPCSession::CompareCRC( /*[out]*/ bool& fMatch )
  584. {
  585. __ULT_FUNC_ENTRY("MPCSession::CompareCRC");
  586. HRESULT hr;
  587. HANDLE hfFile = NULL;
  588. UCHAR rgBuf[BUFFER_SIZE_FILECOPY];
  589. DWORD dwCRC;
  590. fMatch = false;
  591. MPC::InitCRC( dwCRC );
  592. __MPC_EXIT_IF_METHOD_FAILS(hr, OpenFile( hfFile ));
  593. //
  594. // Move to the beginning.
  595. //
  596. ::SetFilePointer( hfFile, 0, NULL, FILE_BEGIN );
  597. //
  598. // Calculate the CRC, reading all the data.
  599. //
  600. while(1)
  601. {
  602. DWORD dwRead;
  603. __MPC_EXIT_IF_CALL_RETURNS_FALSE(hr, ::ReadFile( hfFile, rgBuf, sizeof( rgBuf ), &dwRead, NULL ));
  604. if(dwRead == 0) // End of File.
  605. {
  606. break;
  607. }
  608. MPC::ComputeCRC( dwCRC, rgBuf, dwRead );
  609. }
  610. fMatch = (dwCRC == m_dwCRC);
  611. hr = S_OK;
  612. __ULT_FUNC_CLEANUP;
  613. if(hfFile) ::CloseHandle( hfFile );
  614. __ULT_FUNC_EXIT(hr);
  615. }
  616. /////////////////////////////////////////////////////////////////////////////
  617. //
  618. // Method Name : MPCSession::AppendData
  619. //
  620. // Parameters : MPC::Serializer& conn : stream sourcing the data.
  621. // DWORD size : size of the data.
  622. //
  623. // Return : HRESULT : S_OK on success, failed otherwise.
  624. //
  625. // Synopsis : Writes a block of data from the 'conn' stream to the end of
  626. // the Data File for this session.
  627. //
  628. /////////////////////////////////////////////////////////////////////////////
  629. HRESULT MPCSession::AppendData( /*[in]*/ MPC::Serializer& streamConn ,
  630. /*[in]*/ DWORD dwSize )
  631. {
  632. __ULT_FUNC_ENTRY("MPCSession::AppendData");
  633. HRESULT hr;
  634. HANDLE hfFile = NULL;
  635. //
  636. // Open file and make sure there's enough free space.
  637. //
  638. __MPC_EXIT_IF_METHOD_FAILS(hr, OpenFile( hfFile, dwSize * 3 ));
  639. {
  640. MPC::Serializer_File streamConnOut( hfFile );
  641. BYTE rgBuf[BUFFER_SIZE_FILECOPY];
  642. hr = S_OK;
  643. while(dwSize)
  644. {
  645. DWORD dwRead = min( BUFFER_SIZE_FILECOPY, dwSize );
  646. __MPC_EXIT_IF_METHOD_FAILS(hr, streamConn .read ( rgBuf, dwRead ));
  647. __MPC_EXIT_IF_METHOD_FAILS(hr, streamConnOut.write( rgBuf, dwRead ));
  648. dwSize -= dwRead;
  649. m_dwCurrentSize += dwRead;
  650. ::GetSystemTime( &m_stLastModified );
  651. m_fDirty = true;
  652. }
  653. }
  654. hr = S_OK;
  655. __ULT_FUNC_CLEANUP;
  656. if(hfFile) ::CloseHandle( hfFile );
  657. __ULT_FUNC_EXIT(hr);
  658. }