mirror of
https://github.com/cemu-project/DS4Windows.git
synced 2024-11-29 20:44:20 +01:00
Changed IPC communication to use memory mapped memory instead of physical file to store the name of the DS4Form window class.
This commit is contained in:
parent
75d08fe76c
commit
c6daa18032
@ -87,9 +87,6 @@ namespace DS4Windows.Forms
|
|||||||
[DllImport("psapi.dll")]
|
[DllImport("psapi.dll")]
|
||||||
private static extern uint GetModuleFileNameEx(IntPtr hWnd, IntPtr hModule, StringBuilder lpFileName, int nSize);
|
private static extern uint GetModuleFileNameEx(IntPtr hWnd, IntPtr hModule, StringBuilder lpFileName, int nSize);
|
||||||
|
|
||||||
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
|
|
||||||
private static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
|
|
||||||
|
|
||||||
public DS4Form(string[] args)
|
public DS4Form(string[] args)
|
||||||
{
|
{
|
||||||
Global.FindConfigLocation();
|
Global.FindConfigLocation();
|
||||||
@ -391,16 +388,7 @@ namespace DS4Windows.Forms
|
|||||||
if (!(StartMinimized || mini))
|
if (!(StartMinimized || mini))
|
||||||
Form_Resize(null, null);
|
Form_Resize(null, null);
|
||||||
|
|
||||||
// Write current window class name as InterProcessCommunication identifier. The IPC classname is used in WM_DATACOPY messaging interface. .NET WinForms creates a semi-random clas names per application.
|
Program.CreateIPCClassNameMMF(this.Handle);
|
||||||
StringBuilder wndClassNameStr = new StringBuilder(256);
|
|
||||||
if (GetClassName(this.Handle, wndClassNameStr, wndClassNameStr.Capacity) != 0 && wndClassNameStr.Length > 0)
|
|
||||||
{
|
|
||||||
if (System.IO.File.Exists(appdatapath + "\\IPCClassName.dat") && System.IO.File.ReadAllText(appdatapath + "\\IPCClassName.dat") == wndClassNameStr.ToString())
|
|
||||||
wndClassNameStr.Clear(); // The wnd classname is still the same, so no need to re-write it
|
|
||||||
|
|
||||||
if(wndClassNameStr.Length > 0)
|
|
||||||
System.IO.File.WriteAllText(appdatapath + "\\IPCClassName.dat", wndClassNameStr.ToString());
|
|
||||||
}
|
|
||||||
|
|
||||||
Program.rootHub.Debug += On_Debug;
|
Program.rootHub.Debug += On_Debug;
|
||||||
|
|
||||||
|
@ -6,11 +6,16 @@ using Process = System.Diagnostics.Process;
|
|||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using Microsoft.Win32.TaskScheduler;
|
using Microsoft.Win32.TaskScheduler;
|
||||||
|
using System.IO.MemoryMappedFiles;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
namespace DS4Windows
|
namespace DS4Windows
|
||||||
{
|
{
|
||||||
static class Program
|
static class Program
|
||||||
{
|
{
|
||||||
|
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
|
||||||
|
private static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
|
||||||
|
|
||||||
[DllImport("user32.dll", EntryPoint = "FindWindow")]
|
[DllImport("user32.dll", EntryPoint = "FindWindow")]
|
||||||
private static extern IntPtr FindWindow(string sClass, string sWindow);
|
private static extern IntPtr FindWindow(string sClass, string sWindow);
|
||||||
|
|
||||||
@ -36,6 +41,9 @@ namespace DS4Windows
|
|||||||
private static Thread controlThread;
|
private static Thread controlThread;
|
||||||
private static Form ds4form;
|
private static Form ds4form;
|
||||||
|
|
||||||
|
private static MemoryMappedFile ipcClassNameMMF = null; // MemoryMappedFile for inter-process communication used to hold className of DS4Form window
|
||||||
|
private static MemoryMappedViewAccessor ipcClassNameMMA = null;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The main entry point for the application.
|
/// The main entry point for the application.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -86,15 +94,14 @@ namespace DS4Windows
|
|||||||
|
|
||||||
IntPtr hWndDS4WindowsForm = IntPtr.Zero;
|
IntPtr hWndDS4WindowsForm = IntPtr.Zero;
|
||||||
|
|
||||||
Global.FindConfigLocation();
|
if (args[i].Length > 0 && args[i].Length <= 256)
|
||||||
if (args[i].Length > 0 && args[i].Length <= 256 && !string.IsNullOrEmpty(Global.appdatapath) && System.IO.File.Exists(Global.appdatapath + "\\IPCClassName.dat"))
|
|
||||||
{
|
{
|
||||||
// Find the main DS4Form window handle and post WM_COPYDATA inter-process message. IPCClasName.dat file was created by the main DS4Windows process
|
// Find the main DS4Form window handle and post WM_COPYDATA inter-process message. IPCClasName.dat file was created by the main DS4Windows process
|
||||||
// and it contains the name of the DS4Form .NET window class name string (the hash key part of the string is dynamically generated by .NET engine and it may change,
|
// and it contains the name of the DS4Form .NET window class name string (the hash key part of the string is dynamically generated by .NET engine and it may change,
|
||||||
// so that's why the main process re-creates the file if the window class name is changed by .NET framework). Finding the WND handle usig both class name and window name
|
// so that's why the main process re-creates the file if the window class name is changed by .NET framework). Finding the WND handle usig both class name and window name
|
||||||
// limits chances that WM_COPYDATA message is sent to a wrong window.
|
// limits chances that WM_COPYDATA message is sent to a wrong window.
|
||||||
|
|
||||||
hWndDS4WindowsForm = FindWindow(System.IO.File.ReadAllText(Global.appdatapath + "\\IPCClassName.dat"), "DS4Windows");
|
hWndDS4WindowsForm = FindWindow(ReadIPCClassNameMMF(), "DS4Windows");
|
||||||
if (hWndDS4WindowsForm != IntPtr.Zero)
|
if (hWndDS4WindowsForm != IntPtr.Zero)
|
||||||
{
|
{
|
||||||
COPYDATASTRUCT cds;
|
COPYDATASTRUCT cds;
|
||||||
@ -178,6 +185,9 @@ namespace DS4Windows
|
|||||||
while (testThread.IsAlive)
|
while (testThread.IsAlive)
|
||||||
Thread.SpinWait(500);
|
Thread.SpinWait(500);
|
||||||
threadComEvent.Close();
|
threadComEvent.Close();
|
||||||
|
|
||||||
|
if (ipcClassNameMMA != null) ipcClassNameMMA.Dispose();
|
||||||
|
if (ipcClassNameMMF != null) ipcClassNameMMF.Dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void createControlService()
|
private static void createControlService()
|
||||||
@ -233,5 +243,54 @@ namespace DS4Windows
|
|||||||
temp.WindowState = FormWindowState.Normal;
|
temp.WindowState = FormWindowState.Normal;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static void CreateIPCClassNameMMF(IntPtr hWnd)
|
||||||
|
{
|
||||||
|
if (ipcClassNameMMA != null) return; // Already holding a handle to MMF file. No need to re-write the data
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
StringBuilder wndClassNameStr = new StringBuilder(128);
|
||||||
|
if (GetClassName(hWnd, wndClassNameStr, wndClassNameStr.Capacity) != 0 && wndClassNameStr.Length > 0)
|
||||||
|
{
|
||||||
|
byte[] buffer = ASCIIEncoding.ASCII.GetBytes(wndClassNameStr.ToString());
|
||||||
|
|
||||||
|
ipcClassNameMMF = MemoryMappedFile.CreateNew("DS4Windows_IPCClassName.dat", 128);
|
||||||
|
ipcClassNameMMA = ipcClassNameMMF.CreateViewAccessor(0, buffer.Length);
|
||||||
|
ipcClassNameMMA.WriteArray(0, buffer, 0, buffer.Length);
|
||||||
|
// The MMF file is alive as long this process holds the file handle open
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception)
|
||||||
|
{
|
||||||
|
/* Eat all exceptions because errors here are not fatal for DS4Win */
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string ReadIPCClassNameMMF()
|
||||||
|
{
|
||||||
|
MemoryMappedFile mmf = null;
|
||||||
|
MemoryMappedViewAccessor mma = null;
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
byte[] buffer = new byte[128];
|
||||||
|
mmf = MemoryMappedFile.OpenExisting("DS4Windows_IPCClassName.dat");
|
||||||
|
mma = mmf.CreateViewAccessor(0, 128);
|
||||||
|
mma.ReadArray(0, buffer, 0, buffer.Length);
|
||||||
|
return ASCIIEncoding.ASCII.GetString(buffer);
|
||||||
|
}
|
||||||
|
catch (Exception)
|
||||||
|
{
|
||||||
|
// Eat all exceptions
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (mma != null) mma.Dispose();
|
||||||
|
if (mmf != null) mmf.Dispose();
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
Loading…
Reference in New Issue
Block a user