--- a/uriloader/exthandler/win/nsMIMEInfoWin.cpp
+++ b/uriloader/exthandler/win/nsMIMEInfoWin.cpp
@@ -51,16 +51,26 @@
#include "nsTArray.h"
#include "shlobj.h"
#include "windows.h"
#include "nsIWindowsRegKey.h"
#include "nsIProcess.h"
#include "nsOSHelperAppService.h"
#include "nsUnicharUtils.h"
+#ifdef WINCE
+#ifdef UNICODE
+#define SHELLEXECUTEINFOW SHELLEXECUTEINFO
+#define ShellExecuteExW ShellExecuteEx
+#else
+#error "we don't support narrow char wince"
+#endif
+#endif
+
+
NS_IMPL_ISUPPORTS_INHERITED1(nsMIMEInfoWin, nsMIMEInfoBase, nsIPropertyBag)
nsMIMEInfoWin::~nsMIMEInfoWin()
{
}
nsresult
nsMIMEInfoWin::LaunchDefaultWithFile(nsIFile* aFile)
@@ -118,46 +128,56 @@ nsMIMEInfoWin::LaunchWithFile(nsIFile* a
// executable is rundll32, everything else is a list of parameters,
// including the dll handler.
nsCOMPtr<nsILocalFile> locFile(do_QueryInterface(aFile));
if (!GetDllLaunchInfo(executable, locFile, args, PR_FALSE))
return NS_ERROR_INVALID_ARG;
- int result = (int)
- ::ShellExecuteW(NULL, NULL, L"rundll32.exe", args.get(),
- NULL, SW_SHOWNORMAL);
- // Returns a value greater than 32 if successful. See msdn.
- if (result > 32)
+ SHELLEXECUTEINFOW seinfo;
+ memset(&seinfo, 0, sizeof(seinfo));
+ seinfo.cbSize = sizeof(SHELLEXECUTEINFOW);
+ seinfo.fMask = NULL;
+ seinfo.hwnd = NULL;
+ seinfo.lpVerb = NULL;
+ seinfo.lpFile = L"rundll32.exe";
+ seinfo.lpParameters = args.get();
+ seinfo.lpDirectory = NULL;
+ seinfo.nShow = SW_SHOWNORMAL;
+ if (ShellExecuteExW(&seinfo))
return NS_OK;
- switch (result) {
+ switch ((int)seinfo.hInstApp) {
case 0:
case SE_ERR_OOM:
return NS_ERROR_OUT_OF_MEMORY;
- case ERROR_FILE_NOT_FOUND:
- return NS_ERROR_FILE_NOT_FOUND;
- case ERROR_PATH_NOT_FOUND:
- return NS_ERROR_FILE_UNRECOGNIZED_PATH;
- case ERROR_BAD_FORMAT:
- return NS_ERROR_FILE_CORRUPTED;
case SE_ERR_ACCESSDENIED:
return NS_ERROR_FILE_ACCESS_DENIED;
case SE_ERR_ASSOCINCOMPLETE:
case SE_ERR_NOASSOC:
return NS_ERROR_UNEXPECTED;
case SE_ERR_DDEBUSY:
case SE_ERR_DDEFAIL:
case SE_ERR_DDETIMEOUT:
return NS_ERROR_NOT_AVAILABLE;
case SE_ERR_DLLNOTFOUND:
return NS_ERROR_FAILURE;
case SE_ERR_SHARE:
return NS_ERROR_FILE_IS_LOCKED;
+ default:
+ switch(GetLastError()) {
+ case ERROR_FILE_NOT_FOUND:
+ return NS_ERROR_FILE_NOT_FOUND;
+ case ERROR_PATH_NOT_FOUND:
+ return NS_ERROR_FILE_UNRECOGNIZED_PATH;
+ case ERROR_BAD_FORMAT:
+ return NS_ERROR_FILE_CORRUPTED;
+ }
+
}
return NS_ERROR_FILE_EXECUTION_FAILED;
}
}
return LaunchWithIProcess(executable, path);
}
return NS_ERROR_INVALID_ARG;
@@ -223,22 +243,24 @@ nsMIMEInfoWin::GetProperty(const nsAStri
rv = GetIconURLVariant(executable, _retval);
NS_ENSURE_SUCCESS(rv, rv);
}
return NS_OK;
}
+#ifndef WINCE
typedef HRESULT (STDMETHODCALLTYPE *MySHParseDisplayName)
(PCWSTR pszName,
IBindCtx *pbc,
LPITEMIDLIST *ppidl,
SFGAOF sfgaoIn,
SFGAOF *psfgaoOut);
+#endif
// this implementation was pretty much copied verbatime from
// Tony Robinson's code in nsExternalProtocolWin.cpp
nsresult
nsMIMEInfoWin::LoadUriInternal(nsIURI * aURL)
{
nsresult rv = NS_OK;
@@ -257,54 +279,59 @@ nsMIMEInfoWin::LoadUriInternal(nsIURI *
// Some versions of windows (Win2k before SP3, Win XP before SP1)
// crash in ShellExecute on long URLs (bug 161357).
// IE 5 and 6 support URLS of 2083 chars in length, 2K is safe
const PRUint32 maxSafeURL(2048);
if (urlSpec.Length() > maxSafeURL)
return NS_ERROR_FAILURE;
+ HMODULE hDll = NULL;
+
+ static const PRUnichar cmdVerb[] = L"open";
+ SHELLEXECUTEINFOW sinfo;
+ memset(&sinfo, 0, sizeof(sinfo));
+ sinfo.cbSize = sizeof(sinfo);
+#ifdef WINCE
+ sinfo.fMask = NULL;
+#else
+ sinfo.fMask = SEE_MASK_FLAG_DDEWAIT |
+ SEE_MASK_FLAG_NO_UI ;
+#endif
+ sinfo.hwnd = NULL;
+ sinfo.lpVerb = (LPWSTR)&cmdVerb;
+ sinfo.nShow = SW_SHOWNORMAL;
+
+#ifndef WINCE
LPITEMIDLIST pidl;
SFGAOF sfgao;
// Bug 394974
- HMODULE hDll = ::LoadLibraryW(L"shell32.dll");
+ hDll = ::LoadLibraryW(L"shell32.dll");
MySHParseDisplayName pMySHParseDisplayName = NULL;
// Version 6.0 and higher
- if (pMySHParseDisplayName =
- (MySHParseDisplayName)::GetProcAddress(hDll,
- "SHParseDisplayName")) {
- if (SUCCEEDED(pMySHParseDisplayName(NS_ConvertUTF8toUTF16(urlSpec).get(),
- NULL, &pidl, 0, &sfgao))) {
- static const PRUnichar cmdVerb[] = L"open";
- SHELLEXECUTEINFOW sinfo;
- memset(&sinfo, 0, sizeof(sinfo));
- sinfo.cbSize = sizeof(sinfo);
- sinfo.fMask = SEE_MASK_FLAG_DDEWAIT |
- SEE_MASK_FLAG_NO_UI |
- SEE_MASK_INVOKEIDLIST;
- sinfo.hwnd = NULL;
- sinfo.lpVerb = (LPWSTR)&cmdVerb;
- sinfo.nShow = SW_SHOWNORMAL;
+ if ((pMySHParseDisplayName = (MySHParseDisplayName)
+ ::GetProcAddress(hDll, "SHParseDisplayName")) &&
+ (SUCCEEDED(pMySHParseDisplayName(NS_ConvertUTF8toUTF16(urlSpec).get(),
+ NULL, &pidl, 0, &sfgao)))) {
sinfo.lpIDList = pidl;
-
- BOOL result = ShellExecuteExW(&sinfo);
-
- CoTaskMemFree(pidl);
+ sinfo.fMask |= SEE_MASK_INVOKEIDLIST;
+ } else
+#endif
+ {
+ sinfo.lpFile = NS_ConvertUTF8toUTF16(urlSpec).get();
+ }
+ BOOL result = ShellExecuteExW(&sinfo);
+ if (!result || ((int)sinfo.hInstApp) < 32)
+ rv = NS_ERROR_FAILURE;
- if (!result || ((int)sinfo.hInstApp) < 32)
- rv = NS_ERROR_FAILURE;
- }
- } else {
- // Version of shell32.dll < 6.0
- int r = (int) ::ShellExecuteW(NULL, L"open", NS_ConvertUTF8toUTF16(urlSpec).get(),
- NULL, NULL, SW_SHOWNORMAL);
- if (r < 32)
- rv = NS_ERROR_FAILURE;
- }
+#ifndef WINCE
+ if (pidl)
+ CoTaskMemFree(pidl);
+#endif
if (hDll)
::FreeLibrary(hDll);
}
return rv;
}
// Given a path to a local file, return its nsILocalHandlerApp instance.