Sync to trunk r65566.
[reactos.git] / base / shell / explorer-old / services / shellservices.cpp
1 /*
2 * Copyright 2005 Martin Fuchs
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19
20 //
21 // Explorer clone
22 //
23 // shellservices.cpp
24 //
25 // Martin Fuchs, 28.03.2005
26 //
27
28
29 #include <precomp.h>
30
31 #include "shellservices.h"
32
33
34 int SSOThread::Run()
35 {
36 ComInit usingCOM(COINIT_APARTMENTTHREADED|COINIT_DISABLE_OLE1DDE|COINIT_SPEED_OVER_MEMORY);
37
38 HKEY hkey;
39 CLSID clsid;
40 WCHAR name[MAX_PATH], value[MAX_PATH];
41
42 typedef vector<SIfacePtr<IOleCommandTarget>*> SSOVector;
43 SSOVector sso_ptrs;
44
45 if (!RegOpenKey(HKEY_LOCAL_MACHINE, TEXT("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\ShellServiceObjectDelayLoad"), &hkey)) {
46 for(int idx=0; ; ++idx) {
47 DWORD name_len = MAX_PATH;
48 DWORD value_len = sizeof(value);
49
50 if (RegEnumValueW(hkey, idx, name, &name_len, 0, NULL, (LPBYTE)&value, &value_len))
51 break;
52
53 if (!_alive)
54 break;
55
56 SIfacePtr<IOleCommandTarget>* sso_ptr = new SIfacePtr<IOleCommandTarget>;
57
58 if (CLSIDFromString(value, &clsid) == NOERROR) {
59 if (SUCCEEDED(sso_ptr->CreateInstance(clsid, IID_IOleCommandTarget))) {
60 if (SUCCEEDED((*sso_ptr)->Exec(&CGID_ShellServiceObject, OLECMDID_NEW, OLECMDEXECOPT_DODEFAULT, NULL, NULL)))
61 sso_ptrs.push_back(sso_ptr);
62 }
63 }
64 }
65
66 RegCloseKey(hkey);
67 }
68
69 if (!sso_ptrs.empty()) {
70 MSG msg;
71
72 while(_alive) {
73 if (MsgWaitForMultipleObjects(1, &_evtFinish, FALSE, INFINITE, QS_ALLINPUT) == WAIT_OBJECT_0+0)
74 break; // _evtFinish has been set.
75
76 while(_alive) {
77 if (!PeekMessage(&msg, 0, 0, 0, PM_REMOVE))
78 break;
79
80 if (msg.message == WM_QUIT)
81 break;
82
83 TranslateMessage(&msg);
84 DispatchMessage(&msg);
85 }
86 }
87
88 // shutdown all running Shell Service Objects
89 for(SSOVector::iterator it=sso_ptrs.begin(); it!=sso_ptrs.end(); ++it) {
90 SIfacePtr<IOleCommandTarget>* sso_ptr = *it;
91 (*sso_ptr)->Exec(&CGID_ShellServiceObject, OLECMDID_SAVE, OLECMDEXECOPT_DODEFAULT, NULL, NULL);
92 delete sso_ptr;
93 }
94 }
95
96 return 0;
97 }