Reactos
at master 671 lines 23 kB view raw
1/* 2 * PROJECT: ReactOS API tests 3 * LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+) 4 * PURPOSE: Test for IShellFolderViewCB 5 * COPYRIGHT: Copyright 2017 Mark Jansen (mark.jansen@reactos.org) 6 */ 7 8#include "shelltest.h" 9#include <atlsimpcoll.h> 10#include <stdio.h> 11#include <shellutils.h> 12//#include <msgtrace.h> 13 14static DWORD g_WinVersion; 15#define WINVER_VISTA 0x0600 16 17#ifndef SFVM_SELECTIONCHANGED 18#define SFVM_SELECTIONCHANGED 8 /* undocumented */ 19#define SFVM_DRAWMENUITEM 9 /* undocumented */ 20#define SFVM_MEASUREMENUITEM 10 /* undocumented */ 21#define SFVM_EXITMENULOOP 11 /* undocumented */ 22#define SFVM_VIEWRELEASE 12 /* undocumented */ 23#define SFVM_GETNAMELENGTH 13 /* undocumented */ 24#define SFVM_WINDOWCLOSING 16 /* undocumented */ 25#define SFVM_LISTREFRESHED 17 /* undocumented */ 26#define SFVM_WINDOWFOCUSED 18 /* undocumented */ 27#define SFVM_REGISTERCOPYHOOK 20 /* undocumented */ 28#define SFVM_COPYHOOKCALLBACK 21 /* undocumented */ 29#define SFVM_UNMERGEFROMMENU 28 /* undocumented */ 30#define SFVM_ADDINGOBJECT 29 /* undocumented */ 31#define SFVM_REMOVINGOBJECT 30 /* undocumented */ 32#define SFVM_GETCOMMANDDIR 33 /* undocumented */ 33#define SFVM_GETCOLUMNSTREAM 34 /* undocumented */ 34#define SFVM_CANSELECTALL 35 /* undocumented */ 35#define SFVM_ISSTRICTREFRESH 37 /* undocumented */ 36#define SFVM_ISCHILDOBJECT 38 /* undocumented */ 37#define SFVM_GETEXTVIEWS 40 /* undocumented */ 38#define SFVM_GET_CUSTOMVIEWINFO 77 /* undocumented */ 39#define SFVM_ENUMERATEDITEMS 79 /* undocumented */ 40#define SFVM_GET_VIEW_DATA 80 /* undocumented */ 41#define SFVM_GET_WEBVIEW_LAYOUT 82 /* undocumented */ 42#define SFVM_GET_WEBVIEW_CONTENT 83 /* undocumented */ 43#define SFVM_GET_WEBVIEW_TASKS 84 /* undocumented */ 44#define SFVM_GET_WEBVIEW_THEME 86 /* undocumented */ 45#define SFVM_GETDEFERREDVIEWSETTINGS 92 /* undocumented */ 46#endif 47 48#define DUM_MSG_GetWindow 400 49#define DUM_MSG_ContextSensitiveHelp 401 50#define DUM_MSG_InsertMenusSB 402 51#define DUM_MSG_SetMenuSB 403 52#define DUM_MSG_RemoveMenusSB 404 53#define DUM_MSG_SetStatusTextSB 405 54#define DUM_MSG_EnableModelessSB 406 55#define DUM_MSG_TranslateAcceleratorSB 407 56#define DUM_MSG_BrowseObject 408 57#define DUM_MSG_GetViewStateStream 409 58#define DUM_MSG_GetControlWindow 410 59#define DUM_MSG_SendControlMsg 411 60#define DUM_MSG_QueryActiveShellView 412 61#define DUM_MSG_OnViewWindowActive 413 62#define DUM_MSG_SetToolbarItems 414 63 64 65const char* msg2str(UINT uMsg) 66{ 67 static char buf[2][50]; 68 static int index = 0; 69 index ^= 1; 70 71 switch (uMsg) 72 { 73 case SFVM_MERGEMENU: return "SFVM_MERGEMENU"; 74 case SFVM_INVOKECOMMAND: return "SFVM_INVOKECOMMAND"; 75 case SFVM_GETHELPTEXT: return "SFVM_GETHELPTEXT"; 76 case SFVM_GETTOOLTIPTEXT: return "SFVM_GETTOOLTIPTEXT"; 77 case SFVM_GETBUTTONINFO: return "SFVM_GETBUTTONINFO"; 78 case SFVM_GETBUTTONS: return "SFVM_GETBUTTONS"; 79 case SFVM_INITMENUPOPUP: return "SFVM_INITMENUPOPUP"; 80 case SFVM_SELECTIONCHANGED: return "SFVM_SELECTIONCHANGED"; 81 case SFVM_DRAWMENUITEM: return "SFVM_DRAWMENUITEM"; 82 case SFVM_MEASUREMENUITEM: return "SFVM_MEASUREMENUITEM"; 83 case SFVM_EXITMENULOOP: return "SFVM_EXITMENULOOP"; 84 case SFVM_VIEWRELEASE: return "SFVM_VIEWRELEASE"; 85 case SFVM_GETNAMELENGTH: return "SFVM_GETNAMELENGTH"; 86 case SFVM_FSNOTIFY: return "SFVM_FSNOTIFY"; 87 case SFVM_WINDOWCREATED: return "SFVM_WINDOWCREATED"; 88 case SFVM_WINDOWCLOSING: return "SFVM_WINDOWCLOSING"; 89 case SFVM_LISTREFRESHED: return "SFVM_LISTREFRESHED"; 90 case SFVM_WINDOWFOCUSED: return "SFVM_WINDOWFOCUSED"; 91 case SFVM_REGISTERCOPYHOOK: return "SFVM_REGISTERCOPYHOOK"; 92 case SFVM_COPYHOOKCALLBACK: return "SFVM_COPYHOOKCALLBACK"; 93 case SFVM_GETDETAILSOF: return "SFVM_GETDETAILSOF"; 94 case SFVM_COLUMNCLICK: return "SFVM_COLUMNCLICK"; 95 case SFVM_QUERYFSNOTIFY: return "SFVM_QUERYFSNOTIFY"; 96 case SFVM_DEFITEMCOUNT: return "SFVM_DEFITEMCOUNT"; 97 case SFVM_DEFVIEWMODE: return "SFVM_DEFVIEWMODE"; 98 case SFVM_UNMERGEFROMMENU: return "SFVM_UNMERGEFROMMENU"; 99 case SFVM_ADDINGOBJECT: return "SFVM_ADDINGOBJECT"; 100 case SFVM_REMOVINGOBJECT: return "SFVM_REMOVINGOBJECT"; 101 case SFVM_UPDATESTATUSBAR: return "SFVM_UPDATESTATUSBAR"; 102 case SFVM_BACKGROUNDENUM: return "SFVM_BACKGROUNDENUM"; 103 case SFVM_GETCOMMANDDIR: return "SFVM_GETCOMMANDDIR"; 104 case SFVM_GETCOLUMNSTREAM: return "SFVM_GETCOLUMNSTREAM"; 105 case SFVM_CANSELECTALL: return "SFVM_CANSELECTALL"; 106 case SFVM_DIDDRAGDROP: return "SFVM_DIDDRAGDROP"; 107 case SFVM_ISSTRICTREFRESH: return "SFVM_ISSTRICTREFRESH"; 108 case SFVM_ISCHILDOBJECT: return "SFVM_ISCHILDOBJECT"; 109 case SFVM_SETISFV: return "SFVM_SETISFV"; 110 case SFVM_GETEXTVIEWS: return "SFVM_GETEXTVIEWS"; 111 case SFVM_THISIDLIST: return "SFVM_THISIDLIST"; 112 case SFVM_ADDPROPERTYPAGES: return "SFVM_ADDPROPERTYPAGES"; 113 case SFVM_BACKGROUNDENUMDONE: return "SFVM_BACKGROUNDENUMDONE"; 114 case SFVM_GETNOTIFY: return "SFVM_GETNOTIFY"; 115 case SFVM_GETSORTDEFAULTS: return "SFVM_GETSORTDEFAULTS"; 116 case SFVM_SIZE: return "SFVM_SIZE"; 117 case SFVM_GETZONE: return "SFVM_GETZONE"; 118 case SFVM_GETPANE: return "SFVM_GETPANE"; 119 case SFVM_GETHELPTOPIC: return "SFVM_GETHELPTOPIC"; 120 case SFVM_GETANIMATION: return "SFVM_GETANIMATION"; 121 case SFVM_GET_CUSTOMVIEWINFO: return "SFVM_GET_CUSTOMVIEWINFO"; 122 case SFVM_ENUMERATEDITEMS: return "SFVM_ENUMERATEDITEMS"; 123 case SFVM_GET_VIEW_DATA: return "SFVM_GET_VIEW_DATA"; 124 case SFVM_GET_WEBVIEW_LAYOUT: return "SFVM_GET_WEBVIEW_LAYOUT"; 125 case SFVM_GET_WEBVIEW_CONTENT: return "SFVM_GET_WEBVIEW_CONTENT"; 126 case SFVM_GET_WEBVIEW_TASKS: return "SFVM_GET_WEBVIEW_TASKS"; 127 case SFVM_GET_WEBVIEW_THEME: return "SFVM_GET_WEBVIEW_THEME"; 128 case SFVM_GETDEFERREDVIEWSETTINGS: return "SFVM_GET_WEBVIEW_THEME"; 129 130 case DUM_MSG_GetWindow: return "|GetWindow|"; 131 case DUM_MSG_ContextSensitiveHelp: return "|ContextSensitiveHelp|"; 132 case DUM_MSG_InsertMenusSB: return "|InsertMenusSB|"; 133 case DUM_MSG_SetMenuSB: return "|SetMenuSB|"; 134 case DUM_MSG_RemoveMenusSB: return "|RemoveMenusSB|"; 135 case DUM_MSG_SetStatusTextSB: return "|SetStatusTextSB|"; 136 case DUM_MSG_EnableModelessSB: return "|EnableModelessSB|"; 137 case DUM_MSG_TranslateAcceleratorSB: return "|TranslateAcceleratorSB|"; 138 case DUM_MSG_BrowseObject: return "|BrowseObject|"; 139 case DUM_MSG_GetViewStateStream: return "|GetViewStateStream|"; 140 case DUM_MSG_GetControlWindow: return "|GetControlWindow|"; 141 case DUM_MSG_SendControlMsg: return "|SendControlMsg|"; 142 case DUM_MSG_QueryActiveShellView: return "|QueryActiveShellView|"; 143 case DUM_MSG_OnViewWindowActive: return "|OnViewWindowActive|"; 144 case DUM_MSG_SetToolbarItems: return "|SetToolbarItems|"; 145 default: 146 sprintf(buf[index], "[%u]", uMsg); 147 return buf[index]; 148 } 149} 150 151 152#define PTR_VALUE 0xf7f7f7f7 153 154struct message 155{ 156 message(UINT msg, WPARAM wp, LPARAM lp) : uMsg(msg), wParam(wp), lParam(lp) { ; } 157 158 UINT uMsg; 159 WPARAM wParam; 160 LPARAM lParam; 161}; 162 163CSimpleArray<message> g_Received; 164 165void clear_list() 166{ 167 g_Received.RemoveAll(); 168} 169 170void add_msg(UINT uMsg, WPARAM wParam, LPARAM lParam) 171{ 172 g_Received.Add(message(uMsg, wParam, lParam)); 173} 174 175void print_list_(const CSimpleArray<message>& input, const char* file, int line) 176{ 177 trace_(file, line)("Got list:\n"); 178 for (int n = 0; n < input.GetSize(); ++n) 179 { 180 const message& msg = input[n]; 181 trace_(file, line)("msg: %d(%s), wParam:0x%x, lParam:0x%lx\n", msg.uMsg, msg2str(msg.uMsg), msg.wParam, msg.lParam); 182 } 183 trace_(file, line)("End of list.\n"); 184} 185 186void compare_list_(const CSimpleArray<message>& input, const message* compare, const char* file, int line) 187{ 188 int input_item = 0; 189 int compare_item = 0; 190 LONG old_failures = winetest_get_failures(); 191 while (compare[compare_item].uMsg && input_item < input.GetSize()) 192 { 193 const message& inp = input[input_item]; 194 const message& cmp = compare[compare_item]; 195 if (cmp.uMsg == inp.uMsg) 196 { 197 if (cmp.lParam != (LPARAM)PTR_VALUE) 198 { 199 ok_(file, line)(cmp.lParam == inp.lParam, "Expected lParam to be 0x%lx, was 0x%lx for %i(%s)\n", 200 cmp.lParam, inp.lParam, compare_item, msg2str(cmp.uMsg)); 201 } 202 else 203 { 204 ok_(file, line)(inp.lParam != 0, "Expected lParam to be a pointer, was 0 for %i(%s)\n", 205 compare_item, msg2str(cmp.uMsg)); 206 } 207 if (cmp.wParam != PTR_VALUE) 208 { 209 ok_(file, line)(cmp.wParam == inp.wParam, "Expected wParam to be 0x%x, was 0x%x for %i(%s)\n", 210 cmp.wParam, inp.wParam, compare_item, msg2str(cmp.uMsg)); 211 } 212 else 213 { 214 ok_(file, line)(inp.wParam != 0, "Expected wParam to be a pointer, was 0 for %i(%s)\n", 215 compare_item, msg2str(cmp.uMsg)); 216 } 217 compare_item++; 218 } 219 else 220 { 221 /* We skip unknown items for now */ 222 } 223 224 input_item++; 225 } 226 227 while (compare[compare_item].uMsg) 228 { 229 ok_(file, line)(0, "Message %i(%s) not found\n", compare_item, msg2str(compare[compare_item].uMsg)); 230 compare_item++; 231 } 232 if (old_failures != winetest_get_failures()) 233 { 234 print_list_(input, file, line); 235 } 236} 237 238#define compare_list(cmp) compare_list_(g_Received, cmp, __FILE__, __LINE__) 239#define print_list() print_list_(g_Received, __FILE__, __LINE__) 240 241 242LONG g_AddRef = 0; 243LONG g_Release = 0; 244 245class CFolderViewCB : 246 public IShellFolderViewCB 247{ 248public: 249 CFolderViewCB(void) : 250 m_RefCount(1) 251 { 252 } 253 virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid, void **ppvObject) 254 { 255 if (riid == IID_IShellFolderViewCB) 256 { 257 *ppvObject = static_cast<IShellFolderViewCB*>(this); 258 AddRef(); 259 return S_OK; 260 } 261 return E_NOINTERFACE; 262 } 263 virtual ULONG STDMETHODCALLTYPE AddRef(void) 264 { 265 InterlockedIncrement(&g_AddRef); 266 return InterlockedIncrement(&m_RefCount); 267 } 268 virtual ULONG STDMETHODCALLTYPE Release(void) 269 { 270 InterlockedIncrement(&g_Release); 271 return InterlockedDecrement(&m_RefCount); 272 } 273 virtual HRESULT STDMETHODCALLTYPE MessageSFVCB(UINT uMsg, WPARAM wParam, LPARAM lParam) 274 { 275 //DbgPrint("MessageSFVCB(uMsg:%s, wParam:%u, lParam:%u\n", msg2str(uMsg), wParam, lParam); 276 add_msg(uMsg, wParam, lParam); 277 return E_NOTIMPL; 278 } 279private: 280 LONG m_RefCount; 281}; 282 283 284static LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) 285{ 286 if (msg == WM_DESTROY) 287 { 288 PostQuitMessage(0); 289 return 0; 290 } 291 return DefWindowProc(hwnd, msg, wParam, lParam); 292} 293 294 295class CDummyShellBrowser : public IShellBrowser 296{ 297public: 298 HWND m_hwnd; 299 CDummyShellBrowser() 300 { 301 static const TCHAR* class_name = TEXT("DUMMY_TEST_CLASS"); 302 WNDCLASSEX wx = {}; 303 wx.cbSize = sizeof(WNDCLASSEX); 304 wx.lpfnWndProc = WndProc; 305 wx.hInstance = GetModuleHandle(NULL); 306 wx.lpszClassName = class_name; 307 wx.style = CS_DBLCLKS; 308 RegisterClassEx(&wx); 309 m_hwnd = CreateWindowEx(0, class_name, TEXT("dummy_name"), WS_OVERLAPPEDWINDOW, 0, 0, 0, 0, NULL, NULL, NULL, NULL); 310 ShowWindow(m_hwnd, SW_SHOW); 311 } 312 313 // *** IUnknown methods *** 314 virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid, void **ppvObject) 315 { 316 if (riid == IID_IShellBrowser || riid == IID_IUnknown) 317 { 318 *ppvObject = this; 319 return S_OK; 320 } 321 return E_NOINTERFACE; 322 } 323 virtual ULONG STDMETHODCALLTYPE AddRef(void) 324 { 325 return 2; 326 } 327 virtual ULONG STDMETHODCALLTYPE Release(void) 328 { 329 return 1; 330 } 331 332 // *** IOleWindow methods *** 333 virtual HRESULT STDMETHODCALLTYPE GetWindow(HWND *phwnd) 334 { 335 //DbgPrint("%s()\n", __FUNCTION__); 336 *phwnd = m_hwnd; 337 add_msg(DUM_MSG_GetWindow, NULL, NULL); 338 return S_OK; 339 } 340 virtual HRESULT STDMETHODCALLTYPE ContextSensitiveHelp(BOOL fEnterMode) 341 { 342 //DbgPrint("%s()\n", __FUNCTION__); 343 add_msg(DUM_MSG_ContextSensitiveHelp, NULL, NULL); 344 return E_NOTIMPL; 345 } 346 347 // *** IShellBrowser methods *** 348 virtual HRESULT STDMETHODCALLTYPE InsertMenusSB(HMENU hmenuShared, LPOLEMENUGROUPWIDTHS lpMenuWidths) 349 { 350 //DbgPrint("%s()\n", __FUNCTION__); 351 add_msg(DUM_MSG_InsertMenusSB, NULL, NULL); 352 return S_OK; 353 } 354 virtual HRESULT STDMETHODCALLTYPE SetMenuSB(HMENU hmenuShared, HOLEMENU holemenuRes, HWND hwndActiveObject) 355 { 356 //DbgPrint("%s()\n", __FUNCTION__); 357 add_msg(DUM_MSG_SetMenuSB, NULL, NULL); 358 return S_OK; 359 } 360 virtual HRESULT STDMETHODCALLTYPE RemoveMenusSB(HMENU hmenuShared) 361 { 362 //DbgPrint("%s()\n", __FUNCTION__); 363 add_msg(DUM_MSG_RemoveMenusSB, NULL, NULL); 364 return E_NOTIMPL; 365 } 366 virtual HRESULT STDMETHODCALLTYPE SetStatusTextSB(LPCWSTR pszStatusText) 367 { 368 //DbgPrint("%s()\n", __FUNCTION__); 369 add_msg(DUM_MSG_SetStatusTextSB, NULL, NULL); 370 return E_NOTIMPL; 371 } 372 virtual HRESULT STDMETHODCALLTYPE EnableModelessSB(BOOL fEnable) 373 { 374 //DbgPrint("%s()\n", __FUNCTION__); 375 add_msg(DUM_MSG_EnableModelessSB, NULL, NULL); 376 return E_NOTIMPL; 377 } 378 virtual HRESULT STDMETHODCALLTYPE TranslateAcceleratorSB(MSG *pmsg, WORD wID) 379 { 380 //DbgPrint("%s()\n", __FUNCTION__); 381 add_msg(DUM_MSG_TranslateAcceleratorSB, NULL, NULL); 382 return E_NOTIMPL; 383 } 384 virtual HRESULT STDMETHODCALLTYPE BrowseObject(PCUIDLIST_RELATIVE pidl,UINT wFlags) 385 { 386 //DbgPrint("%s()\n", __FUNCTION__); 387 add_msg(DUM_MSG_BrowseObject, NULL, NULL); 388 return E_NOTIMPL; 389 } 390 virtual HRESULT STDMETHODCALLTYPE GetViewStateStream(DWORD grfMode,IStream **ppStrm) 391 { 392 //DbgPrint("%s()\n", __FUNCTION__); 393 add_msg(DUM_MSG_GetViewStateStream, NULL, NULL); 394 return E_NOTIMPL; 395 } 396 virtual HRESULT STDMETHODCALLTYPE GetControlWindow(UINT id,HWND *phwnd) 397 { 398 //DbgPrint("%s()\n", __FUNCTION__); 399 add_msg(DUM_MSG_GetControlWindow, NULL, NULL); 400 return E_NOTIMPL; 401 } 402 virtual HRESULT STDMETHODCALLTYPE SendControlMsg(UINT id,UINT uMsg,WPARAM wParam,LPARAM lParam,LRESULT *pret) 403 { 404 //DbgPrint("%s()\n", __FUNCTION__); 405 add_msg(DUM_MSG_SendControlMsg, NULL, NULL); 406 return E_NOTIMPL; 407 } 408 virtual HRESULT STDMETHODCALLTYPE QueryActiveShellView(IShellView **ppshv) 409 { 410 //DbgPrint("%s()\n", __FUNCTION__); 411 add_msg(DUM_MSG_QueryActiveShellView, NULL, NULL); 412 return E_NOTIMPL; 413 } 414 virtual HRESULT STDMETHODCALLTYPE OnViewWindowActive(IShellView *pshv) 415 { 416 //DbgPrint("%s()\n", __FUNCTION__); 417 add_msg(DUM_MSG_OnViewWindowActive, NULL, NULL); 418 return E_NOTIMPL; 419 } 420 virtual HRESULT STDMETHODCALLTYPE SetToolbarItems(LPTBBUTTONSB lpButtons,UINT nButtons,UINT uFlags) 421 { 422 //DbgPrint("%s()\n", __FUNCTION__); 423 add_msg(DUM_MSG_SetToolbarItems, NULL, NULL); 424 return E_NOTIMPL; 425 } 426}; 427 428 429START_TEST(IShellFolderViewCB) 430{ 431 RTL_OSVERSIONINFOEXW rtlinfo = { sizeof(rtlinfo) }; 432 void (__stdcall* pRtlGetVersion)(RTL_OSVERSIONINFOEXW*); 433 pRtlGetVersion = (void (__stdcall*)(RTL_OSVERSIONINFOEXW*))GetProcAddress(GetModuleHandleA("ntdll"), "RtlGetVersion"); 434 pRtlGetVersion(&rtlinfo); 435 g_WinVersion = (rtlinfo.dwMajorVersion << 8) | rtlinfo.dwMinorVersion; 436 437 CoInitialize(NULL); 438 CFolderViewCB cb; 439 440 CComPtr<IShellFolder> desktop; 441 442 HRESULT hr = SHGetDesktopFolder(&desktop); 443 ok_hex(hr, S_OK); 444 if (!desktop) 445 return; 446 447 SFV_CREATE sfvc = { sizeof(sfvc), desktop }; 448 sfvc.psfvcb = &cb; 449 IShellView* psv = NULL; 450 451 g_AddRef = 0; 452 g_Release = 0; 453 454 hr = SHCreateShellFolderView(&sfvc, &psv); 455 ok_hex(hr, S_OK); 456 if (!SUCCEEDED(hr)) 457 return; 458 459 ok(g_AddRef == 2 || // Win7+ 460 g_AddRef == 1, // Win2k3-Vista 461 "Wrong value for g_AddRef (0x%lX)\n", g_AddRef); 462 ok_int(g_Release, 0); 463 464 clear_list(); 465 466 HWND wnd; 467 RECT rc = { 0 }; 468 FOLDERSETTINGS fs = { FVM_DETAILS, 0 }; 469 CDummyShellBrowser dum; 470 hr = psv->CreateViewWindow(NULL, &fs, &dum, &rc, &wnd); 471 472 473 static message init_list[] = 474 { 475 /* ... */ 476 message(DUM_MSG_GetWindow, 0, 0), 477 /* Some unknown messages here, and multiple SFVM_GET_WEBVIEW_THEME + SFVM_GETSORTDEFAULTS + SFVM_GETCOLUMNSTREAM */ 478 message(SFVM_SIZE, 0, 0), 479 /* ... */ 480 message(DUM_MSG_InsertMenusSB, 0, 0), 481 message(SFVM_MERGEMENU, 0, PTR_VALUE), 482 message(DUM_MSG_SetMenuSB, 0, 0), 483 /* ... */ 484 message(SFVM_WINDOWCREATED, PTR_VALUE, 0), 485 /* ... */ 486 487 message(SFVM_GETBUTTONINFO, 0, PTR_VALUE), 488 message(SFVM_GETBUTTONS, PTR_VALUE, PTR_VALUE), 489 message(DUM_MSG_SetToolbarItems, 0, 0), 490 491 message(0, 0, 0) 492 }; 493 494 495 static message init_list_vista[] = 496 { 497 /* Some unknown messages here */ 498 message(DUM_MSG_GetWindow, 0, 0), 499 /* Some unknown messages here, and multiple SFVM_GET_WEBVIEW_THEME + SFVM_GETSORTDEFAULTS + SFVM_GETCOLUMNSTREAM */ 500 message(SFVM_SIZE, 0, 0), 501 message(SFVM_WINDOWCREATED, PTR_VALUE, 0), 502 /* Some unknown messages here */ 503 message(DUM_MSG_InsertMenusSB, 0, 0), 504 message(SFVM_MERGEMENU, 0, PTR_VALUE), 505 message(DUM_MSG_SetMenuSB, 0, 0), 506 507 message(0, 0, 0) 508 }; 509 510 if (g_WinVersion < WINVER_VISTA) 511 { 512 compare_list(init_list); 513 } 514 else 515 { 516 compare_list(init_list_vista); 517 } 518 clear_list(); 519 520 hr = psv->Refresh(); 521 //ok_hex(hr, S_FALSE); 522 523 static message refresh_list[] = 524 { 525 message(SFVM_LISTREFRESHED, 1, 0), 526 527 message(SFVM_UNMERGEFROMMENU, 0, PTR_VALUE), 528 message(DUM_MSG_SetMenuSB, 0, 0), 529 message(DUM_MSG_RemoveMenusSB, 0, 0), 530 message(DUM_MSG_InsertMenusSB, 0, 0), 531 message(SFVM_MERGEMENU, 0, PTR_VALUE), 532 message(DUM_MSG_SetMenuSB, 0, 0), 533 534 message(0, 0, 0) 535 }; 536 537 static message refresh_list_vista[] = 538 { 539 message(SFVM_LISTREFRESHED, 1, 0), 540 541 message(SFVM_UNMERGEFROMMENU, 0, PTR_VALUE), 542 message(DUM_MSG_SetMenuSB, 0, 0), 543 message(DUM_MSG_RemoveMenusSB, 0, 0), 544 message(DUM_MSG_InsertMenusSB, 0, 0), 545 message(SFVM_MERGEMENU, 0, PTR_VALUE), 546 message(DUM_MSG_SetMenuSB, 0, 0), 547 /* Some messages here, like SFVM_GET_WEBVIEW_THEME, SFVM_GETSORTDEFAULTS, SFVM_GETCOLUMNSTREAM */ 548 message(SFVM_UNMERGEFROMMENU, 0, PTR_VALUE), 549 message(DUM_MSG_SetMenuSB, 0, 0), 550 message(DUM_MSG_RemoveMenusSB, 0, 0), 551 message(DUM_MSG_InsertMenusSB, 0, 0), 552 message(SFVM_MERGEMENU, 0, PTR_VALUE), 553 message(DUM_MSG_SetMenuSB, 0, 0), 554 555 message(0, 0, 0) 556 }; 557 558 if (g_WinVersion < WINVER_VISTA) 559 { 560 compare_list(refresh_list); 561 } 562 else 563 { 564 compare_list(refresh_list_vista); 565 } 566 clear_list(); 567 568 hr = psv->DestroyViewWindow(); 569 570 static message destroy_list[] = 571 { 572 message(SFVM_UNMERGEFROMMENU, 0, PTR_VALUE), 573 message(DUM_MSG_SetMenuSB, 0, 0), 574 message(DUM_MSG_RemoveMenusSB, 0, 0), 575 message(SFVM_WINDOWCLOSING, PTR_VALUE, 0), 576 577 message(0, 0, 0) 578 }; 579 580 compare_list(destroy_list); 581 clear_list(); 582 583 CComPtr<IShellFolderView> folderView; 584 hr = psv->QueryInterface(IID_PPV_ARG(IShellFolderView, &folderView)); 585 ok_hex(hr, S_OK); 586 if (SUCCEEDED(hr)) 587 { 588 IShellFolderViewCB* oldPtr; 589 590 hr = folderView->SetCallback(NULL, &oldPtr); 591 switch (GetNTVersion()) 592 { 593 case _WIN32_WINNT_WS03: 594 case _WIN32_WINNT_VISTA: 595 ok_int(g_AddRef, 1); 596 ok_int(g_Release, 0); 597 break; 598 case _WIN32_WINNT_WIN7: 599 case _WIN32_WINNT_WIN8: 600 case _WIN32_WINNT_WINBLUE: 601 ok_int(g_AddRef, 3); 602 ok_int(g_Release, 1); 603 break; 604 case _WIN32_WINNT_WIN10: 605 ok_int(g_AddRef, 6); 606 ok_int(g_Release, 4); 607 break; 608 default: 609 skip("Unknown NT Version (0x%lX)\n", GetNTVersion()); 610 break; 611 } 612 613 /* Last pointer is not optional! */ 614 IShellFolderViewCB* oldPtr2; 615 hr = folderView->SetCallback(oldPtr, &oldPtr2); 616 switch (GetNTVersion()) 617 { 618 case _WIN32_WINNT_WS03: 619 case _WIN32_WINNT_VISTA: 620 ok_int(g_AddRef, 2); 621 ok_int(g_Release, 0); 622 break; 623 case _WIN32_WINNT_WIN7: 624 case _WIN32_WINNT_WIN8: 625 case _WIN32_WINNT_WINBLUE: 626 ok_int(g_AddRef, 4); 627 ok_int(g_Release, 1); 628 break; 629 case _WIN32_WINNT_WIN10: 630 ok_int(g_AddRef, 7); 631 ok_int(g_Release, 4); 632 break; 633 default: 634 skip("Unknown NT Version (0x%lX)\n", GetNTVersion()); 635 break; 636 } 637 } 638 639 ULONG refCount = psv->Release(); 640 switch (GetNTVersion()) 641 { 642 case _WIN32_WINNT_WS03: 643 case _WIN32_WINNT_WIN10: 644 ok(refCount == 1, "refCount = %lu\n", refCount); 645 break; 646 case _WIN32_WINNT_VISTA: 647 ok(refCount == 4, "refCount = %lu\n", refCount); 648 break; 649 case _WIN32_WINNT_WIN7: 650 case _WIN32_WINNT_WIN8: 651 case _WIN32_WINNT_WINBLUE: 652 ok(refCount == 6, "refCount = %lu\n", refCount); 653 break; 654 default: 655 skip("Unknown NT Version (0x%lX)\n", GetNTVersion()); 656 break; 657 } 658 659 static message release_list[] = 660 { 661 message(SFVM_VIEWRELEASE, 0, 0), 662 663 message(0, 0, 0) 664 }; 665 666 /* Investigate why this fails */ 667 if (refCount == 0) 668 { 669 compare_list(release_list); 670 } 671}