[shell32.dll]

- Initialize uninitialized variables.
- Add code to guard against potential NULL pointer dereferencing.
Thanks to Amine Khaldi for pointing out all these.

svn path=/branches/shell32_new-bringup/; revision=53633
This commit is contained in:
Claudiu Mihail 2011-09-07 23:21:02 +00:00
parent ea0da4a0a3
commit 261ee4dd58
11 changed files with 1017 additions and 901 deletions

View file

@ -1,8 +1,8 @@
/* /*
* AutoComplete interfaces implementation. * AutoComplete interfaces implementation.
* *
* Copyright 2004 Maxime Bellengé <maxime.bellenge@laposte.net> * Copyright 2004 Maxime Bellengé <maxime.bellenge@laposte.net>
* Copyright 2009 Andrew Hill * Copyright 2009 Andrew Hill
* *
* This library is free software; you can redistribute it and/or * This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public * modify it under the terms of the GNU Lesser General Public
@ -44,12 +44,12 @@ WINE_DEFAULT_DEBUG_CHANNEL(shell);
*/ */
CAutoComplete::CAutoComplete() CAutoComplete::CAutoComplete()
{ {
enabled = TRUE; enabled = TRUE;
options = ACO_AUTOAPPEND; options = ACO_AUTOAPPEND;
wpOrigEditProc = NULL; wpOrigEditProc = NULL;
hwndListBox = NULL; hwndListBox = NULL;
txtbackup = NULL; txtbackup = NULL;
quickComplete = NULL; quickComplete = NULL;
hwndEdit = NULL; hwndEdit = NULL;
wpOrigLBoxProc = NULL; wpOrigLBoxProc = NULL;
} }
@ -59,11 +59,11 @@ CAutoComplete::CAutoComplete()
*/ */
CAutoComplete::~CAutoComplete() CAutoComplete::~CAutoComplete()
{ {
TRACE(" destroying IAutoComplete(%p)\n", this); TRACE(" destroying IAutoComplete(%p)\n", this);
HeapFree(GetProcessHeap(), 0, quickComplete); HeapFree(GetProcessHeap(), 0, quickComplete);
HeapFree(GetProcessHeap(), 0, txtbackup); HeapFree(GetProcessHeap(), 0, txtbackup);
if (hwndListBox) if (hwndListBox)
DestroyWindow(hwndListBox); DestroyWindow(hwndListBox);
} }
/****************************************************************************** /******************************************************************************
@ -88,7 +88,7 @@ HRESULT WINAPI CAutoComplete::Init(HWND hwndEdit, IUnknown *punkACL, LPCOLESTR p
static const WCHAR lbName[] = {'L','i','s','t','B','o','x',0}; static const WCHAR lbName[] = {'L','i','s','t','B','o','x',0};
TRACE("(%p)->(0x%08lx, %p, %s, %s)\n", TRACE("(%p)->(0x%08lx, %p, %s, %s)\n",
this, hwndEdit, punkACL, debugstr_w(pwzsRegKeyPath), debugstr_w(pwszQuickComplete)); this, hwndEdit, punkACL, debugstr_w(pwzsRegKeyPath), debugstr_w(pwszQuickComplete));
if (options & ACO_AUTOSUGGEST) if (options & ACO_AUTOSUGGEST)
TRACE(" ACO_AUTOSUGGEST\n"); TRACE(" ACO_AUTOSUGGEST\n");
@ -105,12 +105,12 @@ HRESULT WINAPI CAutoComplete::Init(HWND hwndEdit, IUnknown *punkACL, LPCOLESTR p
if (options & ACO_RTLREADING) if (options & ACO_RTLREADING)
FIXME(" ACO_RTLREADING not supported\n"); FIXME(" ACO_RTLREADING not supported\n");
hwndEdit = hwndEdit; hwndEdit = hwndEdit;
if (!SUCCEEDED (punkACL->QueryInterface(IID_IEnumString, (LPVOID *)&enumstr))) if (!SUCCEEDED (punkACL->QueryInterface(IID_IEnumString, (LPVOID *)&enumstr)))
{ {
TRACE("No IEnumString interface\n"); TRACE("No IEnumString interface\n");
return E_NOINTERFACE; return E_NOINTERFACE;
} }
wpOrigEditProc = (WNDPROC)SetWindowLongPtrW(hwndEdit, GWLP_WNDPROC, (LONG_PTR) ACEditSubclassProc); wpOrigEditProc = (WNDPROC)SetWindowLongPtrW(hwndEdit, GWLP_WNDPROC, (LONG_PTR) ACEditSubclassProc);
@ -118,65 +118,88 @@ HRESULT WINAPI CAutoComplete::Init(HWND hwndEdit, IUnknown *punkACL, LPCOLESTR p
if (options & ACO_AUTOSUGGEST) if (options & ACO_AUTOSUGGEST)
{ {
HWND hwndParent; HWND hwndParent;
hwndParent = GetParent(hwndEdit); hwndParent = GetParent(hwndEdit);
/* FIXME : The listbox should be resizable with the mouse. WS_THICKFRAME looks ugly */ /* FIXME : The listbox should be resizable with the mouse. WS_THICKFRAME looks ugly */
hwndListBox = CreateWindowExW(0, lbName, NULL, hwndListBox = CreateWindowExW(0, lbName, NULL,
WS_BORDER | WS_CHILD | WS_VSCROLL | LBS_HASSTRINGS | LBS_NOTIFY | LBS_NOINTEGRALHEIGHT, WS_BORDER | WS_CHILD | WS_VSCROLL | LBS_HASSTRINGS | LBS_NOTIFY | LBS_NOINTEGRALHEIGHT,
CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
hwndParent, NULL, hwndParent, NULL,
(HINSTANCE)GetWindowLongPtrW(hwndParent, GWLP_HINSTANCE), NULL); (HINSTANCE)GetWindowLongPtrW(hwndParent, GWLP_HINSTANCE), NULL);
if (hwndListBox) if (hwndListBox)
{ {
wpOrigLBoxProc = (WNDPROC)SetWindowLongPtrW(hwndListBox, GWLP_WNDPROC, (LONG_PTR)ACLBoxSubclassProc); wpOrigLBoxProc = (WNDPROC)SetWindowLongPtrW(hwndListBox, GWLP_WNDPROC, (LONG_PTR)ACLBoxSubclassProc);
SetWindowLongPtrW(hwndListBox, GWLP_USERDATA, (LONG_PTR)this); SetWindowLongPtrW(hwndListBox, GWLP_USERDATA, (LONG_PTR)this);
} }
} }
if (pwzsRegKeyPath) if (pwzsRegKeyPath)
{ {
WCHAR *key; WCHAR *key;
WCHAR result[MAX_PATH]; WCHAR result[MAX_PATH];
WCHAR *value; WCHAR *value;
HKEY hKey = 0; HKEY hKey = 0;
LONG res; LONG res;
LONG len; LONG len;
/* pwszRegKeyPath contains the key as well as the value, so we split */ /* pwszRegKeyPath contains the key as well as the value, so we split */
key = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (wcslen(pwzsRegKeyPath) + 1) * sizeof(WCHAR)); key = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (wcslen(pwzsRegKeyPath) + 1) * sizeof(WCHAR));
wcscpy(key, pwzsRegKeyPath);
value = const_cast<WCHAR *>(strrchrW(key, '\\')); if (key)
*value = 0;
value++;
/* Now value contains the value and buffer the key */
res = RegOpenKeyExW(HKEY_CURRENT_USER, key, 0, KEY_READ, &hKey);
if (res != ERROR_SUCCESS)
{ {
/* if the key is not found, MSDN states we must seek in HKEY_LOCAL_MACHINE */ wcscpy(key, pwzsRegKeyPath);
res = RegOpenKeyExW(HKEY_LOCAL_MACHINE, key, 0, KEY_READ, &hKey); value = const_cast<WCHAR *>(strrchrW(key, '\\'));
}
if (value)
if (res == ERROR_SUCCESS)
{
res = RegQueryValueW(hKey, value, result, &len);
if (res == ERROR_SUCCESS)
{ {
quickComplete = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len * sizeof(WCHAR)); *value = 0;
wcscpy(quickComplete, result); value++;
} /* Now value contains the value and buffer the key */
RegCloseKey(hKey); res = RegOpenKeyExW(HKEY_CURRENT_USER, key, 0, KEY_READ, &hKey);
}
HeapFree(GetProcessHeap(), 0, key); if (res != ERROR_SUCCESS)
{
/* if the key is not found, MSDN states we must seek in HKEY_LOCAL_MACHINE */
res = RegOpenKeyExW(HKEY_LOCAL_MACHINE, key, 0, KEY_READ, &hKey);
}
if (res == ERROR_SUCCESS)
{
res = RegQueryValueW(hKey, value, result, &len);
if (res == ERROR_SUCCESS)
{
quickComplete = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len * sizeof(WCHAR));
wcscpy(quickComplete, result);
}
RegCloseKey(hKey);
}
}
HeapFree(GetProcessHeap(), 0, key);
}
else
{
TRACE("HeapAlloc Failed when trying to alloca %d bytes\n", (wcslen(pwzsRegKeyPath) + 1) * sizeof(WCHAR));
return S_FALSE;
}
} }
if ((pwszQuickComplete) && (!quickComplete)) if ((pwszQuickComplete) && (!quickComplete))
{ {
quickComplete = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (wcslen(pwszQuickComplete) + 1) * sizeof(WCHAR)); quickComplete = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (wcslen(pwszQuickComplete) + 1) * sizeof(WCHAR));
wcscpy(quickComplete, pwszQuickComplete);
if (quickComplete)
{
wcscpy(quickComplete, pwszQuickComplete);
}
else
{
TRACE("HeapAlloc Failed when trying to alloca %d bytes\n", (wcslen(pwszQuickComplete) + 1) * sizeof(WCHAR));
return S_FALSE;
}
} }
return S_OK; return S_OK;
@ -215,7 +238,7 @@ HRESULT WINAPI CAutoComplete::SetOptions(DWORD dwFlag)
*/ */
LRESULT APIENTRY CAutoComplete::ACEditSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) LRESULT APIENTRY CAutoComplete::ACEditSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{ {
CAutoComplete *pThis = (CAutoComplete *)GetWindowLongPtrW(hwnd, GWLP_USERDATA); CAutoComplete *pThis = (CAutoComplete *)GetWindowLongPtrW(hwnd, GWLP_USERDATA);
LPOLESTR strs; LPOLESTR strs;
HRESULT hr; HRESULT hr;
WCHAR hwndText[255]; WCHAR hwndText[255];
@ -231,203 +254,218 @@ LRESULT APIENTRY CAutoComplete::ACEditSubclassProc(HWND hwnd, UINT uMsg, WPARAM
switch (uMsg) switch (uMsg)
{ {
case CB_SHOWDROPDOWN: case CB_SHOWDROPDOWN:
{ {
ShowWindow(pThis->hwndListBox, SW_HIDE); ShowWindow(pThis->hwndListBox, SW_HIDE);
}; break; }; break;
case WM_KILLFOCUS: case WM_KILLFOCUS:
{ {
if ((pThis->options & ACO_AUTOSUGGEST) && ((HWND)wParam != pThis->hwndListBox)) if ((pThis->options & ACO_AUTOSUGGEST) && ((HWND)wParam != pThis->hwndListBox))
{ {
ShowWindow(pThis->hwndListBox, SW_HIDE); ShowWindow(pThis->hwndListBox, SW_HIDE);
} }
return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam); return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam);
}; break; }; break;
case WM_KEYUP: case WM_KEYUP:
{ {
GetWindowTextW(hwnd, (LPWSTR)hwndText, 255); GetWindowTextW(hwnd, (LPWSTR)hwndText, 255);
switch(wParam) switch(wParam)
{ {
case VK_RETURN: case VK_RETURN:
{ {
/* If quickComplete is set and control is pressed, replace the string */ /* If quickComplete is set and control is pressed, replace the string */
control = GetKeyState(VK_CONTROL) & 0x8000; control = GetKeyState(VK_CONTROL) & 0x8000;
if (control && pThis->quickComplete) if (control && pThis->quickComplete)
{ {
hwndQCText = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, hwndQCText = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
(wcslen(pThis->quickComplete)+wcslen(hwndText))*sizeof(WCHAR)); (wcslen(pThis->quickComplete)+wcslen(hwndText))*sizeof(WCHAR));
sel = swprintf(hwndQCText, pThis->quickComplete, hwndText); sel = swprintf(hwndQCText, pThis->quickComplete, hwndText);
SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)hwndQCText); SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)hwndQCText);
SendMessageW(hwnd, EM_SETSEL, 0, sel); SendMessageW(hwnd, EM_SETSEL, 0, sel);
HeapFree(GetProcessHeap(), 0, hwndQCText); HeapFree(GetProcessHeap(), 0, hwndQCText);
} }
ShowWindow(pThis->hwndListBox, SW_HIDE); ShowWindow(pThis->hwndListBox, SW_HIDE);
return 0; return 0;
}; break; }; break;
case VK_LEFT: case VK_LEFT:
case VK_RIGHT: case VK_RIGHT:
{ {
return 0; return 0;
}; break; }; break;
case VK_UP: case VK_UP:
case VK_DOWN: case VK_DOWN:
{ {
/* Two cases here : /* Two cases here :
- if the listbox is not visible, displays it - if the listbox is not visible, displays it
with all the entries if the style ACO_UPDOWNKEYDROPSLIST with all the entries if the style ACO_UPDOWNKEYDROPSLIST
is present but does not select anything. is present but does not select anything.
- if the listbox is visible, change the selection - if the listbox is visible, change the selection
*/ */
if ( (pThis->options & (ACO_AUTOSUGGEST | ACO_UPDOWNKEYDROPSLIST)) if ( (pThis->options & (ACO_AUTOSUGGEST | ACO_UPDOWNKEYDROPSLIST))
&& (!IsWindowVisible(pThis->hwndListBox) && (! *hwndText)) ) && (!IsWindowVisible(pThis->hwndListBox) && (! *hwndText)) )
{ {
/* We must display all the entries */ /* We must display all the entries */
displayall = TRUE; displayall = TRUE;
} }
else else
{ {
if (IsWindowVisible(pThis->hwndListBox)) if (IsWindowVisible(pThis->hwndListBox))
{ {
int count; int count;
count = SendMessageW(pThis->hwndListBox, LB_GETCOUNT, 0, 0); count = SendMessageW(pThis->hwndListBox, LB_GETCOUNT, 0, 0);
/* Change the selection */ /* Change the selection */
sel = SendMessageW(pThis->hwndListBox, LB_GETCURSEL, 0, 0); sel = SendMessageW(pThis->hwndListBox, LB_GETCURSEL, 0, 0);
if (wParam == VK_UP) if (wParam == VK_UP)
sel = ((sel-1)<0)?count-1:sel-1; sel = ((sel-1)<0)?count-1:sel-1;
else else
sel = ((sel+1)>= count)?-1:sel+1; sel = ((sel+1)>= count)?-1:sel+1;
SendMessageW(pThis->hwndListBox, LB_SETCURSEL, sel, 0); SendMessageW(pThis->hwndListBox, LB_SETCURSEL, sel, 0);
if (sel != -1) if (sel != -1)
{ {
WCHAR *msg; WCHAR *msg;
int len; int len;
len = SendMessageW(pThis->hwndListBox, LB_GETTEXTLEN, sel, (LPARAM)NULL); len = SendMessageW(pThis->hwndListBox, LB_GETTEXTLEN, sel, (LPARAM)NULL);
msg = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (len + 1) * sizeof(WCHAR)); msg = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (len + 1) * sizeof(WCHAR));
SendMessageW(pThis->hwndListBox, LB_GETTEXT, sel, (LPARAM)msg); if (msg)
SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)msg); {
SendMessageW(hwnd, EM_SETSEL, wcslen(msg), wcslen(msg)); SendMessageW(pThis->hwndListBox, LB_GETTEXT, sel, (LPARAM)msg);
SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)msg);
HeapFree(GetProcessHeap(), 0, msg); SendMessageW(hwnd, EM_SETSEL, wcslen(msg), wcslen(msg));
}
HeapFree(GetProcessHeap(), 0, msg);
}
else
{
TRACE("HeapAlloc failed to allocate %d bytes\n", (len + 1) * sizeof(WCHAR));
}
}
else else
{ {
SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)pThis->txtbackup); SendMessageW(hwnd, WM_SETTEXT, 0, (LPARAM)pThis->txtbackup);
SendMessageW(hwnd, EM_SETSEL, wcslen(pThis->txtbackup), wcslen(pThis->txtbackup)); SendMessageW(hwnd, EM_SETSEL, wcslen(pThis->txtbackup), wcslen(pThis->txtbackup));
} }
} }
return 0; return 0;
} }
}; break; }; break;
case VK_BACK: case VK_BACK:
case VK_DELETE: case VK_DELETE:
{ {
if ((! *hwndText) && (pThis->options & ACO_AUTOSUGGEST)) if ((! *hwndText) && (pThis->options & ACO_AUTOSUGGEST))
{ {
ShowWindow(pThis->hwndListBox, SW_HIDE); ShowWindow(pThis->hwndListBox, SW_HIDE);
return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam); return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam);
} }
if (pThis->options & ACO_AUTOAPPEND) if (pThis->options & ACO_AUTOAPPEND)
{ {
DWORD b; DWORD b;
SendMessageW(hwnd, EM_GETSEL, (WPARAM)&b, (LPARAM)NULL); SendMessageW(hwnd, EM_GETSEL, (WPARAM)&b, (LPARAM)NULL);
if (b>1) if (b>1)
{ {
hwndText[b-1] = '\0'; hwndText[b-1] = '\0';
} }
else else
{ {
hwndText[0] = '\0'; hwndText[0] = '\0';
SetWindowTextW(hwnd, hwndText); SetWindowTextW(hwnd, hwndText);
} }
} }
}; break; }; break;
default: default:
; ;
} }
SendMessageW(pThis->hwndListBox, LB_RESETCONTENT, 0, 0); SendMessageW(pThis->hwndListBox, LB_RESETCONTENT, 0, 0);
HeapFree(GetProcessHeap(), 0, pThis->txtbackup); HeapFree(GetProcessHeap(), 0, pThis->txtbackup);
pThis->txtbackup = (WCHAR *)HeapAlloc(GetProcessHeap(),
HEAP_ZERO_MEMORY, (wcslen(hwndText)+1)*sizeof(WCHAR));
wcscpy(pThis->txtbackup, hwndText);
/* Returns if there is no text to search and we doesn't want to display all the entries */ pThis->txtbackup = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (wcslen(hwndText)+1)*sizeof(WCHAR));
if ((!displayall) && (! *hwndText) )
break;
pThis->enumstr->Reset(); if (pThis->txtbackup)
filled = FALSE; {
wcscpy(pThis->txtbackup, hwndText);
}
else
{
TRACE("HeapAlloc failed to allocate %d bytes\n", (wcslen(hwndText)+1)*sizeof(WCHAR));
}
/* Returns if there is no text to search and we doesn't want to display all the entries */
if ((!displayall) && (! *hwndText) )
break;
pThis->enumstr->Reset();
filled = FALSE;
for(cpt = 0;;) for(cpt = 0;;)
{ {
hr = pThis->enumstr->Next(1, &strs, NULL); hr = pThis->enumstr->Next(1, &strs, NULL);
if (hr != S_OK) if (hr != S_OK)
break; break;
if ((LPWSTR)strstrW(strs, hwndText) == strs) if ((LPWSTR)strstrW(strs, hwndText) == strs)
{ {
if (pThis->options & ACO_AUTOAPPEND) if (pThis->options & ACO_AUTOAPPEND)
{ {
SetWindowTextW(hwnd, strs); SetWindowTextW(hwnd, strs);
SendMessageW(hwnd, EM_SETSEL, wcslen(hwndText), wcslen(strs)); SendMessageW(hwnd, EM_SETSEL, wcslen(hwndText), wcslen(strs));
break; break;
} }
if (pThis->options & ACO_AUTOSUGGEST) if (pThis->options & ACO_AUTOSUGGEST)
{ {
SendMessageW(pThis->hwndListBox, LB_ADDSTRING, 0, (LPARAM)strs); SendMessageW(pThis->hwndListBox, LB_ADDSTRING, 0, (LPARAM)strs);
filled = TRUE; filled = TRUE;
cpt++; cpt++;
} }
} }
} }
if (pThis->options & ACO_AUTOSUGGEST) if (pThis->options & ACO_AUTOSUGGEST)
{ {
if (filled) if (filled)
{ {
height = SendMessageW(pThis->hwndListBox, LB_GETITEMHEIGHT, 0, 0); height = SendMessageW(pThis->hwndListBox, LB_GETITEMHEIGHT, 0, 0);
SendMessageW(pThis->hwndListBox, LB_CARETOFF, 0, 0); SendMessageW(pThis->hwndListBox, LB_CARETOFF, 0, 0);
GetWindowRect(hwnd, &r); GetWindowRect(hwnd, &r);
SetParent(pThis->hwndListBox, HWND_DESKTOP); SetParent(pThis->hwndListBox, HWND_DESKTOP);
/* It seems that Windows XP displays 7 lines at most /* It seems that Windows XP displays 7 lines at most
and otherwise displays a vertical scroll bar */ and otherwise displays a vertical scroll bar */
SetWindowPos(pThis->hwndListBox, HWND_TOP, SetWindowPos(pThis->hwndListBox, HWND_TOP,
r.left, r.bottom + 1, r.right - r.left, min(height * 7, height * (cpt + 1)), r.left, r.bottom + 1, r.right - r.left, min(height * 7, height * (cpt + 1)),
SWP_SHOWWINDOW ); SWP_SHOWWINDOW );
} }
else else
{ {
ShowWindow(pThis->hwndListBox, SW_HIDE); ShowWindow(pThis->hwndListBox, SW_HIDE);
} }
} }
}; break; }; break;
default: default:
{ {
return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam); return CallWindowProcW(pThis->wpOrigEditProc, hwnd, uMsg, wParam, lParam);
} }
} }
return 0; return 0;
} }
LRESULT APIENTRY CAutoComplete::ACLBoxSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) LRESULT APIENTRY CAutoComplete::ACLBoxSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
@ -438,33 +476,40 @@ LRESULT APIENTRY CAutoComplete::ACLBoxSubclassProc(HWND hwnd, UINT uMsg, WPARAM
switch (uMsg) switch (uMsg)
{ {
case WM_MOUSEMOVE: case WM_MOUSEMOVE:
{ {
sel = SendMessageW(hwnd, LB_ITEMFROMPOINT, 0, lParam); sel = SendMessageW(hwnd, LB_ITEMFROMPOINT, 0, lParam);
SendMessageW(hwnd, LB_SETCURSEL, (WPARAM)sel, (LPARAM)0); SendMessageW(hwnd, LB_SETCURSEL, (WPARAM)sel, (LPARAM)0);
}; break; }; break;
case WM_LBUTTONDOWN: case WM_LBUTTONDOWN:
{ {
sel = SendMessageW(hwnd, LB_GETCURSEL, 0, 0); sel = SendMessageW(hwnd, LB_GETCURSEL, 0, 0);
if (sel < 0) if (sel < 0)
break; break;
len = SendMessageW(pThis->hwndListBox, LB_GETTEXTLEN, sel, 0); len = SendMessageW(pThis->hwndListBox, LB_GETTEXTLEN, sel, 0);
msg = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (len + 1) * sizeof(WCHAR)); msg = (WCHAR *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (len + 1) * sizeof(WCHAR));
SendMessageW(hwnd, LB_GETTEXT, sel, (LPARAM)msg); if (msg)
SendMessageW(pThis->hwndEdit, WM_SETTEXT, 0, (LPARAM)msg); {
SendMessageW(pThis->hwndEdit, EM_SETSEL, 0, wcslen(msg)); SendMessageW(hwnd, LB_GETTEXT, sel, (LPARAM)msg);
ShowWindow(hwnd, SW_HIDE); SendMessageW(pThis->hwndEdit, WM_SETTEXT, 0, (LPARAM)msg);
SendMessageW(pThis->hwndEdit, EM_SETSEL, 0, wcslen(msg));
HeapFree(GetProcessHeap(), 0, msg); ShowWindow(hwnd, SW_HIDE);
HeapFree(GetProcessHeap(), 0, msg);
}
else
{
TRACE("HeapAlloc failed to allocate %d bytes\n", (len + 1) * sizeof(WCHAR));
}
}; break; }; break;
default: default:
return CallWindowProcW(pThis->wpOrigLBoxProc, hwnd, uMsg, wParam, lParam); return CallWindowProcW(pThis->wpOrigLBoxProc, hwnd, uMsg, wParam, lParam);
} }
return 0; return 0;
} }

View file

@ -1,6 +1,6 @@
/* /*
* file type mapping * file type mapping
* (HKEY_CLASSES_ROOT - Stuff) * (HKEY_CLASSES_ROOT - Stuff)
* *
* Copyright 1998, 1999, 2000 Juergen Schmied * Copyright 1998, 1999, 2000 Juergen Schmied
* *
@ -27,76 +27,76 @@ WINE_DEFAULT_DEBUG_CHANNEL(shell);
BOOL HCR_MapTypeToValueW(LPCWSTR szExtension, LPWSTR szFileType, LONG len, BOOL bPrependDot) BOOL HCR_MapTypeToValueW(LPCWSTR szExtension, LPWSTR szFileType, LONG len, BOOL bPrependDot)
{ {
HKEY hkey; HKEY hkey;
WCHAR szTemp[MAX_EXTENSION_LENGTH + 2]; WCHAR szTemp[MAX_EXTENSION_LENGTH + 2];
TRACE("%s %p\n", debugstr_w(szExtension), debugstr_w(szFileType)); TRACE("%s %p\n", debugstr_w(szExtension), debugstr_w(szFileType));
/* added because we do not want to have double dots */ /* added because we do not want to have double dots */
if (szExtension[0] == '.') if (szExtension[0] == '.')
bPrependDot = 0; bPrependDot = 0;
if (bPrependDot) if (bPrependDot)
szTemp[0] = '.'; szTemp[0] = '.';
lstrcpynW(szTemp + (bPrependDot?1:0), szExtension, MAX_EXTENSION_LENGTH); lstrcpynW(szTemp + (bPrependDot?1:0), szExtension, MAX_EXTENSION_LENGTH);
if (RegOpenKeyExW(HKEY_CLASSES_ROOT, szTemp, 0, KEY_READ, &hkey)) if (RegOpenKeyExW(HKEY_CLASSES_ROOT, szTemp, 0, KEY_READ, &hkey))
{ {
return FALSE; return FALSE;
} }
if (RegQueryValueW(hkey, NULL, szFileType, &len)) if (RegQueryValueW(hkey, NULL, szFileType, &len))
{ {
RegCloseKey(hkey); RegCloseKey(hkey);
return FALSE; return FALSE;
} }
RegCloseKey(hkey); RegCloseKey(hkey);
TRACE("--UE;\n} %s\n", debugstr_w(szFileType)); TRACE("--UE;\n} %s\n", debugstr_w(szFileType));
return TRUE; return TRUE;
} }
BOOL HCR_MapTypeToValueA(LPCSTR szExtension, LPSTR szFileType, LONG len, BOOL bPrependDot) BOOL HCR_MapTypeToValueA(LPCSTR szExtension, LPSTR szFileType, LONG len, BOOL bPrependDot)
{ {
HKEY hkey; HKEY hkey;
char szTemp[MAX_EXTENSION_LENGTH + 2]; char szTemp[MAX_EXTENSION_LENGTH + 2];
TRACE("%s %p\n", szExtension, szFileType); TRACE("%s %p\n", szExtension, szFileType);
/* added because we do not want to have double dots */ /* added because we do not want to have double dots */
if (szExtension[0] == '.') if (szExtension[0] == '.')
bPrependDot = 0; bPrependDot = 0;
if (bPrependDot) if (bPrependDot)
szTemp[0] = '.'; szTemp[0] = '.';
lstrcpynA(szTemp + (bPrependDot?1:0), szExtension, MAX_EXTENSION_LENGTH); lstrcpynA(szTemp + (bPrependDot?1:0), szExtension, MAX_EXTENSION_LENGTH);
if (RegOpenKeyExA(HKEY_CLASSES_ROOT, szTemp, 0, KEY_READ, &hkey)) if (RegOpenKeyExA(HKEY_CLASSES_ROOT, szTemp, 0, KEY_READ, &hkey))
{ {
return FALSE; return FALSE;
} }
if (RegLoadMUIStringA(hkey, "FriendlyTypeName", szFileType, len, NULL, 0, NULL) == ERROR_SUCCESS) if (RegLoadMUIStringA(hkey, "FriendlyTypeName", szFileType, len, NULL, 0, NULL) == ERROR_SUCCESS)
{ {
RegCloseKey(hkey); RegCloseKey(hkey);
return TRUE; return TRUE;
} }
if (RegQueryValueA(hkey, NULL, szFileType, &len)) if (RegQueryValueA(hkey, NULL, szFileType, &len))
{ {
RegCloseKey(hkey); RegCloseKey(hkey);
return FALSE; return FALSE;
} }
RegCloseKey(hkey); RegCloseKey(hkey);
TRACE("--UE;\n} %s\n", szFileType); TRACE("--UE;\n} %s\n", szFileType);
return TRUE; return TRUE;
} }
static const WCHAR swShell[] = {'s','h','e','l','l','\\',0}; static const WCHAR swShell[] = {'s','h','e','l','l','\\',0};
@ -164,12 +164,12 @@ BOOL HCR_GetDefaultVerbW( HKEY hkeyClass, LPCWSTR szVerb, LPWSTR szDest, DWORD l
BOOL HCR_GetExecuteCommandW( HKEY hkeyClass, LPCWSTR szClass, LPCWSTR szVerb, LPWSTR szDest, DWORD len ) BOOL HCR_GetExecuteCommandW( HKEY hkeyClass, LPCWSTR szClass, LPCWSTR szVerb, LPWSTR szDest, DWORD len )
{ {
WCHAR sTempVerb[MAX_PATH]; WCHAR sTempVerb[MAX_PATH];
BOOL ret; BOOL ret;
TRACE("%p %s %s %p\n", hkeyClass, debugstr_w(szClass), debugstr_w(szVerb), szDest); TRACE("%p %s %s %p\n", hkeyClass, debugstr_w(szClass), debugstr_w(szVerb), szDest);
if (szClass) if (szClass)
RegOpenKeyExW(HKEY_CLASSES_ROOT, szClass, 0, KEY_READ, &hkeyClass); RegOpenKeyExW(HKEY_CLASSES_ROOT, szClass, 0, KEY_READ, &hkeyClass);
if (!hkeyClass) if (!hkeyClass)
return FALSE; return FALSE;
@ -186,26 +186,26 @@ BOOL HCR_GetExecuteCommandW( HKEY hkeyClass, LPCWSTR szClass, LPCWSTR szVerb, LP
if (szClass) if (szClass)
RegCloseKey(hkeyClass); RegCloseKey(hkeyClass);
TRACE("-- %s\n", debugstr_w(szDest) ); TRACE("-- %s\n", debugstr_w(szDest) );
return ret; return ret;
} }
/*************************************************************************************** /***************************************************************************************
* HCR_GetDefaultIcon [internal] * HCR_GetDefaultIcon [internal]
* *
* Gets the icon for a filetype * Gets the icon for a filetype
*/ */
static BOOL HCR_RegOpenClassIDKey(REFIID riid, HKEY *hkey) static BOOL HCR_RegOpenClassIDKey(REFIID riid, HKEY *hkey)
{ {
WCHAR xriid[50]; WCHAR xriid[50];
swprintf( xriid, L"CLSID\\{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}", swprintf( xriid, L"CLSID\\{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
riid.Data1, riid.Data2, riid.Data3, riid.Data1, riid.Data2, riid.Data3,
riid.Data4[0], riid.Data4[1], riid.Data4[2], riid.Data4[3], riid.Data4[0], riid.Data4[1], riid.Data4[2], riid.Data4[3],
riid.Data4[4], riid.Data4[5], riid.Data4[6], riid.Data4[7] ); riid.Data4[4], riid.Data4[5], riid.Data4[6], riid.Data4[7] );
TRACE("%S\n",xriid ); TRACE("%S\n",xriid );
return !RegOpenKeyExW(HKEY_CLASSES_ROOT, xriid, 0, KEY_READ, hkey); return !RegOpenKeyExW(HKEY_CLASSES_ROOT, xriid, 0, KEY_READ, hkey);
} }
static BOOL HCR_RegGetDefaultIconW(HKEY hkey, LPWSTR szDest, DWORD len, int* picon_idx) static BOOL HCR_RegGetDefaultIconW(HKEY hkey, LPWSTR szDest, DWORD len, int* picon_idx)
@ -234,89 +234,89 @@ static BOOL HCR_RegGetDefaultIconW(HKEY hkey, LPWSTR szDest, DWORD len, int* pic
static BOOL HCR_RegGetDefaultIconA(HKEY hkey, LPSTR szDest, DWORD len, int* picon_idx) static BOOL HCR_RegGetDefaultIconA(HKEY hkey, LPSTR szDest, DWORD len, int* picon_idx)
{ {
DWORD dwType; DWORD dwType;
char sTemp[MAX_PATH]; char sTemp[MAX_PATH];
char sNum[5]; char sNum[5];
if (!RegQueryValueExA(hkey, NULL, 0, &dwType, (LPBYTE)szDest, &len)) if (!RegQueryValueExA(hkey, NULL, 0, &dwType, (LPBYTE)szDest, &len))
{ {
if (dwType == REG_EXPAND_SZ) if (dwType == REG_EXPAND_SZ)
{ {
ExpandEnvironmentStringsA(szDest, sTemp, MAX_PATH); ExpandEnvironmentStringsA(szDest, sTemp, MAX_PATH);
lstrcpynA(szDest, sTemp, len); lstrcpynA(szDest, sTemp, len);
} }
if (ParseFieldA (szDest, 2, sNum, 5)) if (ParseFieldA (szDest, 2, sNum, 5))
*picon_idx=atoi(sNum); *picon_idx=atoi(sNum);
else else
*picon_idx=0; /* sometimes the icon number is missing */ *picon_idx=0; /* sometimes the icon number is missing */
ParseFieldA (szDest, 1, szDest, len); ParseFieldA (szDest, 1, szDest, len);
PathUnquoteSpacesA(szDest); PathUnquoteSpacesA(szDest);
return TRUE; return TRUE;
} }
return FALSE; return FALSE;
} }
BOOL HCR_GetDefaultIconW(LPCWSTR szClass, LPWSTR szDest, DWORD len, int* picon_idx) BOOL HCR_GetDefaultIconW(LPCWSTR szClass, LPWSTR szDest, DWORD len, int* picon_idx)
{ {
static const WCHAR swDefaultIcon[] = {'\\','D','e','f','a','u','l','t','I','c','o','n',0}; static const WCHAR swDefaultIcon[] = {'\\','D','e','f','a','u','l','t','I','c','o','n',0};
HKEY hkey; HKEY hkey;
WCHAR sTemp[MAX_PATH]; WCHAR sTemp[MAX_PATH];
BOOL ret = FALSE; BOOL ret = FALSE;
TRACE("%s\n",debugstr_w(szClass) ); TRACE("%s\n",debugstr_w(szClass) );
lstrcpynW(sTemp, szClass, MAX_PATH); lstrcpynW(sTemp, szClass, MAX_PATH);
wcscat(sTemp, swDefaultIcon); wcscat(sTemp, swDefaultIcon);
if (!RegOpenKeyExW(HKEY_CLASSES_ROOT, sTemp, 0, KEY_READ, &hkey)) if (!RegOpenKeyExW(HKEY_CLASSES_ROOT, sTemp, 0, KEY_READ, &hkey))
{ {
ret = HCR_RegGetDefaultIconW(hkey, szDest, len, picon_idx); ret = HCR_RegGetDefaultIconW(hkey, szDest, len, picon_idx);
RegCloseKey(hkey); RegCloseKey(hkey);
} }
if(ret) if(ret)
TRACE("-- %s %i\n", debugstr_w(szDest), *picon_idx); TRACE("-- %s %i\n", debugstr_w(szDest), *picon_idx);
else else
TRACE("-- not found\n"); TRACE("-- not found\n");
return ret; return ret;
} }
BOOL HCR_GetDefaultIconA(LPCSTR szClass, LPSTR szDest, DWORD len, int* picon_idx) BOOL HCR_GetDefaultIconA(LPCSTR szClass, LPSTR szDest, DWORD len, int* picon_idx)
{ {
HKEY hkey; HKEY hkey;
char sTemp[MAX_PATH]; char sTemp[MAX_PATH];
BOOL ret = FALSE; BOOL ret = FALSE;
TRACE("%s\n",szClass ); TRACE("%s\n",szClass );
sprintf(sTemp, "%s\\DefaultIcon",szClass); sprintf(sTemp, "%s\\DefaultIcon",szClass);
if (!RegOpenKeyExA(HKEY_CLASSES_ROOT, sTemp, 0, KEY_READ, &hkey)) if (!RegOpenKeyExA(HKEY_CLASSES_ROOT, sTemp, 0, KEY_READ, &hkey))
{ {
ret = HCR_RegGetDefaultIconA(hkey, szDest, len, picon_idx); ret = HCR_RegGetDefaultIconA(hkey, szDest, len, picon_idx);
RegCloseKey(hkey); RegCloseKey(hkey);
} }
TRACE("-- %s %i\n", szDest, *picon_idx); TRACE("-- %s %i\n", szDest, *picon_idx);
return ret; return ret;
} }
BOOL HCR_GetDefaultIconFromGUIDW(REFIID riid, LPWSTR szDest, DWORD len, int* picon_idx) BOOL HCR_GetDefaultIconFromGUIDW(REFIID riid, LPWSTR szDest, DWORD len, int* picon_idx)
{ {
HKEY hkey; HKEY hkey;
BOOL ret = FALSE; BOOL ret = FALSE;
if (HCR_RegOpenClassIDKey(riid, &hkey)) if (HCR_RegOpenClassIDKey(riid, &hkey))
{ {
ret = HCR_RegGetDefaultIconW(hkey, szDest, len, picon_idx); ret = HCR_RegGetDefaultIconW(hkey, szDest, len, picon_idx);
RegCloseKey(hkey); RegCloseKey(hkey);
} }
TRACE("-- %s %i\n", debugstr_w(szDest), *picon_idx); TRACE("-- %s %i\n", debugstr_w(szDest), *picon_idx);
return ret; return ret;
} }
/*************************************************************************************** /***************************************************************************************
* HCR_GetClassName [internal] * HCR_GetClassName [internal]
* *
* Gets the name of a registered class * Gets the name of a registered class
*/ */
@ -324,107 +324,107 @@ static const WCHAR swEmpty[] = {0};
BOOL HCR_GetClassNameW(REFIID riid, LPWSTR szDest, DWORD len) BOOL HCR_GetClassNameW(REFIID riid, LPWSTR szDest, DWORD len)
{ {
HKEY hkey; HKEY hkey;
BOOL ret = FALSE; BOOL ret = FALSE;
DWORD buflen = len; DWORD buflen = len;
WCHAR szName[100]; WCHAR szName[100];
LPOLESTR pStr; LPOLESTR pStr;
szDest[0] = 0; szDest[0] = 0;
if (StringFromCLSID(riid, &pStr) == S_OK) if (StringFromCLSID(riid, &pStr) == S_OK)
{ {
DWORD dwLen = buflen * sizeof(WCHAR); DWORD dwLen = buflen * sizeof(WCHAR);
swprintf(szName, L"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CLSID\\%s", pStr); swprintf(szName, L"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\CLSID\\%s", pStr);
if (RegGetValueW(HKEY_CURRENT_USER, szName, NULL, RRF_RT_REG_SZ, NULL, (PVOID)szDest, &dwLen) == ERROR_SUCCESS) if (RegGetValueW(HKEY_CURRENT_USER, szName, NULL, RRF_RT_REG_SZ, NULL, (PVOID)szDest, &dwLen) == ERROR_SUCCESS)
{ {
ret = TRUE; ret = TRUE;
} }
CoTaskMemFree(pStr); CoTaskMemFree(pStr);
} }
if (!ret && HCR_RegOpenClassIDKey(riid, &hkey)) if (!ret && HCR_RegOpenClassIDKey(riid, &hkey))
{ {
static const WCHAR wszLocalizedString[] = static const WCHAR wszLocalizedString[] =
{ 'L','o','c','a','l','i','z','e','d','S','t','r','i','n','g', 0 }; { 'L','o','c','a','l','i','z','e','d','S','t','r','i','n','g', 0 };
if (!RegLoadMUIStringW(hkey, wszLocalizedString, szDest, len, NULL, 0, NULL) || if (!RegLoadMUIStringW(hkey, wszLocalizedString, szDest, len, NULL, 0, NULL) ||
!RegQueryValueExW(hkey, swEmpty, 0, NULL, (LPBYTE)szDest, &len)) !RegQueryValueExW(hkey, swEmpty, 0, NULL, (LPBYTE)szDest, &len))
{ {
ret = TRUE; ret = TRUE;
} }
RegCloseKey(hkey); RegCloseKey(hkey);
} }
if (!ret || !szDest[0]) if (!ret || !szDest[0])
{ {
if(IsEqualIID(riid, CLSID_ShellDesktop)) if(IsEqualIID(riid, CLSID_ShellDesktop))
{ {
if (LoadStringW(shell32_hInstance, IDS_DESKTOP, szDest, buflen)) if (LoadStringW(shell32_hInstance, IDS_DESKTOP, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_MyComputer)) else if (IsEqualIID(riid, CLSID_MyComputer))
{ {
if(LoadStringW(shell32_hInstance, IDS_MYCOMPUTER, szDest, buflen)) if(LoadStringW(shell32_hInstance, IDS_MYCOMPUTER, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_MyDocuments)) else if (IsEqualIID(riid, CLSID_MyDocuments))
{ {
if(LoadStringW(shell32_hInstance, IDS_PERSONAL, szDest, buflen)) if(LoadStringW(shell32_hInstance, IDS_PERSONAL, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_RecycleBin)) else if (IsEqualIID(riid, CLSID_RecycleBin))
{ {
if(LoadStringW(shell32_hInstance, IDS_RECYCLEBIN_FOLDER_NAME, szDest, buflen)) if(LoadStringW(shell32_hInstance, IDS_RECYCLEBIN_FOLDER_NAME, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_ControlPanel)) else if (IsEqualIID(riid, CLSID_ControlPanel))
{ {
if(LoadStringW(shell32_hInstance, IDS_CONTROLPANEL, szDest, buflen)) if(LoadStringW(shell32_hInstance, IDS_CONTROLPANEL, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_AdminFolderShortcut)) else if (IsEqualIID(riid, CLSID_AdminFolderShortcut))
{ {
if(LoadStringW(shell32_hInstance, IDS_ADMINISTRATIVETOOLS, szDest, buflen)) if(LoadStringW(shell32_hInstance, IDS_ADMINISTRATIVETOOLS, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
} }
TRACE("-- %s\n", debugstr_w(szDest)); TRACE("-- %s\n", debugstr_w(szDest));
return ret; return ret;
} }
BOOL HCR_GetClassNameA(REFIID riid, LPSTR szDest, DWORD len) BOOL HCR_GetClassNameA(REFIID riid, LPSTR szDest, DWORD len)
{ HKEY hkey; { HKEY hkey;
BOOL ret = FALSE; BOOL ret = FALSE;
DWORD buflen = len; DWORD buflen = len;
szDest[0] = 0; szDest[0] = 0;
if (HCR_RegOpenClassIDKey(riid, &hkey)) if (HCR_RegOpenClassIDKey(riid, &hkey))
{ {
if (!RegLoadMUIStringA(hkey,"LocalizedString",szDest,len,NULL,0,NULL) || if (!RegLoadMUIStringA(hkey,"LocalizedString",szDest,len,NULL,0,NULL) ||
!RegQueryValueExA(hkey,"",0,NULL,(LPBYTE)szDest,&len)) !RegQueryValueExA(hkey,"",0,NULL,(LPBYTE)szDest,&len))
{ {
ret = TRUE; ret = TRUE;
} }
RegCloseKey(hkey); RegCloseKey(hkey);
} }
if (!ret || !szDest[0]) if (!ret || !szDest[0])
{ {
if(IsEqualIID(riid, CLSID_ShellDesktop)) if(IsEqualIID(riid, CLSID_ShellDesktop))
{ {
if (LoadStringA(shell32_hInstance, IDS_DESKTOP, szDest, buflen)) if (LoadStringA(shell32_hInstance, IDS_DESKTOP, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
else if (IsEqualIID(riid, CLSID_MyComputer)) else if (IsEqualIID(riid, CLSID_MyComputer))
{ {
if(LoadStringA(shell32_hInstance, IDS_MYCOMPUTER, szDest, buflen)) if(LoadStringA(shell32_hInstance, IDS_MYCOMPUTER, szDest, buflen))
ret = TRUE; ret = TRUE;
} }
} }
TRACE("-- %s\n", szDest); TRACE("-- %s\n", szDest);
return ret; return ret;
} }
/****************************************************************************** /******************************************************************************
@ -476,8 +476,8 @@ BOOL HCR_GetFolderAttributes(LPCITEMIDLIST pidlFolder, LPDWORD pdwAttributes)
dwLen = sizeof(DWORD); dwLen = sizeof(DWORD);
lResult = RegQueryValueExW(hSFKey, wszCallForAttributes, 0, NULL, (LPBYTE)&dwTemp, &dwLen); lResult = RegQueryValueExW(hSFKey, wszCallForAttributes, 0, NULL, (LPBYTE)&dwTemp, &dwLen);
if ((lResult == ERROR_SUCCESS) && (dwTemp & *pdwAttributes)) { if ((lResult == ERROR_SUCCESS) && (dwTemp & *pdwAttributes)) {
CComPtr<IShellFolder> psfDesktop; CComPtr<IShellFolder> psfDesktop;
CComPtr<IShellFolder> psfFolder; CComPtr<IShellFolder> psfFolder;
HRESULT hr; HRESULT hr;
RegCloseKey(hSFKey); RegCloseKey(hSFKey);

View file

@ -25,221 +25,221 @@ WINE_DEFAULT_DEBUG_CHANNEL(pidl);
static static
LPITEMIDLIST _dbg_ILGetNext(LPCITEMIDLIST pidl) LPITEMIDLIST _dbg_ILGetNext(LPCITEMIDLIST pidl)
{ {
WORD len; WORD len;
if(pidl) if(pidl)
{ {
len = pidl->mkid.cb; len = pidl->mkid.cb;
if (len) if (len)
{ {
return (LPITEMIDLIST) (((LPBYTE)pidl)+len); return (LPITEMIDLIST) (((LPBYTE)pidl)+len);
} }
} }
return NULL; return NULL;
} }
static static
BOOL _dbg_ILIsDesktop(LPCITEMIDLIST pidl) BOOL _dbg_ILIsDesktop(LPCITEMIDLIST pidl)
{ {
return ( !pidl || (pidl && pidl->mkid.cb == 0x00) ); return ( !pidl || (pidl && pidl->mkid.cb == 0x00) );
} }
static static
LPPIDLDATA _dbg_ILGetDataPointer(LPCITEMIDLIST pidl) LPPIDLDATA _dbg_ILGetDataPointer(LPCITEMIDLIST pidl)
{ {
if(pidl && pidl->mkid.cb != 0x00) if(pidl && pidl->mkid.cb != 0x00)
return (LPPIDLDATA) &(pidl->mkid.abID); return (LPPIDLDATA) &(pidl->mkid.abID);
return NULL; return NULL;
} }
static static
LPSTR _dbg_ILGetTextPointer(LPCITEMIDLIST pidl) LPSTR _dbg_ILGetTextPointer(LPCITEMIDLIST pidl)
{ {
LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl); LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl);
if (pdata) if (pdata)
{ {
switch (pdata->type) switch (pdata->type)
{ {
case PT_GUID: case PT_GUID:
case PT_SHELLEXT: case PT_SHELLEXT:
case PT_YAGUID: case PT_YAGUID:
return NULL; return NULL;
case PT_DRIVE: case PT_DRIVE:
case PT_DRIVE1: case PT_DRIVE1:
case PT_DRIVE2: case PT_DRIVE2:
case PT_DRIVE3: case PT_DRIVE3:
return (LPSTR)&(pdata->u.drive.szDriveName); return (LPSTR)&(pdata->u.drive.szDriveName);
case PT_FOLDER: case PT_FOLDER:
case PT_FOLDER1: case PT_FOLDER1:
case PT_VALUE: case PT_VALUE:
case PT_IESPECIAL1: case PT_IESPECIAL1:
case PT_IESPECIAL2: case PT_IESPECIAL2:
return (LPSTR)&(pdata->u.file.szNames); return (LPSTR)&(pdata->u.file.szNames);
case PT_WORKGRP: case PT_WORKGRP:
case PT_COMP: case PT_COMP:
case PT_NETWORK: case PT_NETWORK:
case PT_NETPROVIDER: case PT_NETPROVIDER:
case PT_SHARE: case PT_SHARE:
return (LPSTR)&(pdata->u.network.szNames); return (LPSTR)&(pdata->u.network.szNames);
} }
} }
return NULL; return NULL;
} }
static static
LPWSTR _dbg_ILGetTextPointerW(LPCITEMIDLIST pidl) LPWSTR _dbg_ILGetTextPointerW(LPCITEMIDLIST pidl)
{ {
LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl); LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl);
if (pdata) if (pdata)
{ {
switch (pdata->type) switch (pdata->type)
{ {
case PT_GUID: case PT_GUID:
case PT_SHELLEXT: case PT_SHELLEXT:
case PT_YAGUID: case PT_YAGUID:
return NULL; return NULL;
case PT_DRIVE: case PT_DRIVE:
case PT_DRIVE1: case PT_DRIVE1:
case PT_DRIVE2: case PT_DRIVE2:
case PT_DRIVE3: case PT_DRIVE3:
/* return (LPSTR)&(pdata->u.drive.szDriveName);*/ /* return (LPSTR)&(pdata->u.drive.szDriveName);*/
return NULL; return NULL;
case PT_FOLDER: case PT_FOLDER:
case PT_FOLDER1: case PT_FOLDER1:
case PT_VALUE: case PT_VALUE:
case PT_IESPECIAL1: case PT_IESPECIAL1:
case PT_IESPECIAL2: case PT_IESPECIAL2:
/* return (LPSTR)&(pdata->u.file.szNames); */ /* return (LPSTR)&(pdata->u.file.szNames); */
return NULL; return NULL;
case PT_WORKGRP: case PT_WORKGRP:
case PT_COMP: case PT_COMP:
case PT_NETWORK: case PT_NETWORK:
case PT_NETPROVIDER: case PT_NETPROVIDER:
case PT_SHARE: case PT_SHARE:
/* return (LPSTR)&(pdata->u.network.szNames); */ /* return (LPSTR)&(pdata->u.network.szNames); */
return NULL; return NULL;
case PT_VALUEW: case PT_VALUEW:
return (LPWSTR)&(pdata->u.file.szNames); return (LPWSTR)&(pdata->u.file.szNames);
} }
} }
return NULL; return NULL;
} }
static static
LPSTR _dbg_ILGetSTextPointer(LPCITEMIDLIST pidl) LPSTR _dbg_ILGetSTextPointer(LPCITEMIDLIST pidl)
{ {
LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl); LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl);
if (pdata) if (pdata)
{ {
switch (pdata->type) switch (pdata->type)
{ {
case PT_FOLDER: case PT_FOLDER:
case PT_VALUE: case PT_VALUE:
case PT_IESPECIAL1: case PT_IESPECIAL1:
case PT_IESPECIAL2: case PT_IESPECIAL2:
return (LPSTR)(pdata->u.file.szNames + strlen (pdata->u.file.szNames) + 1); return (LPSTR)(pdata->u.file.szNames + strlen (pdata->u.file.szNames) + 1);
case PT_WORKGRP: case PT_WORKGRP:
return (LPSTR)(pdata->u.network.szNames + strlen (pdata->u.network.szNames) + 1); return (LPSTR)(pdata->u.network.szNames + strlen (pdata->u.network.szNames) + 1);
} }
} }
return NULL; return NULL;
} }
static static
LPWSTR _dbg_ILGetSTextPointerW(LPCITEMIDLIST pidl) LPWSTR _dbg_ILGetSTextPointerW(LPCITEMIDLIST pidl)
{ {
LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl); LPPIDLDATA pdata =_dbg_ILGetDataPointer(pidl);
if (pdata) if (pdata)
{ {
switch (pdata->type) switch (pdata->type)
{ {
case PT_FOLDER: case PT_FOLDER:
case PT_VALUE: case PT_VALUE:
case PT_IESPECIAL1: case PT_IESPECIAL1:
case PT_IESPECIAL2: case PT_IESPECIAL2:
/*return (LPSTR)(pdata->u.file.szNames + strlen (pdata->u.file.szNames) + 1); */ /*return (LPSTR)(pdata->u.file.szNames + strlen (pdata->u.file.szNames) + 1); */
return NULL; return NULL;
case PT_WORKGRP: case PT_WORKGRP:
/* return (LPSTR)(pdata->u.network.szNames + strlen (pdata->u.network.szNames) + 1); */ /* return (LPSTR)(pdata->u.network.szNames + strlen (pdata->u.network.szNames) + 1); */
return NULL; return NULL;
case PT_VALUEW: case PT_VALUEW:
return (LPWSTR)(pdata->u.file.szNames + wcslen ((LPWSTR)pdata->u.file.szNames) + 1); return (LPWSTR)(pdata->u.file.szNames + wcslen ((LPWSTR)pdata->u.file.szNames) + 1);
} }
} }
return NULL; return NULL;
} }
static static
IID* _dbg_ILGetGUIDPointer(LPCITEMIDLIST pidl) IID* _dbg_ILGetGUIDPointer(LPCITEMIDLIST pidl)
{ {
LPPIDLDATA pdata =_ILGetDataPointer(pidl); LPPIDLDATA pdata =_ILGetDataPointer(pidl);
if (pdata) if (pdata)
{ {
switch (pdata->type) switch (pdata->type)
{ {
case PT_SHELLEXT: case PT_SHELLEXT:
case PT_GUID: case PT_GUID:
case PT_YAGUID: case PT_YAGUID:
return &(pdata->u.guid.guid); return &(pdata->u.guid.guid);
} }
} }
return NULL; return NULL;
} }
static static
void _dbg_ILSimpleGetText (LPCITEMIDLIST pidl, LPSTR szOut, UINT uOutSize) void _dbg_ILSimpleGetText (LPCITEMIDLIST pidl, LPSTR szOut, UINT uOutSize)
{ {
LPSTR szSrc; LPSTR szSrc;
LPWSTR szSrcW; LPWSTR szSrcW;
GUID const * riid; GUID const * riid;
if (!pidl) return; if (!pidl) return;
if (szOut) if (szOut)
*szOut = 0; *szOut = 0;
if (_dbg_ILIsDesktop(pidl)) if (_dbg_ILIsDesktop(pidl))
{ {
/* desktop */ /* desktop */
if (szOut) lstrcpynA(szOut, "Desktop", uOutSize); if (szOut) lstrcpynA(szOut, "Desktop", uOutSize);
} }
else if (( szSrc = _dbg_ILGetTextPointer(pidl) )) else if (( szSrc = _dbg_ILGetTextPointer(pidl) ))
{ {
/* filesystem */ /* filesystem */
if (szOut) lstrcpynA(szOut, szSrc, uOutSize); if (szOut) lstrcpynA(szOut, szSrc, uOutSize);
} }
else if (( szSrcW = _dbg_ILGetTextPointerW(pidl) )) else if (( szSrcW = _dbg_ILGetTextPointerW(pidl) ))
{ {
CHAR tmp[MAX_PATH]; CHAR tmp[MAX_PATH];
/* unicode filesystem */ /* unicode filesystem */
WideCharToMultiByte(CP_ACP,0,szSrcW, -1, tmp, MAX_PATH, NULL, NULL); WideCharToMultiByte(CP_ACP,0,szSrcW, -1, tmp, MAX_PATH, NULL, NULL);
if (szOut) lstrcpynA(szOut, tmp, uOutSize); if (szOut) lstrcpynA(szOut, tmp, uOutSize);
} }
else if (( riid = _dbg_ILGetGUIDPointer(pidl) )) else if (( riid = _dbg_ILGetGUIDPointer(pidl) ))
{ {
if (szOut) if (szOut)
sprintf( szOut, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}", sprintf( szOut, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
riid->Data1, riid->Data2, riid->Data3, riid->Data1, riid->Data2, riid->Data3,
riid->Data4[0], riid->Data4[1], riid->Data4[2], riid->Data4[3], riid->Data4[0], riid->Data4[1], riid->Data4[2], riid->Data4[3],
riid->Data4[4], riid->Data4[5], riid->Data4[6], riid->Data4[7] ); riid->Data4[4], riid->Data4[5], riid->Data4[6], riid->Data4[7] );
} }
} }
@ -247,21 +247,21 @@ void _dbg_ILSimpleGetText (LPCITEMIDLIST pidl, LPSTR szOut, UINT uOutSize)
void pdump (LPCITEMIDLIST pidl) void pdump (LPCITEMIDLIST pidl)
{ {
LPCITEMIDLIST pidltemp = pidl; LPCITEMIDLIST pidltemp = pidl;
if (!TRACE_ON(pidl)) return; if (!TRACE_ON(pidl)) return;
if (! pidltemp) if (! pidltemp)
{ {
MESSAGE ("-------- pidl=NULL (Desktop)\n"); MESSAGE ("-------- pidl=NULL (Desktop)\n");
} }
else else
{ {
MESSAGE ("-------- pidl=%p\n", pidl); MESSAGE ("-------- pidl=%p\n", pidl);
if (pidltemp->mkid.cb) if (pidltemp->mkid.cb)
{ {
do do
{ {
if (_ILIsUnicode(pidltemp)) if (_ILIsUnicode(pidltemp))
{ {
DWORD dwAttrib = 0; DWORD dwAttrib = 0;
@ -297,16 +297,16 @@ void pdump (LPCITEMIDLIST pidl)
debugstr_a(szName), debugstr_a(szLongName), debugstr_a(szShortName)); debugstr_a(szName), debugstr_a(szLongName), debugstr_a(szShortName));
} }
pidltemp = _dbg_ILGetNext(pidltemp); pidltemp = _dbg_ILGetNext(pidltemp);
} while (pidltemp && pidltemp->mkid.cb); } while (pidltemp && pidltemp->mkid.cb);
} }
else else
{ {
MESSAGE ("empty pidl (Desktop)\n"); MESSAGE ("empty pidl (Desktop)\n");
} }
pcheck(pidl); pcheck(pidl);
} }
} }
static void dump_pidl_hex( LPCITEMIDLIST pidl ) static void dump_pidl_hex( LPCITEMIDLIST pidl )
@ -340,83 +340,92 @@ BOOL pcheck( LPCITEMIDLIST pidl )
while( pidltemp && pidltemp->mkid.cb ) while( pidltemp && pidltemp->mkid.cb )
{ {
type = _dbg_ILGetDataPointer(pidltemp)->type; LPPIDLDATA pidlData = _dbg_ILGetDataPointer(pidltemp);
switch( type )
if (pidlData)
{
type = pidlData->type;
switch( type )
{
case PT_CPLAPPLET:
case PT_GUID:
case PT_SHELLEXT:
case PT_DRIVE:
case PT_DRIVE1:
case PT_DRIVE2:
case PT_DRIVE3:
case PT_FOLDER:
case PT_VALUE:
case PT_VALUEW:
case PT_FOLDER1:
case PT_WORKGRP:
case PT_COMP:
case PT_NETPROVIDER:
case PT_NETWORK:
case PT_IESPECIAL1:
case PT_YAGUID:
case PT_IESPECIAL2:
case PT_SHARE:
break;
default:
ERR("unknown IDLIST %p [%p] size=%u type=%x\n",
pidl, pidltemp, pidltemp->mkid.cb,type );
dump_pidl_hex( pidltemp );
return FALSE;
}
pidltemp = _dbg_ILGetNext(pidltemp);
}
else
{ {
case PT_CPLAPPLET:
case PT_GUID:
case PT_SHELLEXT:
case PT_DRIVE:
case PT_DRIVE1:
case PT_DRIVE2:
case PT_DRIVE3:
case PT_FOLDER:
case PT_VALUE:
case PT_VALUEW:
case PT_FOLDER1:
case PT_WORKGRP:
case PT_COMP:
case PT_NETPROVIDER:
case PT_NETWORK:
case PT_IESPECIAL1:
case PT_YAGUID:
case PT_IESPECIAL2:
case PT_SHARE:
break;
default:
ERR("unknown IDLIST %p [%p] size=%u type=%x\n",
pidl, pidltemp, pidltemp->mkid.cb,type );
dump_pidl_hex( pidltemp );
return FALSE; return FALSE;
} }
pidltemp = _dbg_ILGetNext(pidltemp);
} }
return TRUE; return TRUE;
} }
static const struct { static const struct {
REFIID riid; REFIID riid;
const char *name; const char *name;
} InterfaceDesc[] = { } InterfaceDesc[] = {
{IID_IUnknown, "IID_IUnknown"}, {IID_IUnknown, "IID_IUnknown"},
{IID_IClassFactory, "IID_IClassFactory"}, {IID_IClassFactory, "IID_IClassFactory"},
{IID_IShellView, "IID_IShellView"}, {IID_IShellView, "IID_IShellView"},
{IID_IOleCommandTarget, "IID_IOleCommandTarget"}, {IID_IOleCommandTarget, "IID_IOleCommandTarget"},
{IID_IDropTarget, "IID_IDropTarget"}, {IID_IDropTarget, "IID_IDropTarget"},
{IID_IDropSource, "IID_IDropSource"}, {IID_IDropSource, "IID_IDropSource"},
{IID_IViewObject, "IID_IViewObject"}, {IID_IViewObject, "IID_IViewObject"},
{IID_IContextMenu, "IID_IContextMenu"}, {IID_IContextMenu, "IID_IContextMenu"},
{IID_IShellExtInit, "IID_IShellExtInit"}, {IID_IShellExtInit, "IID_IShellExtInit"},
{IID_IShellFolder, "IID_IShellFolder"}, {IID_IShellFolder, "IID_IShellFolder"},
{IID_IShellFolder2, "IID_IShellFolder2"}, {IID_IShellFolder2, "IID_IShellFolder2"},
{IID_IPersist, "IID_IPersist"}, {IID_IPersist, "IID_IPersist"},
{IID_IPersistFolder, "IID_IPersistFolder"}, {IID_IPersistFolder, "IID_IPersistFolder"},
{IID_IPersistFolder2, "IID_IPersistFolder2"}, {IID_IPersistFolder2, "IID_IPersistFolder2"},
{IID_IPersistFolder3, "IID_IPersistFolder3"}, {IID_IPersistFolder3, "IID_IPersistFolder3"},
{IID_IExtractIconA, "IID_IExtractIconA"}, {IID_IExtractIconA, "IID_IExtractIconA"},
{IID_IExtractIconW, "IID_IExtractIconW"}, {IID_IExtractIconW, "IID_IExtractIconW"},
{IID_IDataObject, "IID_IDataObject"}, {IID_IDataObject, "IID_IDataObject"},
{IID_IAutoComplete, "IID_IAutoComplete"}, {IID_IAutoComplete, "IID_IAutoComplete"},
{IID_IAutoComplete2, "IID_IAutoComplete2"}, {IID_IAutoComplete2, "IID_IAutoComplete2"},
{IID_IShellLinkA, "IID_IShellLinkA"}, {IID_IShellLinkA, "IID_IShellLinkA"},
{IID_IShellLinkW, "IID_IShellLinkW"}, {IID_IShellLinkW, "IID_IShellLinkW"},
}; };
const char * shdebugstr_guid( const struct _GUID *id ) const char * shdebugstr_guid( const struct _GUID *id )
{ {
unsigned int i; unsigned int i;
const char* name = NULL; const char* name = NULL;
char clsidbuf[100]; char clsidbuf[100];
if (!id) return "(null)"; if (!id) return "(null)";
for (i=0; i < sizeof(InterfaceDesc) / sizeof(InterfaceDesc[0]); i++) { for (i=0; i < sizeof(InterfaceDesc) / sizeof(InterfaceDesc[0]); i++) {
if (IsEqualIID(InterfaceDesc[i].riid, *id)) name = InterfaceDesc[i].name; if (IsEqualIID(InterfaceDesc[i].riid, *id)) name = InterfaceDesc[i].name;
} }
if (!name) { if (!name) {
if (HCR_GetClassNameA(*id, clsidbuf, 100)) if (HCR_GetClassNameA(*id, clsidbuf, 100))
name = clsidbuf; name = clsidbuf;
} }
return wine_dbg_sprintf( "\n\t{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x} (%s)", return wine_dbg_sprintf( "\n\t{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x} (%s)",
id->Data1, id->Data2, id->Data3, id->Data1, id->Data2, id->Data3,

View file

@ -1,5 +1,5 @@
/* /*
* common shell dialogs * common shell dialogs
* *
* Copyright 2000 Juergen Schmied * Copyright 2000 Juergen Schmied
* *
@ -22,14 +22,14 @@
typedef struct typedef struct
{ {
HWND hwndOwner ; HWND hwndOwner ;
HICON hIcon ; HICON hIcon ;
LPCWSTR lpstrDirectory ; LPCWSTR lpstrDirectory ;
LPCWSTR lpstrTitle ; LPCWSTR lpstrTitle ;
LPCWSTR lpstrDescription ; LPCWSTR lpstrDescription ;
UINT uFlags ; UINT uFlags ;
} RUNFILEDLGPARAMS ; } RUNFILEDLGPARAMS ;
typedef BOOL (WINAPI * LPFNOFN) (OPENFILENAMEW *) ; typedef BOOL (WINAPI * LPFNOFN) (OPENFILENAMEW *) ;
@ -39,7 +39,7 @@ static void FillList (HWND, char *, BOOL) ;
/************************************************************************* /*************************************************************************
* PickIconDlg [SHELL32.62] * PickIconDlg [SHELL32.62]
* *
*/ */
@ -261,17 +261,17 @@ BOOL WINAPI PickIconDlg(
} }
/************************************************************************* /*************************************************************************
* RunFileDlg [internal] * RunFileDlg [internal]
* *
* The Unicode function that is available as ordinal 61 on Windows NT/2000/XP/... * The Unicode function that is available as ordinal 61 on Windows NT/2000/XP/...
*/ */
void WINAPI RunFileDlg( void WINAPI RunFileDlg(
HWND hwndOwner, HWND hwndOwner,
HICON hIcon, HICON hIcon,
LPCWSTR lpstrDirectory, LPCWSTR lpstrDirectory,
LPCWSTR lpstrTitle, LPCWSTR lpstrTitle,
LPCWSTR lpstrDescription, LPCWSTR lpstrDescription,
UINT uFlags) UINT uFlags)
{ {
static const WCHAR resnameW[] = {'S','H','E','L','L','_','R','U','N','_','D','L','G',0}; static const WCHAR resnameW[] = {'S','H','E','L','L','_','R','U','N','_','D','L','G',0};
RUNFILEDLGPARAMS rfdp; RUNFILEDLGPARAMS rfdp;
@ -295,7 +295,7 @@ void WINAPI RunFileDlg(
} }
DialogBoxIndirectParamW(shell32_hInstance, DialogBoxIndirectParamW(shell32_hInstance,
(LPCDLGTEMPLATEW)tmplate, hwndOwner, RunDlgProc, (LPARAM)&rfdp); (LPCDLGTEMPLATEW)tmplate, hwndOwner, RunDlgProc, (LPARAM)&rfdp);
} }
@ -309,6 +309,12 @@ static LPWSTR RunDlg_GetParentDir(LPCWSTR cmdline)
result = (WCHAR *)HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR)*(strlenW(cmdline)+5)); result = (WCHAR *)HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR)*(strlenW(cmdline)+5));
if (NULL == result)
{
TRACE("HeapAlloc couldn't allocate %d bytes\n", sizeof(WCHAR)*(strlenW(cmdline)+5));
return NULL;
}
src = cmdline; src = cmdline;
dest = result; dest = result;
@ -391,50 +397,54 @@ static INT_PTR CALLBACK RunDlgProc (HWND hwnd, UINT message, WPARAM wParam, LPAR
case WM_COMMAND : case WM_COMMAND :
switch (LOWORD (wParam)) switch (LOWORD (wParam))
{ {
case IDOK : case IDOK :
{ {
int ic ; int ic ;
HWND htxt = GetDlgItem (hwnd, IDC_RUNDLG_EDITPATH); HWND htxt = GetDlgItem (hwnd, IDC_RUNDLG_EDITPATH);
if ((ic = GetWindowTextLengthW (htxt))) if ((ic = GetWindowTextLengthW (htxt)))
{ {
WCHAR *psz, *parent=NULL ; WCHAR *psz, *parent=NULL ;
SHELLEXECUTEINFOW sei ; SHELLEXECUTEINFOW sei ;
ZeroMemory (&sei, sizeof(sei)) ; ZeroMemory (&sei, sizeof(sei)) ;
sei.cbSize = sizeof(sei) ; sei.cbSize = sizeof(sei) ;
psz = (WCHAR *)HeapAlloc( GetProcessHeap(), 0, (ic + 1)*sizeof(WCHAR) ); psz = (WCHAR *)HeapAlloc( GetProcessHeap(), 0, (ic + 1)*sizeof(WCHAR) );
GetWindowTextW (htxt, psz, ic + 1) ;
/* according to http://www.codeproject.com/KB/shell/runfiledlg.aspx we should send a if (psz)
* WM_NOTIFY before execution */
sei.hwnd = hwnd;
sei.nShow = SW_SHOWNORMAL;
sei.lpFile = psz;
if (prfdp->lpstrDirectory)
sei.lpDirectory = prfdp->lpstrDirectory;
else
sei.lpDirectory = parent = RunDlg_GetParentDir(sei.lpFile);
if (!ShellExecuteExW( &sei ))
{ {
GetWindowTextW (htxt, psz, ic + 1) ;
/* according to http://www.codeproject.com/KB/shell/runfiledlg.aspx we should send a
* WM_NOTIFY before execution */
sei.hwnd = hwnd;
sei.nShow = SW_SHOWNORMAL;
sei.lpFile = psz;
if (prfdp->lpstrDirectory)
sei.lpDirectory = prfdp->lpstrDirectory;
else
sei.lpDirectory = parent = RunDlg_GetParentDir(sei.lpFile);
if (!ShellExecuteExW( &sei ))
{
HeapFree(GetProcessHeap(), 0, psz);
HeapFree(GetProcessHeap(), 0, parent);
SendMessageA (htxt, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ;
return TRUE ;
}
/* FillList is still ANSI */
GetWindowTextA (htxt, (LPSTR)psz, ic + 1) ;
FillList (htxt, (LPSTR)psz, FALSE) ;
HeapFree(GetProcessHeap(), 0, psz); HeapFree(GetProcessHeap(), 0, psz);
HeapFree(GetProcessHeap(), 0, parent); HeapFree(GetProcessHeap(), 0, parent);
SendMessageA (htxt, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ; EndDialog (hwnd, 0);
return TRUE ;
}
/* FillList is still ANSI */
GetWindowTextA (htxt, (LPSTR)psz, ic + 1) ;
FillList (htxt, (LPSTR)psz, FALSE) ;
HeapFree(GetProcessHeap(), 0, psz);
HeapFree(GetProcessHeap(), 0, parent);
EndDialog (hwnd, 0);
} }
} }
}
case IDCANCEL : case IDCANCEL :
EndDialog (hwnd, 0) ; EndDialog (hwnd, 0) ;
@ -491,7 +501,7 @@ static INT_PTR CALLBACK RunDlgProc (HWND hwnd, UINT message, WPARAM wParam, LPAR
/* This grabs the MRU list from the registry and fills the combo for the "Run" dialog above */ /* This grabs the MRU list from the registry and fills the combo for the "Run" dialog above */
/* fShowDefault ignored if pszLatest != NULL */ /* fShowDefault ignored if pszLatest != NULL */
static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault) static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
{ {
HKEY hkey ; HKEY hkey ;
/* char szDbgMsg[256] = "" ; */ /* char szDbgMsg[256] = "" ; */
char *pszList = NULL, *pszCmd = NULL, cMatch = 0, cMax = 0x60, szIndex[2] = "-" ; char *pszList = NULL, *pszCmd = NULL, cMatch = 0, cMax = 0x60, szIndex[2] = "-" ;
@ -508,20 +518,28 @@ static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
RegQueryValueExA (hkey, "MRUList", NULL, NULL, NULL, &icList) ; RegQueryValueExA (hkey, "MRUList", NULL, NULL, NULL, &icList) ;
if (icList > 0) if (icList > 0)
{ {
pszList = (char *)HeapAlloc( GetProcessHeap(), 0, icList) ; pszList = (char *)HeapAlloc( GetProcessHeap(), 0, icList) ;
if (ERROR_SUCCESS != RegQueryValueExA (hkey, "MRUList", NULL, NULL, (LPBYTE)pszList, &icList))
MessageBoxA (hCb, "Unable to grab MRUList !", "Nix", MB_OK) ; if (pszList)
}
else
{ {
if (ERROR_SUCCESS != RegQueryValueExA (hkey, "MRUList", NULL, NULL, (LPBYTE)pszList, &icList))
MessageBoxA (hCb, "Unable to grab MRUList !", "Nix", MB_OK);
}
else
{
TRACE("HeapAlloc failed to allocate %d bytes\n", icList);
}
}
else
{
icList = 1 ; icList = 1 ;
pszList = (char *)HeapAlloc( GetProcessHeap(), 0, icList) ; pszList = (char *)HeapAlloc( GetProcessHeap(), 0, icList) ;
pszList[0] = 0 ; pszList[0] = 0 ;
} }
for (Nix = 0 ; Nix < icList - 1 ; Nix++) for (Nix = 0 ; Nix < icList - 1 ; Nix++)
{ {
if (pszList[Nix] > cMax) if (pszList[Nix] > cMax)
cMax = pszList[Nix] ; cMax = pszList[Nix] ;
@ -537,9 +555,9 @@ static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
MessageBoxA (hCb, "Unable to grab index", "Nix", MB_OK) ; MessageBoxA (hCb, "Unable to grab index", "Nix", MB_OK) ;
if (NULL != pszLatest) if (NULL != pszLatest)
{ {
if (!lstrcmpiA(pszCmd, pszLatest)) if (!lstrcmpiA(pszCmd, pszLatest))
{ {
/* /*
sprintf (szDbgMsg, "Found existing (%d).\n", Nix) ; sprintf (szDbgMsg, "Found existing (%d).\n", Nix) ;
MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ; MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ;
@ -552,25 +570,24 @@ static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
memmove (&pszList[1], pszList, Nix) ; memmove (&pszList[1], pszList, Nix) ;
pszList[0] = cMatch ; pszList[0] = cMatch ;
continue ; continue ;
}
} }
}
if (26 != icList - 1 || icList - 2 != Nix || cMatch || NULL == pszLatest) if (26 != icList - 1 || icList - 2 != Nix || cMatch || NULL == pszLatest)
{ {
/* /*
sprintf (szDbgMsg, "Happily appending (%d).\n", Nix) ; sprintf (szDbgMsg, "Happily appending (%d).\n", Nix) ;
MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ; MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ;
*/ */
SendMessageA (hCb, CB_ADDSTRING, 0, (LPARAM)pszCmd) ; SendMessageA (hCb, CB_ADDSTRING, 0, (LPARAM)pszCmd) ;
if (!Nix && fShowDefault) if (!Nix && fShowDefault)
{ {
SetWindowTextA (hCb, pszCmd) ; SetWindowTextA (hCb, pszCmd) ;
SendMessageA (hCb, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ; SendMessageA (hCb, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ;
}
} }
}
else else
{ {
/* /*
sprintf (szDbgMsg, "Doing loop thing.\n") ; sprintf (szDbgMsg, "Doing loop thing.\n") ;
MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ; MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ;
@ -584,11 +601,11 @@ static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
pszList[0] = cMatch ; pszList[0] = cMatch ;
szIndex[0] = cMatch ; szIndex[0] = cMatch ;
RegSetValueExA (hkey, szIndex, 0, REG_SZ, (LPBYTE)pszLatest, strlen (pszLatest) + 1) ; RegSetValueExA (hkey, szIndex, 0, REG_SZ, (LPBYTE)pszLatest, strlen (pszLatest) + 1) ;
}
} }
}
if (!cMatch && NULL != pszLatest) if (!cMatch && NULL != pszLatest)
{ {
/* /*
sprintf (szDbgMsg, "Simply inserting (increasing list).\n") ; sprintf (szDbgMsg, "Simply inserting (increasing list).\n") ;
MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ; MessageBoxA (hCb, szDbgMsg, "Nix", MB_OK) ;
@ -598,25 +615,33 @@ static void FillList (HWND hCb, char *pszLatest, BOOL fShowDefault)
SendMessageA (hCb, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ; SendMessageA (hCb, CB_SETEDITSEL, 0, MAKELPARAM (0, -1)) ;
cMatch = ++cMax ; cMatch = ++cMax ;
if( pszList ) if (pszList)
pszList = (char *)HeapReAlloc(GetProcessHeap(), 0, pszList, ++icList) ; pszList = (char *)HeapReAlloc(GetProcessHeap(), 0, pszList, ++icList) ;
else else
pszList = (char *)HeapAlloc(GetProcessHeap(), 0, ++icList) ; pszList = (char *)HeapAlloc(GetProcessHeap(), 0, ++icList) ;
memmove (&pszList[1], pszList, icList - 1) ;
pszList[0] = cMatch ; if (pszList)
szIndex[0] = cMatch ; {
RegSetValueExA (hkey, szIndex, 0, REG_SZ, (LPBYTE)pszLatest, strlen (pszLatest) + 1) ; memmove (&pszList[1], pszList, icList - 1) ;
pszList[0] = cMatch ;
szIndex[0] = cMatch ;
RegSetValueExA (hkey, szIndex, 0, REG_SZ, (LPBYTE)pszLatest, strlen (pszLatest) + 1) ;
} }
else
{
TRACE("HeapAlloc or HeapReAlloc failed to allocate enough bytes\n");
}
}
RegSetValueExA (hkey, "MRUList", 0, REG_SZ, (LPBYTE)pszList, strlen (pszList) + 1) ; RegSetValueExA (hkey, "MRUList", 0, REG_SZ, (LPBYTE)pszList, strlen (pszList) + 1) ;
HeapFree( GetProcessHeap(), 0, pszCmd) ; HeapFree( GetProcessHeap(), 0, pszCmd) ;
HeapFree( GetProcessHeap(), 0, pszList) ; HeapFree( GetProcessHeap(), 0, pszList) ;
} }
/************************************************************************* /*************************************************************************
* ConfirmDialog [internal] * ConfirmDialog [internal]
* *
* Put up a confirm box, return TRUE if the user confirmed * Put up a confirm box, return TRUE if the user confirmed
*/ */
@ -632,7 +657,7 @@ static BOOL ConfirmDialog(HWND hWndOwner, UINT PromptId, UINT TitleId)
/************************************************************************* /*************************************************************************
* RestartDialogEx [SHELL32.730] * RestartDialogEx [SHELL32.730]
*/ */
int WINAPI RestartDialogEx(HWND hWndOwner, LPCWSTR lpwstrReason, DWORD uFlags, DWORD uReason) int WINAPI RestartDialogEx(HWND hWndOwner, LPCWSTR lpwstrReason, DWORD uFlags, DWORD uReason)
@ -675,7 +700,7 @@ EXTERN_C int WINAPI LogoffWindowsDialog(HWND hWndOwner)
/************************************************************************* /*************************************************************************
* RestartDialog [SHELL32.59] * RestartDialog [SHELL32.59]
*/ */
int WINAPI RestartDialog(HWND hWndOwner, LPCWSTR lpstrReason, DWORD uFlags) int WINAPI RestartDialog(HWND hWndOwner, LPCWSTR lpstrReason, DWORD uFlags)
@ -685,7 +710,7 @@ int WINAPI RestartDialog(HWND hWndOwner, LPCWSTR lpstrReason, DWORD uFlags)
/************************************************************************* /*************************************************************************
* ExitWindowsDialog [SHELL32.60] * ExitWindowsDialog [SHELL32.60]
* *
* NOTES * NOTES
* exported by ordinal * exported by ordinal

View file

@ -1,7 +1,7 @@
/* /*
* IEnumIDList * IEnumIDList
* *
* Copyright 1998 Juergen Schmied <juergen.schmied@metronet.de> * Copyright 1998 Juergen Schmied <juergen.schmied@metronet.de>
* *
* This library is free software; you can redistribute it and/or * This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public * modify it under the terms of the GNU Lesser General Public
@ -24,9 +24,9 @@ WINE_DEFAULT_DEBUG_CHANNEL(shell);
IEnumIDListImpl::IEnumIDListImpl() IEnumIDListImpl::IEnumIDListImpl()
{ {
mpFirst = NULL; mpFirst = NULL;
mpLast = NULL; mpLast = NULL;
mpCurrent = NULL; mpCurrent = NULL;
} }
IEnumIDListImpl::~IEnumIDListImpl() IEnumIDListImpl::~IEnumIDListImpl()
@ -38,39 +38,39 @@ IEnumIDListImpl::~IEnumIDListImpl()
*/ */
BOOL IEnumIDListImpl::AddToEnumList(LPITEMIDLIST pidl) BOOL IEnumIDListImpl::AddToEnumList(LPITEMIDLIST pidl)
{ {
ENUMLIST *pNew; ENUMLIST *pNew;
TRACE("(%p)->(pidl=%p)\n", this, pidl); TRACE("(%p)->(pidl=%p)\n", this, pidl);
if (!pidl) if (!pidl)
return FALSE; return FALSE;
pNew = (ENUMLIST *)SHAlloc(sizeof(ENUMLIST)); pNew = (ENUMLIST *)SHAlloc(sizeof(ENUMLIST));
if (pNew) if (pNew)
{ {
/*set the next pointer */ /*set the next pointer */
pNew->pNext = NULL; pNew->pNext = NULL;
pNew->pidl = pidl; pNew->pidl = pidl;
/*is This the first item in the list? */ /*is This the first item in the list? */
if (!mpFirst) if (!mpFirst)
{ {
mpFirst = pNew; mpFirst = pNew;
mpCurrent = pNew; mpCurrent = pNew;
} }
if (mpLast) if (mpLast)
{ {
/*add the new item to the end of the list */ /*add the new item to the end of the list */
mpLast->pNext = pNew; mpLast->pNext = pNew;
} }
/*update the last item pointer */ /*update the last item pointer */
mpLast = pNew; mpLast = pNew;
TRACE("-- (%p)->(first=%p, last=%p)\n", this, mpFirst, mpLast); TRACE("-- (%p)->(first=%p, last=%p)\n", this, mpFirst, mpLast);
return TRUE; return TRUE;
} }
return FALSE; return FALSE;
} }
/************************************************************************** /**************************************************************************
@ -78,21 +78,21 @@ BOOL IEnumIDListImpl::AddToEnumList(LPITEMIDLIST pidl)
*/ */
BOOL IEnumIDListImpl::DeleteList() BOOL IEnumIDListImpl::DeleteList()
{ {
ENUMLIST *pDelete; ENUMLIST *pDelete;
TRACE("(%p)->()\n", this); TRACE("(%p)->()\n", this);
while (mpFirst) while (mpFirst)
{ {
pDelete = mpFirst; pDelete = mpFirst;
mpFirst = pDelete->pNext; mpFirst = pDelete->pNext;
SHFree(pDelete->pidl); SHFree(pDelete->pidl);
SHFree(pDelete); SHFree(pDelete);
} }
mpFirst = NULL; mpFirst = NULL;
mpLast = NULL; mpLast = NULL;
mpCurrent = NULL; mpCurrent = NULL;
return TRUE; return TRUE;
} }
/************************************************************************** /**************************************************************************
@ -100,20 +100,25 @@ BOOL IEnumIDListImpl::DeleteList()
*/ */
BOOL IEnumIDListImpl::HasItemWithCLSID(LPITEMIDLIST pidl) BOOL IEnumIDListImpl::HasItemWithCLSID(LPITEMIDLIST pidl)
{ {
ENUMLIST *pCur; ENUMLIST *pCur;
REFIID refid = *_ILGetGUIDPointer(pidl); IID *ptr = _ILGetGUIDPointer(pidl);
pCur = mpFirst; if (ptr)
while(pCur)
{ {
LPGUID curid = _ILGetGUIDPointer(pCur->pidl); REFIID refid = *ptr;
if (curid && IsEqualGUID(*curid, refid)) pCur = mpFirst;
while(pCur)
{ {
return TRUE; LPGUID curid = _ILGetGUIDPointer(pCur->pidl);
if (curid && IsEqualGUID(*curid, refid))
{
return TRUE;
}
pCur = pCur->pNext;
} }
pCur = pCur->pNext;
} }
return FALSE; return FALSE;
} }
@ -122,8 +127,8 @@ BOOL IEnumIDListImpl::HasItemWithCLSID(LPITEMIDLIST pidl)
* CreateFolderEnumList() * CreateFolderEnumList()
*/ */
BOOL IEnumIDListImpl::CreateFolderEnumList( BOOL IEnumIDListImpl::CreateFolderEnumList(
LPCWSTR lpszPath, LPCWSTR lpszPath,
DWORD dwFlags) DWORD dwFlags)
{ {
LPITEMIDLIST pidl=NULL; LPITEMIDLIST pidl=NULL;
WIN32_FIND_DATAW stffile; WIN32_FIND_DATAW stffile;
@ -179,6 +184,7 @@ BOOL IEnumIDListImpl::CreateFolderEnumList(
} while (succeeded && !findFinished); } while (succeeded && !findFinished);
FindClose(hFile); FindClose(hFile);
} }
return succeeded; return succeeded;
} }
@ -187,66 +193,66 @@ BOOL IEnumIDListImpl::CreateFolderEnumList(
*/ */
HRESULT WINAPI IEnumIDListImpl::Next( HRESULT WINAPI IEnumIDListImpl::Next(
ULONG celt, ULONG celt,
LPITEMIDLIST * rgelt, LPITEMIDLIST * rgelt,
ULONG *pceltFetched) ULONG *pceltFetched)
{ {
ULONG i; ULONG i;
HRESULT hr = S_OK; HRESULT hr = S_OK;
LPITEMIDLIST temp; LPITEMIDLIST temp;
TRACE("(%p)->(%d,%p, %p)\n", this, celt, rgelt, pceltFetched); TRACE("(%p)->(%d,%p, %p)\n", this, celt, rgelt, pceltFetched);
/* It is valid to leave pceltFetched NULL when celt is 1. Some of explorer's /* It is valid to leave pceltFetched NULL when celt is 1. Some of explorer's
* subsystems actually use it (and so may a third party browser) * subsystems actually use it (and so may a third party browser)
*/ */
if(pceltFetched) if(pceltFetched)
*pceltFetched = 0; *pceltFetched = 0;
*rgelt=0; *rgelt=0;
if(celt > 1 && !pceltFetched) if(celt > 1 && !pceltFetched)
{ return E_INVALIDARG; { return E_INVALIDARG;
} }
if(celt > 0 && !mpCurrent) if(celt > 0 && !mpCurrent)
{ return S_FALSE; { return S_FALSE;
} }
for(i = 0; i < celt; i++) for(i = 0; i < celt; i++)
{ if(!mpCurrent) { if(!mpCurrent)
break; break;
temp = ILClone(mpCurrent->pidl); temp = ILClone(mpCurrent->pidl);
rgelt[i] = temp; rgelt[i] = temp;
mpCurrent = mpCurrent->pNext; mpCurrent = mpCurrent->pNext;
} }
if(pceltFetched) if(pceltFetched)
{ *pceltFetched = i; { *pceltFetched = i;
} }
return hr; return hr;
} }
/************************************************************************** /**************************************************************************
* IEnumIDList_fnSkip * IEnumIDList_fnSkip
*/ */
HRESULT WINAPI IEnumIDListImpl::Skip( HRESULT WINAPI IEnumIDListImpl::Skip(
ULONG celt) ULONG celt)
{ {
DWORD dwIndex; DWORD dwIndex;
HRESULT hr = S_OK; HRESULT hr = S_OK;
TRACE("(%p)->(%u)\n", this, celt); TRACE("(%p)->(%u)\n", this, celt);
for(dwIndex = 0; dwIndex < celt; dwIndex++) for(dwIndex = 0; dwIndex < celt; dwIndex++)
{ if(!mpCurrent) { if(!mpCurrent)
{ hr = S_FALSE; { hr = S_FALSE;
break; break;
} }
mpCurrent = mpCurrent->pNext; mpCurrent = mpCurrent->pNext;
} }
return hr; return hr;
} }
/************************************************************************** /**************************************************************************
@ -254,9 +260,9 @@ HRESULT WINAPI IEnumIDListImpl::Skip(
*/ */
HRESULT WINAPI IEnumIDListImpl::Reset() HRESULT WINAPI IEnumIDListImpl::Reset()
{ {
TRACE("(%p)\n", this); TRACE("(%p)\n", this);
mpCurrent = mpFirst; mpCurrent = mpFirst;
return S_OK; return S_OK;
} }
/************************************************************************** /**************************************************************************
@ -264,8 +270,8 @@ HRESULT WINAPI IEnumIDListImpl::Reset()
*/ */
HRESULT WINAPI IEnumIDListImpl::Clone(LPENUMIDLIST *ppenum) HRESULT WINAPI IEnumIDListImpl::Clone(LPENUMIDLIST *ppenum)
{ {
TRACE("(%p)->() to (%p)->() E_NOTIMPL\n", this, ppenum); TRACE("(%p)->() to (%p)->() E_NOTIMPL\n", this, ppenum);
return E_NOTIMPL; return E_NOTIMPL;
} }
/************************************************************************** /**************************************************************************
@ -274,22 +280,22 @@ HRESULT WINAPI IEnumIDListImpl::Clone(LPENUMIDLIST *ppenum)
*/ */
HRESULT IEnumIDList_Constructor(IEnumIDList **enumerator) HRESULT IEnumIDList_Constructor(IEnumIDList **enumerator)
{ {
CComObject<IEnumIDListImpl> *theEnumerator; CComObject<IEnumIDListImpl> *theEnumerator;
CComPtr<IEnumIDList> result; CComPtr<IEnumIDList> result;
HRESULT hResult; HRESULT hResult;
if (enumerator == NULL) if (enumerator == NULL)
return E_POINTER; return E_POINTER;
*enumerator = NULL; *enumerator = NULL;
ATLTRY (theEnumerator = new CComObject<IEnumIDListImpl>); ATLTRY (theEnumerator = new CComObject<IEnumIDListImpl>);
if (theEnumerator == NULL) if (theEnumerator == NULL)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result); hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result);
if (FAILED (hResult)) if (FAILED (hResult))
{ {
delete theEnumerator; delete theEnumerator;
return hResult; return hResult;
} }
*enumerator = result.Detach (); *enumerator = result.Detach ();
return S_OK; return S_OK;
} }

View file

@ -77,6 +77,8 @@ CDrivesFolderEnum::~CDrivesFolderEnum()
HRESULT WINAPI CDrivesFolderEnum::Initialize(HWND hwndOwner, DWORD dwFlags) HRESULT WINAPI CDrivesFolderEnum::Initialize(HWND hwndOwner, DWORD dwFlags)
{ {
DbgPrint("[shell32, CDrivesFolderEnum::Initialize] Called with flags = %d\n", dwFlags);
if (CreateMyCompEnumList(dwFlags) == FALSE) if (CreateMyCompEnumList(dwFlags) == FALSE)
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
@ -97,6 +99,8 @@ BOOL CDrivesFolderEnum::CreateMyCompEnumList(DWORD dwFlags)
TRACE("(%p)->(flags=0x%08x)\n", this, dwFlags); TRACE("(%p)->(flags=0x%08x)\n", this, dwFlags);
DbgPrint("[shell32, CDrivesFolderEnum::CreateMyCompEnumList] Called with flags = %d\n", dwFlags);
/* enumerate the folders */ /* enumerate the folders */
if (dwFlags & SHCONTF_FOLDERS) if (dwFlags & SHCONTF_FOLDERS)
{ {
@ -114,7 +118,8 @@ BOOL CDrivesFolderEnum::CreateMyCompEnumList(DWORD dwFlags)
} }
TRACE("-- (%p)-> enumerate (mycomputer shell extensions)\n", this); TRACE("-- (%p)-> enumerate (mycomputer shell extensions)\n", this);
for (i=0; i<2; i++) { for (i=0; i<2; i++)
{
if (ret && !RegOpenKeyExW(i == 0 ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER, if (ret && !RegOpenKeyExW(i == 0 ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER,
MyComputer_NameSpaceW, 0, KEY_READ, &hkey)) MyComputer_NameSpaceW, 0, KEY_READ, &hkey))
{ {
@ -255,19 +260,27 @@ HRESULT WINAPI CDrivesFolder::EnumObjects (HWND hwndOwner, DWORD dwFlags, LPENUM
TRACE ("(%p)->(HWND=%p flags=0x%08x pplist=%p)\n", this, hwndOwner, dwFlags, ppEnumIDList); TRACE ("(%p)->(HWND=%p flags=0x%08x pplist=%p)\n", this, hwndOwner, dwFlags, ppEnumIDList);
DbgPrint("[shell32, CDrivesFolder::EnumObjects] Called with flags = %d\n", dwFlags);
if (ppEnumIDList == NULL) if (ppEnumIDList == NULL)
return E_POINTER; return E_POINTER;
*ppEnumIDList = NULL;
*ppEnumIDList = NULL;
ATLTRY (theEnumerator = new CComObject<CDrivesFolderEnum>); ATLTRY (theEnumerator = new CComObject<CDrivesFolderEnum>);
if (theEnumerator == NULL)
if (theEnumerator == NULL)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result);
hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result);
if (FAILED (hResult)) if (FAILED (hResult))
{ {
delete theEnumerator; delete theEnumerator;
return hResult; return hResult;
} }
hResult = theEnumerator->Initialize (hwndOwner, dwFlags);
DbgPrint("[shell32, CDrivesFolder::EnumObjects] Calling theEnumerator->Initialize\n");
hResult = theEnumerator->Initialize (hwndOwner, dwFlags);
if (FAILED (hResult)) if (FAILED (hResult))
return hResult; return hResult;
*ppEnumIDList = result.Detach (); *ppEnumIDList = result.Detach ();

View file

@ -29,28 +29,28 @@ WINE_DEFAULT_DEBUG_CHANNEL (shell);
* Printers_IExtractIconW implementation * Printers_IExtractIconW implementation
*/ */
class IExtractIconWImpl : class IExtractIconWImpl :
public CComObjectRootEx<CComMultiThreadModelNoCS>, public CComObjectRootEx<CComMultiThreadModelNoCS>,
public IExtractIconW, public IExtractIconW,
public IExtractIconA public IExtractIconA
{ {
private: private:
LPITEMIDLIST pidl; LPITEMIDLIST pidl;
public: public:
IExtractIconWImpl(); IExtractIconWImpl();
~IExtractIconWImpl(); ~IExtractIconWImpl();
HRESULT WINAPI Initialize(LPCITEMIDLIST pidl); HRESULT WINAPI Initialize(LPCITEMIDLIST pidl);
// IExtractIconW // IExtractIconW
virtual HRESULT STDMETHODCALLTYPE GetIconLocation(UINT uFlags, LPWSTR szIconFile, UINT cchMax, int *piIndex, UINT *pwFlags); virtual HRESULT STDMETHODCALLTYPE GetIconLocation(UINT uFlags, LPWSTR szIconFile, UINT cchMax, int *piIndex, UINT *pwFlags);
virtual HRESULT STDMETHODCALLTYPE Extract(LPCWSTR pszFile, UINT nIconIndex, HICON *phiconLarge, HICON *phiconSmall, UINT nIconSize); virtual HRESULT STDMETHODCALLTYPE Extract(LPCWSTR pszFile, UINT nIconIndex, HICON *phiconLarge, HICON *phiconSmall, UINT nIconSize);
// IExtractIconA // IExtractIconA
virtual HRESULT STDMETHODCALLTYPE GetIconLocation(UINT uFlags, LPSTR szIconFile, UINT cchMax, int *piIndex, UINT *pwFlags); virtual HRESULT STDMETHODCALLTYPE GetIconLocation(UINT uFlags, LPSTR szIconFile, UINT cchMax, int *piIndex, UINT *pwFlags);
virtual HRESULT STDMETHODCALLTYPE Extract(LPCSTR pszFile, UINT nIconIndex, HICON *phiconLarge, HICON *phiconSmall, UINT nIconSize); virtual HRESULT STDMETHODCALLTYPE Extract(LPCSTR pszFile, UINT nIconIndex, HICON *phiconLarge, HICON *phiconSmall, UINT nIconSize);
BEGIN_COM_MAP(IExtractIconWImpl) BEGIN_COM_MAP(IExtractIconWImpl)
COM_INTERFACE_ENTRY_IID(IID_IExtractIconW, IExtractIconW) COM_INTERFACE_ENTRY_IID(IID_IExtractIconW, IExtractIconW)
COM_INTERFACE_ENTRY_IID(IID_IExtractIconA, IExtractIconA) COM_INTERFACE_ENTRY_IID(IID_IExtractIconA, IExtractIconA)
END_COM_MAP() END_COM_MAP()
}; };
@ -75,7 +75,7 @@ static shvheader PrinterSFHeader[] = {
IExtractIconWImpl::IExtractIconWImpl() IExtractIconWImpl::IExtractIconWImpl()
{ {
pidl = NULL; pidl = NULL;
} }
IExtractIconWImpl::~IExtractIconWImpl() IExtractIconWImpl::~IExtractIconWImpl()
@ -89,7 +89,7 @@ HRESULT WINAPI IExtractIconWImpl::Initialize(LPCITEMIDLIST pidl)
pidl = ILClone(pidl); pidl = ILClone(pidl);
pdump(pidl); pdump(pidl);
return S_OK; return S_OK;
} }
/************************************************************************** /**************************************************************************
@ -97,11 +97,11 @@ HRESULT WINAPI IExtractIconWImpl::Initialize(LPCITEMIDLIST pidl)
* *
* mapping filetype to icon * mapping filetype to icon
*/ */
HRESULT WINAPI IExtractIconWImpl::GetIconLocation(UINT uFlags, /* GIL_ flags */ HRESULT WINAPI IExtractIconWImpl::GetIconLocation(UINT uFlags, /* GIL_ flags */
LPWSTR szIconFile, LPWSTR szIconFile,
UINT cchMax, UINT cchMax,
int *piIndex, int *piIndex,
UINT *pwFlags) /* returned GIL_ flags */ UINT *pwFlags) /* returned GIL_ flags */
{ {
TRACE("(%p) (flags=%u %p %u %p %p)\n", this, uFlags, szIconFile, cchMax, piIndex, pwFlags); TRACE("(%p) (flags=%u %p %u %p %p)\n", this, uFlags, szIconFile, cchMax, piIndex, pwFlags);
@ -142,10 +142,10 @@ HRESULT WINAPI IExtractIconWImpl::Extract(LPCWSTR pszFile,
* IExtractIconA_GetIconLocation * IExtractIconA_GetIconLocation
*/ */
HRESULT WINAPI IExtractIconWImpl::GetIconLocation(UINT uFlags, HRESULT WINAPI IExtractIconWImpl::GetIconLocation(UINT uFlags,
LPSTR szIconFile, LPSTR szIconFile,
UINT cchMax, UINT cchMax,
int * piIndex, int * piIndex,
UINT * pwFlags) UINT * pwFlags)
{ {
HRESULT ret; HRESULT ret;
LPWSTR lpwstrFile = (LPWSTR)HeapAlloc(GetProcessHeap(), 0, cchMax * sizeof(WCHAR)); LPWSTR lpwstrFile = (LPWSTR)HeapAlloc(GetProcessHeap(), 0, cchMax * sizeof(WCHAR));
@ -183,27 +183,27 @@ HRESULT WINAPI IExtractIconWImpl::Extract(LPCSTR pszFile,
*/ */
static HRESULT WINAPI IEI_Printers_Constructor(LPCITEMIDLIST pidl, REFIID riid, IUnknown **ppv) static HRESULT WINAPI IEI_Printers_Constructor(LPCITEMIDLIST pidl, REFIID riid, IUnknown **ppv)
{ {
CComObject<IExtractIconWImpl> *theExtractor; CComObject<IExtractIconWImpl> *theExtractor;
CComPtr<IUnknown> result; CComPtr<IUnknown> result;
HRESULT hResult; HRESULT hResult;
if (ppv == NULL) if (ppv == NULL)
return E_POINTER; return E_POINTER;
*ppv = NULL; *ppv = NULL;
ATLTRY (theExtractor = new CComObject<IExtractIconWImpl>); ATLTRY (theExtractor = new CComObject<IExtractIconWImpl>);
if (theExtractor == NULL) if (theExtractor == NULL)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
hResult = theExtractor->QueryInterface (riid, (void **)&result); hResult = theExtractor->QueryInterface (riid, (void **)&result);
if (FAILED (hResult)) if (FAILED (hResult))
{ {
delete theExtractor; delete theExtractor;
return hResult; return hResult;
} }
hResult = theExtractor->Initialize (pidl); hResult = theExtractor->Initialize (pidl);
if (FAILED (hResult)) if (FAILED (hResult))
return hResult; return hResult;
*ppv = result.Detach (); *ppv = result.Detach ();
return S_OK; return S_OK;
} }
/*********************************************************************** /***********************************************************************
@ -211,17 +211,17 @@ static HRESULT WINAPI IEI_Printers_Constructor(LPCITEMIDLIST pidl, REFIID riid,
*/ */
class CPrintersEnum : class CPrintersEnum :
public IEnumIDListImpl public IEnumIDListImpl
{ {
private: private:
public: public:
CPrintersEnum(); CPrintersEnum();
~CPrintersEnum(); ~CPrintersEnum();
HRESULT WINAPI Initialize(HWND hwndOwner, DWORD dwFlags); HRESULT WINAPI Initialize(HWND hwndOwner, DWORD dwFlags);
BOOL CreatePrintersEnumList(DWORD dwFlags); BOOL CreatePrintersEnumList(DWORD dwFlags);
BEGIN_COM_MAP(CPrintersEnum) BEGIN_COM_MAP(CPrintersEnum)
COM_INTERFACE_ENTRY_IID(IID_IEnumIDList, IEnumIDList) COM_INTERFACE_ENTRY_IID(IID_IEnumIDList, IEnumIDList)
END_COM_MAP() END_COM_MAP()
}; };
@ -235,9 +235,9 @@ CPrintersEnum::~CPrintersEnum()
HRESULT WINAPI CPrintersEnum::Initialize(HWND hwndOwner, DWORD dwFlags) HRESULT WINAPI CPrintersEnum::Initialize(HWND hwndOwner, DWORD dwFlags)
{ {
if (CreatePrintersEnumList(dwFlags) == FALSE) if (CreatePrintersEnumList(dwFlags) == FALSE)
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
} }
static LPITEMIDLIST _ILCreatePrinterItem(PRINTER_INFO_4W *pi) static LPITEMIDLIST _ILCreatePrinterItem(PRINTER_INFO_4W *pi)
@ -327,6 +327,7 @@ CPrinterFolder::CPrinterFolder()
{ {
pidlRoot = NULL; pidlRoot = NULL;
dwAttributes = 0; dwAttributes = 0;
pclsid = NULL;
} }
CPrinterFolder::~CPrinterFolder() CPrinterFolder::~CPrinterFolder()
@ -339,9 +340,9 @@ CPrinterFolder::~CPrinterFolder()
HRESULT WINAPI CPrinterFolder::FinalConstruct() HRESULT WINAPI CPrinterFolder::FinalConstruct()
{ {
pidlRoot = _ILCreatePrinters(); /* my qualified pidl */ pidlRoot = _ILCreatePrinters(); /* my qualified pidl */
if (pidlRoot == NULL) if (pidlRoot == NULL)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
return S_OK; return S_OK;
} }
/************************************************************************** /**************************************************************************
@ -378,32 +379,32 @@ static PIDLPrinterStruct * _ILGetPrinterStruct(LPCITEMIDLIST pidl)
*/ */
HRESULT WINAPI CPrinterFolder::EnumObjects(HWND hwndOwner, DWORD dwFlags, LPENUMIDLIST * ppEnumIDList) HRESULT WINAPI CPrinterFolder::EnumObjects(HWND hwndOwner, DWORD dwFlags, LPENUMIDLIST * ppEnumIDList)
{ {
CComObject<CPrintersEnum> *theEnumerator; CComObject<CPrintersEnum> *theEnumerator;
CComPtr<IEnumIDList> result; CComPtr<IEnumIDList> result;
HRESULT hResult; HRESULT hResult;
TRACE ("(%p)->(HWND=%p flags=0x%08x pplist=%p)\n", this, hwndOwner, dwFlags, ppEnumIDList); TRACE ("(%p)->(HWND=%p flags=0x%08x pplist=%p)\n", this, hwndOwner, dwFlags, ppEnumIDList);
if (ppEnumIDList == NULL) if (ppEnumIDList == NULL)
return E_POINTER; return E_POINTER;
*ppEnumIDList = NULL; *ppEnumIDList = NULL;
ATLTRY (theEnumerator = new CComObject<CPrintersEnum>); ATLTRY (theEnumerator = new CComObject<CPrintersEnum>);
if (theEnumerator == NULL) if (theEnumerator == NULL)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result); hResult = theEnumerator->QueryInterface (IID_IEnumIDList, (void **)&result);
if (FAILED (hResult)) if (FAILED (hResult))
{ {
delete theEnumerator; delete theEnumerator;
return hResult; return hResult;
} }
hResult = theEnumerator->Initialize (hwndOwner, dwFlags); hResult = theEnumerator->Initialize (hwndOwner, dwFlags);
if (FAILED (hResult)) if (FAILED (hResult))
return hResult; return hResult;
*ppEnumIDList = result.Detach (); *ppEnumIDList = result.Detach ();
TRACE ("-- (%p)->(new ID List: %p)\n", this, *ppEnumIDList); TRACE ("-- (%p)->(new ID List: %p)\n", this, *ppEnumIDList);
return S_OK; return S_OK;
} }
/************************************************************************** /**************************************************************************

View file

@ -20,6 +20,7 @@
*/ */
#include <precomp.h> #include <precomp.h>
#include <windef.h>
WINE_DEFAULT_DEBUG_CHANNEL(exec); WINE_DEFAULT_DEBUG_CHANNEL(exec);

View file

@ -660,7 +660,7 @@ IDefaultContextMenuImpl::AddStaticContextMenusToMenu(
} }
else else
{ {
TRACE("Failed to laod string, defaulting to default (NULL) value for mii.dwTypeData\n"); TRACE("Failed to load string, defaulting to NULL value for mii.dwTypeData\n");
} }
} }
else else

View file

@ -87,6 +87,21 @@ GetKeyDescription(LPWSTR szKeyName, LPWSTR szResult)
return TRUE; return TRUE;
} }
void CNewMenu::UnloadItem(SHELLNEW_ITEM *item)
{
// bail if the item is clearly invalid
if (NULL == item)
return;
if (NULL != item->szTarget)
free(item->szTarget);
free(item->szDesc);
free(item->szIcon);
free(item->szExt);
HeapFree(GetProcessHeap(), 0, item);
}
CNewMenu::SHELLNEW_ITEM *CNewMenu::LoadItem(LPWSTR szKeyName) CNewMenu::SHELLNEW_ITEM *CNewMenu::LoadItem(LPWSTR szKeyName)
{ {

View file

@ -56,6 +56,7 @@ public:
CNewMenu(); CNewMenu();
~CNewMenu(); ~CNewMenu();
SHELLNEW_ITEM *LoadItem(LPWSTR szKeyName); SHELLNEW_ITEM *LoadItem(LPWSTR szKeyName);
void UnloadItem(SHELLNEW_ITEM *item);
BOOL LoadShellNewItems(); BOOL LoadShellNewItems();
UINT InsertShellNewItems(HMENU hMenu, UINT idFirst, UINT idMenu); UINT InsertShellNewItems(HMENU hMenu, UINT idFirst, UINT idMenu);
HRESULT DoShellNewCmd(LPCMINVOKECOMMANDINFO lpcmi); HRESULT DoShellNewCmd(LPCMINVOKECOMMANDINFO lpcmi);