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.

1481 lines
28 KiB

  1. //+-------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1992 - 1993.
  5. //
  6. // File: cliptest.cpp
  7. //
  8. // Contents: Clipboard Unit tests
  9. //
  10. // Classes:
  11. //
  12. // Functions: LEClipTest1
  13. //
  14. // History: dd-mmm-yy Author Comment
  15. // 23-Mar-94 alexgo author
  16. //
  17. //--------------------------------------------------------------------------
  18. #include "oletest.h"
  19. #include "gendata.h"
  20. #include "genenum.h"
  21. #include "letest.h"
  22. SLETestInfo letiClipTest = { "cntroutl", WM_TEST1 };
  23. //
  24. // functions local to this file
  25. //
  26. void DumpClipboardFormats(FILE *fp);
  27. HRESULT LEOle1ClipTest2Callback( void );
  28. HRESULT StressOleFlushClipboard(void);
  29. HRESULT StressOleGetClipboard(void);
  30. HRESULT StressOleIsCurrentClipboard(void);
  31. HRESULT StressOleSetClipboard(void);
  32. class CClipEnumeratorTest : public CEnumeratorTest
  33. {
  34. public:
  35. CClipEnumeratorTest(
  36. IEnumFORMATETC *penum,
  37. LONG clEntries,
  38. HRESULT& rhr);
  39. BOOL Verify(void *);
  40. };
  41. CClipEnumeratorTest::CClipEnumeratorTest(
  42. IEnumFORMATETC *penum,
  43. LONG clEntries,
  44. HRESULT& rhr)
  45. : CEnumeratorTest(penum, sizeof(FORMATETC), clEntries, rhr)
  46. {
  47. // Header does all the work
  48. }
  49. BOOL CClipEnumeratorTest::Verify(void *)
  50. {
  51. return TRUE;
  52. }
  53. //+-------------------------------------------------------------------------
  54. //
  55. // Function: DumpClipboardFormats
  56. //
  57. // Synopsis: dumps the formats currently on the clipboard to a file
  58. //
  59. // Effects:
  60. //
  61. // Arguments: [fp] -- the file to print the current formats
  62. //
  63. // Requires:
  64. //
  65. // Returns: void
  66. //
  67. // Signals:
  68. //
  69. // Modifies:
  70. //
  71. // Algorithm:
  72. //
  73. // History: dd-mmm-yy Author Comment
  74. // 11-Aug-94 alexgo author
  75. //
  76. // Notes:
  77. //
  78. //--------------------------------------------------------------------------
  79. void DumpClipboardFormats( FILE *fp )
  80. {
  81. char szBuf[256];
  82. UINT cf = 0;
  83. fprintf(fp, "==================================================\n\n");
  84. OpenClipboard(NULL);
  85. while( (cf = EnumClipboardFormats(cf)) != 0)
  86. {
  87. GetClipboardFormatName(cf, szBuf, sizeof(szBuf));
  88. fprintf(fp, "%s\n", szBuf);
  89. }
  90. fprintf(fp, "\n==================================================\n");
  91. CloseClipboard();
  92. return;
  93. }
  94. //+-------------------------------------------------------------------------
  95. //
  96. // Function: LEClipTest1
  97. //
  98. // Synopsis: runs the clipboard through a series of tests
  99. //
  100. // Effects:
  101. //
  102. // Arguments: void
  103. //
  104. // Requires:
  105. //
  106. // Returns: HRESULT
  107. //
  108. // Signals:
  109. //
  110. // Modifies:
  111. //
  112. // Algorithm: Tests basic OLE32 functionality of the apis:
  113. // OleSetClipboard
  114. // OleGetClipboard
  115. // OleIsCurrentClipboard
  116. // OleFlushClipboard
  117. // downlevel format and clipboard data object testing is *not*
  118. // done by this routine
  119. //
  120. // History: dd-mmm-yy Author Comment
  121. // 23-Mar-94 alexgo author
  122. // 22-Jul-94 AlexT Add OleInit/OleUninit call
  123. //
  124. // Notes:
  125. //
  126. //--------------------------------------------------------------------------
  127. HRESULT LEClipTest1( void )
  128. {
  129. HRESULT hresult = NOERROR;
  130. CGenDataObject *pDO;
  131. ULONG cRefs;
  132. IDataObject * pIDO;
  133. pDO = new CGenDataObject;
  134. assert(pDO);
  135. cRefs = pDO->AddRef();
  136. // if cRefs != 1, then somebody modified this test code; the tests
  137. // below will be invalid.
  138. assert(cRefs==1);
  139. //
  140. // Basic Tests
  141. //
  142. hresult = OleSetClipboard(pDO);
  143. if( hresult != NOERROR )
  144. {
  145. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  146. return hresult;
  147. }
  148. // the data object should have been AddRef'ed
  149. cRefs = pDO->AddRef();
  150. if( cRefs != 3 )
  151. {
  152. OutputString("Wrong reference count!! Should be 3, "
  153. "was %lu\r\n", cRefs);
  154. return ResultFromScode(E_FAIL);
  155. }
  156. pDO->Release();
  157. // Calling OleInitialize & OleUninitialize should not disturb the
  158. // clipboard
  159. hresult = OleInitialize(NULL);
  160. if (FAILED(hresult))
  161. {
  162. OutputString("LEClipTest1: OleInitialize failed - hr = %lx\n",
  163. hresult);
  164. return ResultFromScode(E_FAIL);
  165. }
  166. OleUninitialize();
  167. hresult = OleGetClipboard(&pIDO);
  168. if( hresult != NOERROR )
  169. {
  170. OutputString("OleGetClipboard failed! (%lx)\r\n", hresult);
  171. return hresult;
  172. }
  173. if( pIDO == NULL )
  174. {
  175. OutputString("OleGetClipboard returned NULL IDO\r\n");
  176. return ResultFromScode(E_FAIL);
  177. }
  178. // the reference count on the clipboard data object should have gone up
  179. // by one (to be 2). Remember this is not our data object but
  180. // the clipboard's.
  181. cRefs = pIDO->AddRef();
  182. if( cRefs != 2 )
  183. {
  184. OutputString("Wrong ref count!! Should be 2, was %lu\r\n",
  185. cRefs);
  186. return ResultFromScode(E_FAIL);
  187. }
  188. // Release the clipboard data object's extra add ref.
  189. pIDO->Release();
  190. // Release the clipboard's data object entirely.
  191. pIDO->Release();
  192. // the reference count on our data object should be 2 still
  193. cRefs = pDO->AddRef();
  194. if( cRefs != 3 )
  195. {
  196. OutputString("Wrong ref count!! Should be 3, was %lu\r\n",
  197. cRefs);
  198. return ResultFromScode(E_FAIL);
  199. }
  200. pDO->Release();
  201. // now check to see if the we are the current clipboard
  202. hresult = OleIsCurrentClipboard( pDO );
  203. if( hresult != NOERROR )
  204. {
  205. OutputString("OleIsCurrentClipboard failed! (%lx)\r\n",
  206. hresult);
  207. return hresult;
  208. }
  209. // now flush the clipboard, removing the data object
  210. hresult = OleFlushClipboard();
  211. if( hresult != NOERROR )
  212. {
  213. OutputString("OleFlushClipboard failed! (%lx)\r\n", hresult);
  214. return hresult;
  215. }
  216. // Flush should have released the data object (ref count should
  217. // be 1)
  218. cRefs = pDO->AddRef();
  219. if( cRefs != 2 )
  220. {
  221. OutputString("Wrong ref count!! Should be 2, was %lu\r\n",
  222. cRefs);
  223. return ResultFromScode(E_FAIL);
  224. }
  225. pDO->Release(); // take it down to 1
  226. cRefs = pDO->Release(); // should be zero now
  227. if(cRefs != 0 )
  228. {
  229. OutputString("Wrong ref count on data transfer object! "
  230. "Unable to delete\r\n");
  231. return ResultFromScode(E_FAIL);
  232. }
  233. // if we got this far, basic clipboard tests passed
  234. OutputString("Basic Clipboard tests passed\r\n");
  235. // now stress individual API's
  236. OutputString("Now stressing clipboard API's\r\n");
  237. if( (hresult = StressOleFlushClipboard()) != NOERROR )
  238. {
  239. return hresult;
  240. }
  241. if( (hresult = StressOleGetClipboard()) != NOERROR )
  242. {
  243. return hresult;
  244. }
  245. if( (hresult = StressOleIsCurrentClipboard()) != NOERROR )
  246. {
  247. return hresult;
  248. }
  249. if( (hresult = StressOleSetClipboard()) != NOERROR )
  250. {
  251. return hresult;
  252. }
  253. OutputString("Clipoard API stress passed!\r\n");
  254. return NOERROR;
  255. }
  256. //+-------------------------------------------------------------------------
  257. //
  258. // Function: LEClipTest2
  259. //
  260. // Synopsis: Tests the clipboard data object
  261. //
  262. // Effects:
  263. //
  264. // Arguments: void
  265. //
  266. // Requires:
  267. //
  268. // Returns: HRESULT
  269. //
  270. // Signals:
  271. //
  272. // Modifies:
  273. //
  274. // Algorithm:
  275. //
  276. // History: dd-mmm-yy Author Comment
  277. // 15-Apr-94 alexgo author
  278. //
  279. // Notes:
  280. //
  281. //--------------------------------------------------------------------------
  282. HRESULT LEClipTest2( void )
  283. {
  284. CGenDataObject * pGenData;
  285. IDataObject * pDataObj;
  286. HRESULT hresult;
  287. IEnumFORMATETC * penum;
  288. FORMATETC formatetc;
  289. STGMEDIUM medium;
  290. ULONG cRefs;
  291. pGenData = new CGenDataObject();
  292. assert(pGenData);
  293. cRefs = pGenData->AddRef();
  294. // ref count should be 1
  295. assert(cRefs == 1);
  296. hresult = OleSetClipboard(pGenData);
  297. if( hresult != NOERROR )
  298. {
  299. OutputString("Clip2: OleSetClipboard failed! (%lx)\r\n",
  300. hresult);
  301. goto errRtn2;
  302. }
  303. hresult = OleFlushClipboard();
  304. if( hresult != NOERROR )
  305. {
  306. OutputString("Clip2: OleFlushClipboard failed! (%lx)\r\n",
  307. hresult);
  308. goto errRtn2;
  309. }
  310. // get the fake clipboard data object
  311. hresult = OleGetClipboard(&pDataObj);
  312. if( hresult != NOERROR )
  313. {
  314. OutputString("Clip2: OleGetClipboard failed! (%lx)\r\n",
  315. hresult);
  316. goto errRtn2;
  317. }
  318. hresult = pDataObj->EnumFormatEtc(DATADIR_GET, &penum);
  319. if( hresult != NOERROR )
  320. {
  321. OutputString("Clip2: EnumFormatEtc failed! (%lx)\r\n",
  322. hresult);
  323. goto errRtn;
  324. }
  325. while( penum->Next( 1, &formatetc, NULL ) == NOERROR )
  326. {
  327. if( formatetc.cfFormat == pGenData->m_cfTestStorage ||
  328. formatetc.cfFormat == pGenData->m_cfEmbeddedObject )
  329. {
  330. // we should be told IStorage
  331. if( !(formatetc.tymed & TYMED_ISTORAGE) )
  332. {
  333. hresult = ResultFromScode(E_FAIL);
  334. OutputString("medium mismatch, ISTORAGE");
  335. break;
  336. }
  337. }
  338. hresult = pDataObj->GetData(&formatetc, &medium);
  339. if( hresult != NOERROR )
  340. {
  341. break;
  342. }
  343. // verify the data
  344. if( !pGenData->VerifyFormatAndMedium(&formatetc, &medium) )
  345. {
  346. hresult = ResultFromScode(E_FAIL);
  347. OutputString("Clip2: retrieved data doesn't match! "
  348. "cf == %d\r\n", formatetc.cfFormat);
  349. break;
  350. }
  351. ReleaseStgMedium(&medium);
  352. memset(&medium, 0, sizeof(STGMEDIUM));
  353. }
  354. {
  355. CClipEnumeratorTest cet(penum, -1, hresult);
  356. if (hresult == S_OK)
  357. {
  358. hresult = cet.TestAll();
  359. }
  360. }
  361. penum->Release();
  362. errRtn:
  363. pDataObj->Release();
  364. errRtn2:
  365. pGenData->Release();
  366. if( hresult == NOERROR )
  367. {
  368. OutputString("Clipboard data object tests Passed!\r\n");
  369. }
  370. return hresult;
  371. }
  372. //+-------------------------------------------------------------------------
  373. //
  374. // Function: LEOle1ClipTest1
  375. //
  376. // Synopsis: Simple tests of OLE1 clipboard compatibility (copy from
  377. // and OLE1 server)
  378. //
  379. // Effects:
  380. //
  381. // Arguments:
  382. //
  383. // Requires:
  384. //
  385. // Returns:
  386. //
  387. // Signals:
  388. //
  389. // Modifies:
  390. //
  391. // Algorithm: Run through 15 combinations of OLE1 support and verify
  392. // everything came out OK
  393. //
  394. // History: dd-mmm-yy Author Comment
  395. // 06-Jun-94 alexgo author
  396. //
  397. // Notes:
  398. //
  399. //--------------------------------------------------------------------------
  400. HRESULT LEOle1ClipTest1( void )
  401. {
  402. HRESULT hresult;
  403. DWORD flags;
  404. CGenDataObject * pGenData = NULL;
  405. IDataObject * pDataObj = NULL;
  406. IEnumFORMATETC * penum = NULL;
  407. FORMATETC formatetc;
  408. STGMEDIUM medium;
  409. // we are going to take advantage of the fact that the interesting
  410. // OLE1 bit flags for this test are the bottom 4 bits.
  411. pGenData = new CGenDataObject();
  412. assert(pGenData);
  413. for( flags = 1; flags < 16; flags++ )
  414. {
  415. // test #8 is not interesting (because no ole1
  416. // formats are offered on the clipboard
  417. if( (Ole1TestFlags)flags == OLE1_OWNERLINK_PRECEDES_NATIVE )
  418. {
  419. continue;
  420. }
  421. // setup the OLE1 mode desired
  422. pGenData->SetupOle1Mode((Ole1TestFlags)flags);
  423. hresult = pGenData->SetOle1ToClipboard();
  424. if( hresult != NOERROR )
  425. {
  426. goto errRtn;
  427. }
  428. // log the formats that are currently on the clipboard
  429. DumpClipboardFormats(vApp.m_fpLog);
  430. // get the fake clipboard data object
  431. hresult = OleGetClipboard(&pDataObj);
  432. if( hresult != NOERROR )
  433. {
  434. OutputString("Ole1Clip1: OleGetClipboard failed! "
  435. "(%lx)\r\n", hresult);
  436. goto errRtn;
  437. }
  438. hresult = pDataObj->EnumFormatEtc(DATADIR_GET, &penum);
  439. if( hresult != NOERROR )
  440. {
  441. OutputString("Ole1Clip1: EnumFormatEtc failed! "
  442. "(%lx)\r\n", hresult);
  443. goto errRtn;
  444. }
  445. while( penum->Next( 1, &formatetc, NULL ) == NOERROR )
  446. {
  447. DumpFormatetc(&formatetc, vApp.m_fpLog);
  448. #ifdef WIN32
  449. hresult = pDataObj->GetData(&formatetc, &medium);
  450. if( hresult != NOERROR )
  451. {
  452. goto errRtn;
  453. }
  454. // verify the data
  455. if( !pGenData->VerifyFormatAndMedium(&formatetc,
  456. &medium) )
  457. {
  458. hresult = ResultFromScode(E_FAIL);
  459. OutputString("Ole1Clip1: retrieved data "
  460. "doesn't match! cf == %d\r\n",
  461. formatetc.cfFormat);
  462. goto errRtn;
  463. }
  464. ReleaseStgMedium(&medium);
  465. memset(&medium, 0, sizeof(STGMEDIUM));
  466. #endif // WIN32
  467. }
  468. // now release everything
  469. penum->Release();
  470. penum = NULL;
  471. pDataObj->Release();
  472. pDataObj = NULL;
  473. }
  474. errRtn:
  475. if( penum )
  476. {
  477. penum->Release();
  478. }
  479. if( pDataObj )
  480. {
  481. pDataObj->Release();
  482. }
  483. if( pGenData )
  484. {
  485. pGenData->Release();
  486. }
  487. return hresult;
  488. }
  489. //+-------------------------------------------------------------------------
  490. //
  491. // Function: LEOle1ClipTest2
  492. //
  493. // Synopsis: Tests OLE1 container support via the clipboard
  494. //
  495. // Effects:
  496. //
  497. // Arguments:
  498. //
  499. // Requires:
  500. //
  501. // Returns:
  502. //
  503. // Signals:
  504. //
  505. // Modifies:
  506. //
  507. // Algorithm: Start cntroutl, tell it to copy a simpsvr object to the
  508. // clipboard. Check the clipboard to make sure OLE1 formats
  509. // are available.
  510. //
  511. // We do this by sheduling a function to check the clipboard
  512. // after we've launched the standard copy-to-clipboard
  513. // routines.
  514. //
  515. // History: dd-mmm-yy Author Comment
  516. // 16-Jun-94 alexgo author
  517. //
  518. // Notes:
  519. //
  520. //--------------------------------------------------------------------------
  521. void LEOle1ClipTest2( void *pv )
  522. {
  523. // this will get triggered by the return of WM_TEST1 from
  524. // container outline
  525. vApp.m_TaskStack.Push(RunApi, (void *)LEOle1ClipTest2Callback);
  526. vApp.m_TaskStack.Push(LETest1, (void *)&letiClipTest);
  527. // now post a message to ourselves to get things rollling
  528. PostMessage(vApp.m_hwndMain, WM_TEST1, 0, 0);
  529. return;
  530. }
  531. //+-------------------------------------------------------------------------
  532. //
  533. // Function: LEOle1ClipTest2Callback
  534. //
  535. // Synopsis: checks the clipboard for OLE1 formats
  536. //
  537. // Effects:
  538. //
  539. // Arguments: [pv] -- unused
  540. //
  541. // Requires:
  542. //
  543. // Returns:
  544. //
  545. // Signals:
  546. //
  547. // Modifies:
  548. //
  549. // Algorithm:
  550. //
  551. // History: dd-mmm-yy Author Comment
  552. // 20-Aug-94 alexgo updated to cfObjectLink test
  553. // 16-Jun-94 alexgo author
  554. //
  555. // Notes:
  556. //
  557. //--------------------------------------------------------------------------
  558. HRESULT LEOle1ClipTest2Callback( void )
  559. {
  560. HRESULT hresult;
  561. IDataObject * pDO;
  562. IEnumFORMATETC *penum;
  563. FORMATETC formatetc;
  564. BOOL fGotNative = FALSE,
  565. fGotOwnerLink = FALSE,
  566. fGotObjectLink = FALSE;
  567. UINT cfNative,
  568. cfOwnerLink,
  569. cfObjectLink;
  570. cfNative = RegisterClipboardFormat("Native");
  571. cfOwnerLink = RegisterClipboardFormat("OwnerLink");
  572. cfObjectLink = RegisterClipboardFormat("ObjectLink");
  573. assert(vApp.m_message == WM_TEST1);
  574. hresult = (HRESULT)vApp.m_wparam;
  575. if( hresult != NOERROR )
  576. {
  577. return hresult;
  578. }
  579. // we need to wait for cntroutl to shut down before
  580. // fetching the clipboard
  581. while( (hresult = OleGetClipboard(&pDO)) != NOERROR )
  582. {
  583. if( hresult != ResultFromScode(CLIPBRD_E_CANT_OPEN) )
  584. {
  585. return hresult;
  586. }
  587. }
  588. hresult = pDO->EnumFormatEtc(DATADIR_GET, &penum);
  589. if( hresult != NOERROR )
  590. {
  591. return hresult;
  592. }
  593. while( penum->Next(1, &formatetc, NULL) == NOERROR )
  594. {
  595. if( formatetc.cfFormat == cfNative )
  596. {
  597. fGotNative = TRUE;
  598. }
  599. else if( formatetc.cfFormat == cfOwnerLink )
  600. {
  601. fGotOwnerLink = TRUE;
  602. }
  603. else if( formatetc.cfFormat == cfObjectLink )
  604. {
  605. fGotObjectLink = TRUE;
  606. }
  607. }
  608. penum->Release();
  609. pDO->Release();
  610. // the OLE1 container compatibility code should put
  611. // OLE1 formats on the clipboard. However, they should NOT
  612. // be in the enumerator since the stuff was copied from
  613. // an OLE2 container.
  614. if( (fGotNative || fGotOwnerLink || fGotObjectLink) )
  615. {
  616. hresult = ResultFromScode(E_FAIL);
  617. return hresult;
  618. }
  619. if( IsClipboardFormatAvailable(cfNative) )
  620. {
  621. fGotNative = TRUE;
  622. }
  623. if( IsClipboardFormatAvailable(cfOwnerLink) )
  624. {
  625. fGotOwnerLink = TRUE;
  626. }
  627. if( IsClipboardFormatAvailable(cfObjectLink) )
  628. {
  629. fGotObjectLink = TRUE;
  630. }
  631. // NB!! only Native and OwnerLink should be on the clipboard
  632. // this test puts an OLE2 *embedding* on the clipbaord, which
  633. // an OLE1 container cannot link to. So ObjectLink should not
  634. // be available
  635. if( !(fGotNative && fGotOwnerLink && !fGotObjectLink) )
  636. {
  637. hresult = ResultFromScode(E_FAIL);
  638. }
  639. return hresult;
  640. }
  641. //+-------------------------------------------------------------------------
  642. //
  643. // Function: StressOleFlushClipboard
  644. //
  645. // Synopsis:
  646. //
  647. // Effects:
  648. //
  649. // Arguments: void
  650. //
  651. // Requires:
  652. //
  653. // Returns: HRESULT
  654. //
  655. // Signals:
  656. //
  657. // Modifies:
  658. //
  659. // Algorithm: stresses the following cases:
  660. // 1. Caller is not the clipboard owner (somebody else put
  661. // data on the clipboard)
  662. // 2. somebody else has the clipboard open
  663. // 3. OleFlushClipboard is called twice (second attempt should
  664. // not fail).
  665. //
  666. // History: dd-mmm-yy Author Comment
  667. // 28-Mar-94 alexgo author
  668. //
  669. // Notes:
  670. //
  671. //--------------------------------------------------------------------------
  672. HRESULT StressOleFlushClipboard(void)
  673. {
  674. HRESULT hresult;
  675. CGenDataObject *pDO;
  676. ULONG cRefs;
  677. OutputString("Now stressing OleFlushClipboard() \r\n");
  678. pDO = new CGenDataObject();
  679. assert(pDO);
  680. pDO->AddRef(); //initial count of 1
  681. //take ownership of the clipboard
  682. if( !OpenClipboard(vApp.m_hwndMain) )
  683. {
  684. OutputString("Can't OpenClipboard! \r\n");
  685. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  686. }
  687. if( !EmptyClipboard() )
  688. {
  689. OutputString("Can't EmptyClipboard! \r\n");
  690. return ResultFromScode(CLIPBRD_E_CANT_EMPTY);
  691. }
  692. if( !CloseClipboard() )
  693. {
  694. OutputString("Can't CloseClipboard! \r\n");
  695. return ResultFromScode(CLIPBRD_E_CANT_CLOSE);
  696. }
  697. // now to flush the clipboard; we should get E_FAIL
  698. hresult = OleFlushClipboard();
  699. if( hresult != ResultFromScode(E_FAIL) )
  700. {
  701. OutputString("Unexpected hresult:(%lx)\r\n", hresult);
  702. return (hresult) ? hresult : ResultFromScode(E_UNEXPECTED);
  703. }
  704. // now put something on the clipboard so we can flush it
  705. hresult = OleSetClipboard(pDO);
  706. if( hresult != NOERROR )
  707. {
  708. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  709. return hresult;
  710. }
  711. // open the clipboard with us
  712. if( !OpenClipboard(vApp.m_hwndMain) )
  713. {
  714. OutputString("Can't OpenClipboard!\r\n");
  715. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  716. }
  717. // OleFlushClipboard should return with CLIPBRD_E_CANT_OPEN
  718. // since another window has the clipboard open
  719. hresult = OleFlushClipboard();
  720. if( hresult != ResultFromScode(CLIPBRD_E_CANT_OPEN) )
  721. {
  722. OutputString("Unexpected hresult:(%lx)\r\n", hresult);
  723. return (hresult)? hresult :ResultFromScode(E_UNEXPECTED);
  724. }
  725. cRefs = pDO->AddRef();
  726. // cRefs should be 3 (one from beginning, one from OleSetClipboard
  727. // and 1 from above. OleFlushClipboard should *not* remove the
  728. // count for the above failure case)
  729. if( cRefs != 3 )
  730. {
  731. OutputString("Bad ref count, was %lu, should be 3\r\n",
  732. cRefs);
  733. return ResultFromScode(E_FAIL);
  734. }
  735. // undo the most recent addref above
  736. pDO->Release();
  737. // close the clipboard
  738. if( !CloseClipboard() )
  739. {
  740. OutputString("Can't CloseClipboard!\r\n");
  741. return ResultFromScode(CLIPBRD_E_CANT_CLOSE);
  742. }
  743. // now call OleFlushClipboard for real
  744. hresult = OleFlushClipboard();
  745. if( hresult != NOERROR )
  746. {
  747. OutputString("OleFlushClipboard failed! (%lx)\r\n", hresult);
  748. return hresult;
  749. }
  750. // now call it once more
  751. hresult = OleFlushClipboard();
  752. if( hresult != NOERROR )
  753. {
  754. OutputString("Second call to OleFlushClipboard should not"
  755. "have failed! (%lx)\r\n", hresult);
  756. return hresult;
  757. }
  758. // there should have only been 1 release from the first
  759. // OleFlushClipboard call. This next release should nuke the object
  760. cRefs = pDO->Release();
  761. if( cRefs != 0 )
  762. {
  763. OutputString("Bad ref count, was %lu, should be 0\r\n", cRefs);
  764. return ResultFromScode(E_FAIL);
  765. }
  766. return NOERROR;
  767. }
  768. //+-------------------------------------------------------------------------
  769. //
  770. // Function: StressOleGetClipboard
  771. //
  772. // Synopsis:
  773. //
  774. // Effects:
  775. //
  776. // Arguments: void
  777. //
  778. // Requires:
  779. //
  780. // Returns: HRESULT
  781. //
  782. // Signals:
  783. //
  784. // Modifies:
  785. //
  786. // Algorithm: tests the following cases:
  787. // 1. somebody else has the clipboard open
  788. //
  789. // History: dd-mmm-yy Author Comment
  790. // 28-Mar-94 alexgo author
  791. //
  792. // Notes:
  793. //
  794. //--------------------------------------------------------------------------
  795. HRESULT StressOleGetClipboard(void)
  796. {
  797. HRESULT hresult;
  798. IDataObject * pIDO;
  799. CGenDataObject *pDO;
  800. ULONG cRefs;
  801. OutputString("Stressing OleGetClipboard()\r\n");
  802. pDO = new CGenDataObject();
  803. assert(pDO);
  804. pDO->AddRef();
  805. hresult = OleSetClipboard(pDO);
  806. if( hresult != NOERROR )
  807. {
  808. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  809. return hresult;
  810. }
  811. if( !OpenClipboard(vApp.m_hwndMain) )
  812. {
  813. OutputString("Can't OpenClipboard!\r\n");
  814. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  815. }
  816. hresult = OleGetClipboard(&pIDO);
  817. if( hresult != ResultFromScode(CLIPBRD_E_CANT_OPEN) )
  818. {
  819. OutputString("Unexpected hresult (%lx)\r\n", hresult);
  820. return (hresult) ? hresult : ResultFromScode(E_UNEXPECTED);
  821. }
  822. // the ref count should not have gone up
  823. cRefs = pDO->AddRef();
  824. if( cRefs != 3 )
  825. {
  826. OutputString("Bad ref count, was %lu, should be 3\r\n", cRefs);
  827. return ResultFromScode(E_FAIL);
  828. }
  829. pDO->Release();
  830. // now clear stuff out and go home
  831. if( !CloseClipboard() )
  832. {
  833. OutputString("CloseClipboard failed!\r\n");
  834. return ResultFromScode(E_FAIL);
  835. }
  836. // this should clear the clipboard
  837. hresult = OleSetClipboard(NULL);
  838. if( hresult != NOERROR )
  839. {
  840. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  841. return hresult;
  842. }
  843. // this should be the final release on the object
  844. cRefs = pDO->Release();
  845. if( cRefs != 0 )
  846. {
  847. OutputString("Bad ref count, was %lu, should be 0\r\n", cRefs);
  848. return ResultFromScode(E_FAIL);
  849. }
  850. return NOERROR;
  851. }
  852. //+-------------------------------------------------------------------------
  853. //
  854. // Function: StressOleIsCurrentClipboard
  855. //
  856. // Synopsis:
  857. //
  858. // Effects:
  859. //
  860. // Arguments: void
  861. //
  862. // Requires:
  863. //
  864. // Returns: HRESULT
  865. //
  866. // Signals:
  867. //
  868. // Modifies:
  869. //
  870. // Algorithm: tests the following cases
  871. // 1. the caller is not the clipboard owner
  872. // 2. somebody else has the clipboard open
  873. // 2. the data object is NULL
  874. // 3. the data object is not the data object put on the clipboard
  875. //
  876. // History: dd-mmm-yy Author Comment
  877. // 28-Mar-94 alexgo author
  878. //
  879. // Notes:
  880. //
  881. //--------------------------------------------------------------------------
  882. HRESULT StressOleIsCurrentClipboard(void)
  883. {
  884. HRESULT hresult;
  885. CGenDataObject *pDO, *pDO2;
  886. ULONG cRefs;
  887. OutputString("Stressing OleIsCurrentClipboard()\r\n");
  888. pDO = new CGenDataObject();
  889. pDO2 = new CGenDataObject();
  890. assert(pDO);
  891. assert(pDO2);
  892. pDO->AddRef();
  893. pDO2->AddRef();
  894. //take ownership of the clipboard
  895. if( !OpenClipboard(vApp.m_hwndMain) )
  896. {
  897. OutputString("Can't OpenClipboard! \r\n");
  898. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  899. }
  900. if( !EmptyClipboard() )
  901. {
  902. OutputString("Can't EmptyClipboard! \r\n");
  903. return ResultFromScode(CLIPBRD_E_CANT_EMPTY);
  904. }
  905. if( !CloseClipboard() )
  906. {
  907. OutputString("Can't CloseClipboard! \r\n");
  908. return ResultFromScode(CLIPBRD_E_CANT_CLOSE);
  909. }
  910. // now to flush the clipboard; we should get S_FALSE
  911. hresult = OleIsCurrentClipboard(pDO);
  912. if( hresult != ResultFromScode(S_FALSE) )
  913. {
  914. OutputString("Unexpected hresult:(%lx)\r\n", hresult);
  915. return (hresult) ? hresult : ResultFromScode(E_UNEXPECTED);
  916. }
  917. // now set the clipboard and test w/ the clipboard open
  918. // we should not fail in this case
  919. hresult = OleSetClipboard(pDO);
  920. if( hresult != NOERROR )
  921. {
  922. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  923. return hresult;
  924. }
  925. if( !OpenClipboard(vApp.m_hwndMain) )
  926. {
  927. OutputString("Can't OpenClipboard!\r\n");
  928. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  929. }
  930. hresult = OleIsCurrentClipboard(pDO);
  931. if( hresult != NOERROR )
  932. {
  933. OutputString("Unexpected hresult (%lx)\r\n", hresult);
  934. return (hresult) ? hresult : ResultFromScode(E_UNEXPECTED);
  935. }
  936. // the ref count should not have gone up
  937. cRefs = pDO->AddRef();
  938. if( cRefs != 3 )
  939. {
  940. OutputString("Bad ref count, was %lu, should be 3\r\n", cRefs);
  941. return ResultFromScode(E_FAIL);
  942. }
  943. pDO->Release();
  944. // now close the clipboard
  945. if( !CloseClipboard() )
  946. {
  947. OutputString("CloseClipboard failed!\r\n");
  948. return ResultFromScode(E_FAIL);
  949. }
  950. // now test for passing NULL
  951. hresult = OleIsCurrentClipboard(NULL);
  952. if( hresult != ResultFromScode(S_FALSE) )
  953. {
  954. OutputString("Unexpected hresult (%lx)\r\n", hresult);
  955. return (hresult)? hresult : ResultFromScode(E_FAIL);
  956. }
  957. // now test for passign other pointer
  958. hresult = OleIsCurrentClipboard(pDO2);
  959. if( hresult != ResultFromScode(S_FALSE) )
  960. {
  961. OutputString("Unexpected hresult (%lx)\r\n", hresult);
  962. return (hresult)? hresult : ResultFromScode(E_FAIL);
  963. }
  964. // now clean stuff up and go home
  965. hresult = OleSetClipboard(NULL);
  966. if( hresult != NOERROR )
  967. {
  968. OutputString("OleSetClipboard(NULL) failed!! (%lx)\r\n",
  969. hresult);
  970. return hresult;
  971. }
  972. cRefs = pDO->Release();
  973. // cRefs should be 0 now
  974. if( cRefs != 0 )
  975. {
  976. OutputString("Bad ref count, was %lu, should be 0\r\n", cRefs);
  977. return ResultFromScode(E_FAIL);
  978. }
  979. pDO2->Release();
  980. return NOERROR;
  981. }
  982. //+-------------------------------------------------------------------------
  983. //
  984. // Function: StressOleSetClipboard
  985. //
  986. // Synopsis:
  987. //
  988. // Effects:
  989. //
  990. // Arguments: void
  991. //
  992. // Requires:
  993. //
  994. // Returns: HRESULT
  995. //
  996. // Signals:
  997. //
  998. // Modifies:
  999. //
  1000. // Algorithm: tests the following cases:
  1001. // 1. somebody else has the clipboard open
  1002. // 2. Do OleSetClipboard with data and then
  1003. // OleSetClipboard(NULL) to clear it out
  1004. //
  1005. // History: dd-mmm-yy Author Comment
  1006. // 28-Mar-94 alexgo author
  1007. //
  1008. // Notes:
  1009. //
  1010. //--------------------------------------------------------------------------
  1011. HRESULT StressOleSetClipboard(void)
  1012. {
  1013. HRESULT hresult;
  1014. CGenDataObject *pDO;
  1015. ULONG cRefs;
  1016. OutputString("Stressing OleGetClipboard()\r\n");
  1017. pDO = new CGenDataObject();
  1018. assert(pDO);
  1019. pDO->AddRef();
  1020. if( !OpenClipboard(vApp.m_hwndMain) )
  1021. {
  1022. OutputString("Can't OpenClipboard!\r\n");
  1023. return ResultFromScode(CLIPBRD_E_CANT_OPEN);
  1024. }
  1025. hresult = OleSetClipboard(pDO);
  1026. if( hresult != ResultFromScode(CLIPBRD_E_CANT_OPEN) )
  1027. {
  1028. OutputString("Unexpected hresult (%lx)\r\n", hresult);
  1029. return (hresult) ? hresult : ResultFromScode(E_UNEXPECTED);
  1030. }
  1031. // the ref count should not have gone up
  1032. cRefs = pDO->AddRef();
  1033. if( cRefs != 2 )
  1034. {
  1035. OutputString("Bad ref count, was %lu, should be 2\r\n", cRefs);
  1036. return ResultFromScode(E_FAIL);
  1037. }
  1038. pDO->Release();
  1039. if( !CloseClipboard() )
  1040. {
  1041. OutputString("CloseClipboard failed!\r\n");
  1042. return ResultFromScode(E_FAIL);
  1043. }
  1044. // now really set the clipboard so we can try to clear it
  1045. hresult = OleSetClipboard(pDO);
  1046. if( hresult != NOERROR )
  1047. {
  1048. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  1049. return hresult;
  1050. }
  1051. // this should clear the clipboard
  1052. hresult = OleSetClipboard(NULL);
  1053. if( hresult != NOERROR )
  1054. {
  1055. OutputString("OleSetClipboard failed! (%lx)\r\n", hresult);
  1056. return hresult;
  1057. }
  1058. // this should be the final release on the object
  1059. cRefs = pDO->Release();
  1060. if( cRefs != 0 )
  1061. {
  1062. OutputString("Bad ref count, was %lu, should be 0\r\n", cRefs);
  1063. return ResultFromScode(E_FAIL);
  1064. }
  1065. return NOERROR;
  1066. }
  1067. //+-------------------------------------------------------------------------
  1068. //
  1069. // Function: TestOleQueryCreateFromDataMFCHack
  1070. //
  1071. // Synopsis: tests the MFC hack put into OleQueryCreateFromData
  1072. //
  1073. // Effects:
  1074. //
  1075. // Arguments: void
  1076. //
  1077. // Requires:
  1078. //
  1079. // Returns: HRESULT
  1080. //
  1081. // Signals:
  1082. //
  1083. // Modifies:
  1084. //
  1085. // Algorithm: create a data object that offers private data
  1086. // put on the clipboard and then retrieve the clipboard data
  1087. // object.
  1088. // Call OleQueryCreateFromData on clipboard data object--
  1089. // QI for IPS should not be called
  1090. // Call OleQueryCreateFromData on generic data object
  1091. // QI for IPS should be called
  1092. // set EmbeddedObject on the generic data object
  1093. // Call OleQueryCreateFromData; should return S_OK
  1094. //
  1095. // History: dd-mmm-yy Author Comment
  1096. // 23-Aug-94 alexgo author
  1097. //
  1098. // Notes:
  1099. //
  1100. //--------------------------------------------------------------------------
  1101. HRESULT TestOleQueryCreateFromDataMFCHack( void )
  1102. {
  1103. CGenDataObject * pgendata;
  1104. IDataObject * pdataobj;
  1105. HRESULT hresult;
  1106. pgendata = new CGenDataObject();
  1107. assert(pgendata);
  1108. pgendata->AddRef();
  1109. pgendata->SetDataFormats(OFFER_TESTSTORAGE);
  1110. hresult = OleSetClipboard(pgendata);
  1111. if( hresult != NOERROR )
  1112. {
  1113. return hresult;
  1114. }
  1115. hresult = OleGetClipboard(&pdataobj);
  1116. if( hresult != NOERROR )
  1117. {
  1118. return hresult;
  1119. }
  1120. hresult = OleQueryCreateFromData(pdataobj);
  1121. // for a clipboard data object, we should not call QueryInterface
  1122. // for IPersistStorage.
  1123. if( hresult != S_FALSE || pgendata->HasQIBeenCalled() == TRUE )
  1124. {
  1125. return ResultFromScode(E_FAIL);
  1126. }
  1127. // for other data objects, if there are no OLE2 formats, then
  1128. // we should call QI for IPersistStorage
  1129. hresult = OleQueryCreateFromData(pgendata);
  1130. if( hresult != S_FALSE || pgendata->HasQIBeenCalled() == FALSE )
  1131. {
  1132. return ResultFromScode(E_FAIL);
  1133. }
  1134. // now clear the clipboard and continue testing
  1135. pdataobj->Release();
  1136. hresult = OleSetClipboard(NULL);
  1137. if( hresult != NOERROR )
  1138. {
  1139. return hresult;
  1140. }
  1141. pgendata->SetDataFormats(OFFER_EMBEDDEDOBJECT);
  1142. hresult = OleQueryCreateFromData(pgendata);
  1143. // we just set OLE2 data on the data object. OQCFD should return
  1144. // S_OK
  1145. if( hresult != NOERROR )
  1146. {
  1147. return ResultFromScode(E_FAIL);
  1148. }
  1149. if( pgendata->Release() == 0 )
  1150. {
  1151. return NOERROR;
  1152. }
  1153. else
  1154. {
  1155. return ResultFromScode(E_FAIL);
  1156. }
  1157. }