Add a separate sanity check for SMX.dll existing, since Windows gives the same error if a DLL is missing or one of its dependencies is missing.
This commit is contained in:
parent
8ea8070d51
commit
3d6eb112e6
@ -15,9 +15,16 @@ namespace smx_config
|
|||||||
{
|
{
|
||||||
AppDomain.CurrentDomain.UnhandledException += UnhandledExceptionEventHandler;
|
AppDomain.CurrentDomain.UnhandledException += UnhandledExceptionEventHandler;
|
||||||
|
|
||||||
|
if(!SMX.SMX.DLLExists())
|
||||||
|
{
|
||||||
|
MessageBox.Show("SMXConfig encountered an unexpected error.\n\nSMX.dll couldn't be found:\n\n" + Helpers.GetLastWin32ErrorString(), "SMXConfig");
|
||||||
|
Current.Shutdown();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if(!SMX.SMX.DLLAvailable())
|
if(!SMX.SMX.DLLAvailable())
|
||||||
{
|
{
|
||||||
MessageBox.Show("SMXConfig encountered an unexpected error:\n\nSMX.dll failed to load.", "SMXConfig");
|
MessageBox.Show("SMXConfig encountered an unexpected error.\n\nSMX.dll failed to load:\n\n" + Helpers.GetLastWin32ErrorString(), "SMXConfig");
|
||||||
Current.Shutdown();
|
Current.Shutdown();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Runtime.InteropServices;
|
||||||
using System.Windows.Media;
|
using System.Windows.Media;
|
||||||
using System.Windows.Threading;
|
using System.Windows.Threading;
|
||||||
using SMXJSON;
|
using SMXJSON;
|
||||||
@ -79,6 +80,15 @@ namespace smx_config
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Return the last Win32 error as a string.
|
||||||
|
public static string GetLastWin32ErrorString()
|
||||||
|
{
|
||||||
|
int error = Marshal.GetLastWin32Error();
|
||||||
|
if(error == 0)
|
||||||
|
return "";
|
||||||
|
return new System.ComponentModel.Win32Exception(error).Message;
|
||||||
|
}
|
||||||
|
|
||||||
// Work around Enumerable.SequenceEqual not checking if the arrays are null.
|
// Work around Enumerable.SequenceEqual not checking if the arrays are null.
|
||||||
public static bool SequenceEqual<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
|
public static bool SequenceEqual<TSource>(this IEnumerable<TSource> first, IEnumerable<TSource> second)
|
||||||
{
|
{
|
||||||
|
@ -198,8 +198,27 @@ namespace SMX
|
|||||||
|
|
||||||
public static class SMX
|
public static class SMX
|
||||||
{
|
{
|
||||||
|
[System.Flags]
|
||||||
|
enum LoadLibraryFlags : uint
|
||||||
|
{
|
||||||
|
None = 0,
|
||||||
|
DONT_RESOLVE_DLL_REFERENCES = 0x00000001,
|
||||||
|
LOAD_IGNORE_CODE_AUTHZ_LEVEL = 0x00000010,
|
||||||
|
LOAD_LIBRARY_AS_DATAFILE = 0x00000002,
|
||||||
|
LOAD_LIBRARY_AS_DATAFILE_EXCLUSIVE = 0x00000040,
|
||||||
|
LOAD_LIBRARY_AS_IMAGE_RESOURCE = 0x00000020,
|
||||||
|
LOAD_LIBRARY_SEARCH_APPLICATION_DIR = 0x00000200,
|
||||||
|
LOAD_LIBRARY_SEARCH_DEFAULT_DIRS = 0x00001000,
|
||||||
|
LOAD_LIBRARY_SEARCH_DLL_LOAD_DIR = 0x00000100,
|
||||||
|
LOAD_LIBRARY_SEARCH_SYSTEM32 = 0x00000800,
|
||||||
|
LOAD_LIBRARY_SEARCH_USER_DIRS = 0x00000400,
|
||||||
|
LOAD_WITH_ALTERED_SEARCH_PATH = 0x00000008
|
||||||
|
}
|
||||||
|
|
||||||
[DllImport("kernel32", SetLastError=true)]
|
[DllImport("kernel32", SetLastError=true)]
|
||||||
static extern IntPtr LoadLibrary(string lpFileName);
|
static extern IntPtr LoadLibrary(string lpFileName);
|
||||||
|
[DllImport("kernel32.dll", SetLastError = true)]
|
||||||
|
static extern IntPtr LoadLibraryEx(string lpFileName, IntPtr hReservedNull, LoadLibraryFlags dwFlags);
|
||||||
[DllImport("SMX.dll", CallingConvention = CallingConvention.Cdecl)]
|
[DllImport("SMX.dll", CallingConvention = CallingConvention.Cdecl)]
|
||||||
private static extern void SMX_Start(
|
private static extern void SMX_Start(
|
||||||
[MarshalAs(UnmanagedType.FunctionPtr)] InternalUpdateCallback callback,
|
[MarshalAs(UnmanagedType.FunctionPtr)] InternalUpdateCallback callback,
|
||||||
@ -229,11 +248,21 @@ namespace SMX
|
|||||||
private static extern bool SMX_ReenableAutoLights();
|
private static extern bool SMX_ReenableAutoLights();
|
||||||
|
|
||||||
// Check if the native DLL is available. This is mostly to avoid exceptions in the designer.
|
// Check if the native DLL is available. This is mostly to avoid exceptions in the designer.
|
||||||
|
// This returns false if the DLL doesn't load.
|
||||||
public static bool DLLAvailable()
|
public static bool DLLAvailable()
|
||||||
{
|
{
|
||||||
|
|
||||||
return LoadLibrary("SMX.dll") != IntPtr.Zero;
|
return LoadLibrary("SMX.dll") != IntPtr.Zero;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check if the native DLL exists. This will return false if SMX.dll is missing entirely,
|
||||||
|
// but not if it fails to load for another reason like runtime dependencies. This just lets
|
||||||
|
// us print a more specific error message.
|
||||||
|
public static bool DLLExists()
|
||||||
|
{
|
||||||
|
return LoadLibraryEx("SMX.dll", (IntPtr)0, LoadLibraryFlags.LOAD_LIBRARY_AS_DATAFILE_EXCLUSIVE) != IntPtr.Zero;
|
||||||
|
}
|
||||||
|
|
||||||
public delegate void UpdateCallback(int PadNumber, SMXUpdateCallbackReason reason);
|
public delegate void UpdateCallback(int PadNumber, SMXUpdateCallbackReason reason);
|
||||||
|
|
||||||
// The C API allows a user pointer, but we don't use that here.
|
// The C API allows a user pointer, but we don't use that here.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user