diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/App.config b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/App.config new file mode 100644 index 0000000..56efbc7 --- /dev/null +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/App.config @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/NamedSharedMemory.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/NamedSharedMemory.cs new file mode 100644 index 0000000..92722fe --- /dev/null +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/NamedSharedMemory.cs @@ -0,0 +1,197 @@ +/* + * WelsonJS.Toolkit.Experimental: WelsonJS experimental native testing component + * + * filename: + * NamedSharedMemory.cs + * + * description: + * WelsonJS - Build a Windows app on the Windows built-in JavaScript engine + * + * website: + * - https://github.com/gnh1201/welsonjs + * - https://catswords.social/@catswords_oss + * + * author: + * Namhyeon Go + * + * license: + * GPLv3 or MS-RL(Microsoft Reciprocal License) + * + */ +using System; +using System.Collections.Generic; +using System.Runtime.InteropServices; +using System.Text; + +namespace WelsonJS.Toolkit.Experimental +{ + public class NamedSharedMemory + { + private IntPtr hFile; + private IntPtr hFileMappingObject; + private string lpName; + private static Dictionary memDict = new Dictionary(); + + [Flags] + public enum FileProtection : uint + { + PAGE_NOACCESS = 1u, + PAGE_READONLY = 2u, + PAGE_READWRITE = 4u, + PAGE_WRITECOPY = 8u, + PAGE_EXECUTE = 0x10u, + PAGE_EXECUTE_READ = 0x20u, + PAGE_EXECUTE_READWRITE = 0x40u, + PAGE_EXECUTE_WRITECOPY = 0x80u, + PAGE_GUARD = 0x100u, + PAGE_NOCACHE = 0x200u, + PAGE_WRITECOMBINE = 0x400u, + SEC_FILE = 0x800000u, + SEC_IMAGE = 0x1000000u, + SEC_RESERVE = 0x4000000u, + SEC_COMMIT = 0x8000000u, + SEC_NOCACHE = 0x10000000u + } + + [Flags] + public enum FileMapAccess + { + FILE_MAP_COPY = 1, + FILE_MAP_WRITE = 2, + FILE_MAP_READ = 4, + FILE_MAP_ALL_ACCESS = 0xF001F + } + + public class FileMappingNative + { + public const int INVALID_HANDLE_VALUE = -1; + + [DllImport("kernel32.dll", SetLastError = true)] + public static extern IntPtr CreateFileMapping(IntPtr hFile, IntPtr lpAttributes, FileProtection flProtect, uint dwMaximumSizeHigh, uint dwMaximumSizeLow, string lpName); + + [DllImport("kernel32.dll", SetLastError = true)] + public static extern IntPtr MapViewOfFile(IntPtr hFileMappingObject, FileMapAccess dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow, uint dwNumberOfBytesToMap); + + [DllImport("kernel32.dll", SetLastError = true)] + public static extern IntPtr OpenFileMapping(FileMapAccess dwDesiredAccess, bool bInheritHandle, string lpName); + + [DllImport("kernel32.dll", SetLastError = true)] + [return: MarshalAs(UnmanagedType.Bool)] + public static extern bool UnmapViewOfFile(IntPtr lpBaseAddress); + + [DllImport("kernel32.dll", SetLastError = true)] + [return: MarshalAs(UnmanagedType.Bool)] + public static extern bool CloseHandle(IntPtr hHandle); + + [DllImport("kernel32.dll", SetLastError = true)] + public static extern uint GetLastError(); + } + + public NamedSharedMemory(string lpName) + { + this.lpName = lpName; + Open(); + } + + public bool Open() + { + if (memDict.ContainsKey(lpName)) + { + hFile = memDict[lpName].hFile; + hFileMappingObject = memDict[lpName].hFileMappingObject; + return true; + } + + try + { + hFile = FileMappingNative.CreateFileMapping((IntPtr)(-1), IntPtr.Zero, FileProtection.PAGE_READWRITE, 0u, 1024u, lpName); + hFileMappingObject = FileMappingNative.MapViewOfFile(hFile, FileMapAccess.FILE_MAP_ALL_ACCESS, 0u, 0u, 1024u); + memDict.Add(lpName, this); + } + catch + { + return false; + } + + return IsInitialized(); + } + + public bool IsInitialized() + { + return hFile != IntPtr.Zero; + } + + public string ReadText() + { + try + { + if (hFile == IntPtr.Zero || hFileMappingObject == IntPtr.Zero) + { + throw new Exception("Could not access the shared memory"); + } + return Marshal.PtrToStringAnsi(hFileMappingObject); + } + catch (Exception e) + { + return "Exception: " + e.Message; + } + } + + public bool WriteText(string text, int size = 1024) + { + try + { + if (hFile == IntPtr.Zero || hFileMappingObject == IntPtr.Zero) + { + throw new Exception("Could not access the shared memory"); + } + byte[] bytes = Encoding.ASCII.GetBytes(text); + byte[] array = new byte[size + 1]; + Array.Copy(bytes, array, bytes.Length); + Marshal.Copy(array, 0, hFileMappingObject, size); + } + catch + { + return false; + } + + return true; + } + + public bool Clear(int size = 1024) + { + try + { + Marshal.Copy(new byte[size + 1], 0, hFileMappingObject, size); + } + catch + { + return false; + } + + return true; + } + + public bool Close() + { + try + { + if (hFile == IntPtr.Zero || hFileMappingObject == IntPtr.Zero) + { + throw new Exception("Could not access the shared memory"); + } + + FileMappingNative.UnmapViewOfFile(hFileMappingObject); + hFileMappingObject = IntPtr.Zero; + FileMappingNative.CloseHandle(hFile); + hFile = IntPtr.Zero; + } + catch + { + return false; + } + + return true; + } + } +} diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Program.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Program.cs new file mode 100644 index 0000000..b12af77 --- /dev/null +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Program.cs @@ -0,0 +1,60 @@ +using System; +using System.Diagnostics; +using System.Threading; +using System.Windows.Forms; + +namespace WelsonJS.Toolkit.Experimental +{ + internal class Program + { + static void Main(string[] args) + { + SharedMemoryListener listener = new SharedMemoryListener(); + + Console.Write("Input the shared memory name: "); + listener.memName = Console.ReadLine(); + + Console.Write("Input the second process name: "); + listener.processName = listener.OpenFileDialog(); + + Thread listenerThread = new Thread(listener.Listen); + listenerThread.Start(); + + Process.Start(listener.processName); + } + + class SharedMemoryListener + { + public string memName { get; set; } + public string processName { get; set; } + + public void Listen() + { + NamedSharedMemory mem = new NamedSharedMemory(memName); + Console.WriteLine("Listening the shared memory..."); + while (true) + { + Console.WriteLine(mem.ReadText()); + Thread.Sleep(100); + } + } + + public string OpenFileDialog() + { + string filepath = string.Empty; + + using (OpenFileDialog openFileDialog = new OpenFileDialog()) + { + openFileDialog.Filter = "All files (*.*)|*.*"; + openFileDialog.RestoreDirectory = true; + if (openFileDialog.ShowDialog() == DialogResult.OK) + { + filepath = openFileDialog.FileName; + } + } + + return filepath; + } + } + } +} diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Properties/AssemblyInfo.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..42d5fec --- /dev/null +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// 어셈블리에 대한 일반 정보는 다음 특성 집합을 통해 +// 제어됩니다. 어셈블리와 관련된 정보를 수정하려면 +// 이러한 특성 값을 변경하세요. +[assembly: AssemblyTitle("WelsonJS.Toolkit.Experimental")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("WelsonJS.Toolkit.Experimental")] +[assembly: AssemblyCopyright("Copyright © 2024")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// ComVisible을 false로 설정하면 이 어셈블리의 형식이 COM 구성 요소에 +// 표시되지 않습니다. COM에서 이 어셈블리의 형식에 액세스하려면 +// 해당 형식에 대해 ComVisible 특성을 true로 설정하세요. +[assembly: ComVisible(false)] + +// 이 프로젝트가 COM에 노출되는 경우 다음 GUID는 typelib의 ID를 나타냅니다. +[assembly: Guid("3a53f700-57a3-48ed-9e3d-92b4f8c43056")] + +// 어셈블리의 버전 정보는 다음 네 가지 값으로 구성됩니다. +// +// 주 버전 +// 부 버전 +// 빌드 번호 +// 수정 버전 +// +// 모든 값을 지정하거나 아래와 같이 '*'를 사용하여 빌드 번호 및 수정 번호를 +// 기본값으로 할 수 있습니다. +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/WelsonJS.Toolkit.Experimental.csproj b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/WelsonJS.Toolkit.Experimental.csproj new file mode 100644 index 0000000..ddaefe0 --- /dev/null +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.Experimental/WelsonJS.Toolkit.Experimental.csproj @@ -0,0 +1,55 @@ + + + + + Debug + AnyCPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056} + Exe + WelsonJS.Toolkit.Experimental + WelsonJS.Toolkit.Experimental + v4.7.2 + 512 + true + true + + + AnyCPU + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + AnyCPU + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit.sln b/WelsonJS.Toolkit/WelsonJS.Toolkit.sln index 1a3ba0e..fec15c0 100644 --- a/WelsonJS.Toolkit/WelsonJS.Toolkit.sln +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit.sln @@ -5,6 +5,8 @@ VisualStudioVersion = 17.8.34322.80 MinimumVisualStudioVersion = 10.0.40219.1 Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WelsonJS.Toolkit", "WelsonJS.Toolkit\WelsonJS.Toolkit.csproj", "{D6007282-B4F7-4694-AC67-BB838D91B77A}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WelsonJS.Toolkit.Experimental", "WelsonJS.Toolkit.Experimental\WelsonJS.Toolkit.Experimental.csproj", "{3A53F700-57A3-48ED-9E3D-92B4F8C43056}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -25,6 +27,18 @@ Global {D6007282-B4F7-4694-AC67-BB838D91B77A}.Release|x64.ActiveCfg = Release|x64 {D6007282-B4F7-4694-AC67-BB838D91B77A}.Release|x64.Build.0 = Release|x64 {D6007282-B4F7-4694-AC67-BB838D91B77A}.Release|x86.ActiveCfg = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|Any CPU.Build.0 = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|x64.ActiveCfg = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|x64.Build.0 = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|x86.ActiveCfg = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Debug|x86.Build.0 = Debug|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|Any CPU.ActiveCfg = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|Any CPU.Build.0 = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|x64.ActiveCfg = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|x64.Build.0 = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|x86.ActiveCfg = Release|Any CPU + {3A53F700-57A3-48ED-9E3D-92B4F8C43056}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit/NamedSharedMemory.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit/NamedSharedMemory.cs index 8c78a49..31fda99 100644 --- a/WelsonJS.Toolkit/WelsonJS.Toolkit/NamedSharedMemory.cs +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit/NamedSharedMemory.cs @@ -1,5 +1,5 @@ /* - * WelsonJS.Toolkit: WelsonJS dotNET native component + * WelsonJS.Toolkit: WelsonJS native component * * filename: * NamedSharedMemory.cs @@ -62,7 +62,7 @@ namespace WelsonJS FILE_MAP_ALL_ACCESS = 0xF001F } - public static class FileMappingNative + public class FileMappingNative { public const int INVALID_HANDLE_VALUE = -1; diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit/Prompt.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit/Prompt.cs index 240e82d..cc8e43f 100644 --- a/WelsonJS.Toolkit/WelsonJS.Toolkit/Prompt.cs +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit/Prompt.cs @@ -1,5 +1,5 @@ /* - * WelsonJS.Toolkit: WelsonJS dotNET native component + * WelsonJS.Toolkit: WelsonJS native component * * filename: * Prompt.cs diff --git a/WelsonJS.Toolkit/WelsonJS.Toolkit/Toolkit.cs b/WelsonJS.Toolkit/WelsonJS.Toolkit/Toolkit.cs index 618331b..ae80305 100644 --- a/WelsonJS.Toolkit/WelsonJS.Toolkit/Toolkit.cs +++ b/WelsonJS.Toolkit/WelsonJS.Toolkit/Toolkit.cs @@ -1,5 +1,5 @@ /* - * WelsonJS.Toolkit: WelsonJS dotNET native component + * WelsonJS.Toolkit: WelsonJS native component * * filename: * Toolkit.cs diff --git a/bin/x64/WelsonJS.Toolkit.Experimental.exe b/bin/x64/WelsonJS.Toolkit.Experimental.exe new file mode 100644 index 0000000..125f5db Binary files /dev/null and b/bin/x64/WelsonJS.Toolkit.Experimental.exe differ diff --git a/bin/x64/WelsonJS.Toolkit.dll b/bin/x64/WelsonJS.Toolkit.dll index e6c846a..5b101e1 100644 Binary files a/bin/x64/WelsonJS.Toolkit.dll and b/bin/x64/WelsonJS.Toolkit.dll differ diff --git a/bin/x64/WelsonJS.Toolkit.pdb b/bin/x64/WelsonJS.Toolkit.pdb index 5b1b931..fa13b0c 100644 Binary files a/bin/x64/WelsonJS.Toolkit.pdb and b/bin/x64/WelsonJS.Toolkit.pdb differ diff --git a/bin/x86/WelsonJS.Toolkit.dll b/bin/x86/WelsonJS.Toolkit.dll index 4d069c0..5c0bf3e 100644 Binary files a/bin/x86/WelsonJS.Toolkit.dll and b/bin/x86/WelsonJS.Toolkit.dll differ diff --git a/bin/x86/WelsonJS.Toolkit.pdb b/bin/x86/WelsonJS.Toolkit.pdb index 5b1b931..fa13b0c 100644 Binary files a/bin/x86/WelsonJS.Toolkit.pdb and b/bin/x86/WelsonJS.Toolkit.pdb differ