فهرست منبع

Holyfuckitworks

Krzysztof Krysiński 1 سال پیش
والد
کامیت
7039e7e4e1

+ 1 - 5
src/PixiEditor.Extensions.Wasm/Api/Logger.cs

@@ -25,10 +25,6 @@ public class Logger : ILogger
 
 
     private void InvokeApiLog(string message)
     private void InvokeApiLog(string message)
     {
     {
-        unsafe
-        {
-            IntPtr ptr = Marshal.StringToHGlobalAnsi(message);
-            Interop.LogMessage((char*)ptr);
-        }
+        Interop.LogMessage(message);
     }
     }
 }
 }

+ 2 - 1
src/PixiEditor.Extensions.Wasm/Interop.cs

@@ -5,5 +5,6 @@ namespace PixiEditor.Extensions.Wasm;
 
 
 internal class Interop
 internal class Interop
 {
 {
-    internal static extern unsafe void LogMessage(char* message);
+    [MethodImpl(MethodImplOptions.InternalCall)]
+    internal static extern void LogMessage(string message);
 }
 }

+ 2 - 1
src/PixiEditor.Extensions.Wasm/build/PixiEditor.Extensions.Wasm.targets

@@ -1,7 +1,8 @@
 <Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
 <Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
 
 
   <ItemGroup>
   <ItemGroup>
-    <WasmImport Include="$(MSBuildThisFileDirectory)..\native\*.c" />
+    <WasiNativeFileReference Include="$(MSBuildThisFileDirectory)..\native\*.c" />
+    <WasiAfterRuntimeLoaded Include="attach_internal_calls" />
   </ItemGroup>
   </ItemGroup>
 
 
 </Project>
 </Project>

+ 25 - 1
src/PixiEditor.Extensions.Wasm/native/api_interop.c

@@ -1,9 +1,33 @@
 #include <mono-wasi/driver.h>
 #include <mono-wasi/driver.h>
+#include <string.h>
+#include <assert.h>
+
+MonoMethod* method_entry;
 
 
 __attribute__((import_name("log_message")))
 __attribute__((import_name("log_message")))
 void log_message(const char* message);
 void log_message(const char* message);
 
 
+__attribute__((export_name("entry")))
+void entry()
+{
+    if (!method_entry) {
+        method_entry = lookup_dotnet_method("PixiEditor.Extensions.Wasm.dll", "PixiEditor.Extensions.Wasm", "Interop", "Entry", -1);
+        assert(method_entry);
+    }
+
+    void* method_params[] = {};
+    MonoObject *exception;
+    mono_wasm_invoke_method (method_entry, NULL, method_params, &exception);
+    assert (!exception);
+}
+
+void logger_log_message(MonoString* message)
+{
+    char* message_utf8 = mono_wasm_string_get_utf8(message);
+    log_message(message_utf8);
+}
+
 void attach_internal_calls()
 void attach_internal_calls()
 {
 {
-    mono_add_internal_call("PixiEditor.Extensions.Wasm.Interop::LogMessage", (void*)log_message);
+    mono_add_internal_call("PixiEditor.Extensions.Wasm.Interop::LogMessage", logger_log_message);
 }
 }

+ 1 - 0
src/PixiEditor.WasmRuntime/PixiEditor.WasmRuntime.csproj

@@ -4,6 +4,7 @@
         <TargetFramework>net8.0</TargetFramework>
         <TargetFramework>net8.0</TargetFramework>
         <ImplicitUsings>enable</ImplicitUsings>
         <ImplicitUsings>enable</ImplicitUsings>
         <Nullable>enable</Nullable>
         <Nullable>enable</Nullable>
+        <AllowUnsafeBlocks>true</AllowUnsafeBlocks>
     </PropertyGroup>
     </PropertyGroup>
 
 
     <ItemGroup>
     <ItemGroup>

+ 43 - 7
src/PixiEditor.WasmRuntime/WasmRuntime.cs

@@ -1,4 +1,7 @@
-using Wasmtime;
+using System.Runtime.InteropServices;
+using System.Text;
+using Wasmtime;
+using IntPtr = System.IntPtr;
 
 
 namespace PixiEditor.WasmRuntime;
 namespace PixiEditor.WasmRuntime;
 
 
@@ -6,22 +9,55 @@ public class WasmRuntime
 {
 {
     private Engine engine = new Engine();
     private Engine engine = new Engine();
 
 
-    public void LoadModule(string path)
+    public unsafe void LoadModule(string path)
     {
     {
         Module module = Module.FromFile(engine, path);
         Module module = Module.FromFile(engine, path);
         WasiConfiguration wasiConfig = new WasiConfiguration();
         WasiConfiguration wasiConfig = new WasiConfiguration();
+        wasiConfig.WithInheritedStandardError().WithInheritedStandardInput().WithInheritedStandardOutput()
+            .WithInheritedArgs().WithInheritedEnvironment();
+
+        using var config = new Config().WithDebugInfo(true)
+            .WithCraneliftDebugVerifier(true)
+            .WithOptimizationLevel(OptimizationLevel.SpeedAndSize)
+            .WithWasmThreads(true)
+            .WithBulkMemory(true)
+            .WithMultiMemory(true);
 
 
         var linker = new Linker(engine);
         var linker = new Linker(engine);
         var store = new Store(engine);
         var store = new Store(engine);
         store.SetWasiConfiguration(wasiConfig);
         store.SetWasiConfiguration(wasiConfig);
-
         linker.DefineWasi();
         linker.DefineWasi();
 
 
-        var instance = linker.Instantiate(store, module);
+        Instance? instance = null;
+
+        linker.DefineFunction("env", "log_message",(int message) =>
+        {
+            string messageString = GetFromWasmMemory(message, instance.GetMemory("memory"));
+            Console.WriteLine(messageString);
+        });
+
+        linker.DefineModule(store, module);
 
 
-        instance.GetAction("ProvideApi").Invoke();
-        var main = instance.GetAction("Entry");
+        instance = linker.Instantiate(store, module);
 
 
-        main.Invoke();
+        instance.GetFunction("_start").Invoke();
+        //linker.GetDefaultFunction(store, "WasmSampleExtension").Invoke();
+        /*var main = instance.GetAction("entry");
+
+        main.Invoke();*/
+    }
+
+    private string GetFromWasmMemory(int offset, Memory memory)
+    {
+        var span = memory.GetSpan<byte>(offset);
+        int length = 0;
+        while (span[length] != 0)
+        {
+            length++;
+        }
+
+        var buffer = new byte[length];
+        span.Slice(0, length).CopyTo(buffer);
+        return Encoding.UTF8.GetString(buffer);
     }
     }
 }
 }

+ 1 - 1
src/WasmRuntimeTest/Program.cs

@@ -2,4 +2,4 @@
 using PixiEditor.WasmRuntime;
 using PixiEditor.WasmRuntime;
 
 
 WasmRuntime runtime = new WasmRuntime();
 WasmRuntime runtime = new WasmRuntime();
-runtime.LoadModule(@"C:\Git\PixiEditor\src\WasmSampleExtension\bin\Release\net8.0\wasi-wasm\publish\WasmSampleExtension.wasm");
+runtime.LoadModule(@"C:\Git\PixiEditor\src\WasmSampleExtension\bin\Debug\net8.0\WasmSampleExtension.wasm");

+ 0 - 14
src/WasmSampleExtension/Entry.cs

@@ -1,14 +0,0 @@
-using System.Runtime.InteropServices;
-using PixiEditor.Extensions.Wasm;
-
-namespace SampleExtension.WASM;
-
-public static class Entry
-{
-    [UnmanagedCallersOnly(EntryPoint = "Entry")]
-    public static void EntryPoint()
-    {
-        SampleExtension extension = new SampleExtension();
-        extension.OnLoaded();
-    }
-}

+ 11 - 0
src/WasmSampleExtension/Program.cs

@@ -0,0 +1,11 @@
+namespace SampleExtension.WASM;
+
+public static class Program
+{
+    public static void Main(string[] args)
+    {
+        SampleExtension sampleExtension = new SampleExtension();
+        sampleExtension.OnLoaded();
+        sampleExtension.OnInitialized();
+    }
+}

+ 6 - 3
src/WasmSampleExtension/WasmSampleExtension.csproj

@@ -2,16 +2,19 @@
 
 
   <PropertyGroup>
   <PropertyGroup>
     <TargetFramework>net8.0</TargetFramework>
     <TargetFramework>net8.0</TargetFramework>
-    <OutputType>Library</OutputType>
+    <OutputType>Exe</OutputType>
     <ImplicitUsings>enable</ImplicitUsings>
     <ImplicitUsings>enable</ImplicitUsings>
     <Nullable>enable</Nullable>
     <Nullable>enable</Nullable>
     <PublishTrimmed>true</PublishTrimmed>
     <PublishTrimmed>true</PublishTrimmed>
-    <RuntimeIdentifier>wasi-wasm</RuntimeIdentifier>
     <MSBuildEnableWorkloadResolver>false</MSBuildEnableWorkloadResolver>
     <MSBuildEnableWorkloadResolver>false</MSBuildEnableWorkloadResolver>
   </PropertyGroup>
   </PropertyGroup>
 
 
+  <Import Project="..\PixiEditor.Extensions.Wasm\build\PixiEditor.Extensions.Wasm.targets"/>
+  <Import Project="..\PixiEditor.Extensions.Wasm\build\PixiEditor.Extensions.Wasm.props"/>
+  
   <ItemGroup>
   <ItemGroup>
-    <PackageReference Include="Microsoft.DotNet.ILCompiler.LLVM; runtime.win-x64.Microsoft.DotNet.ILCompiler.LLVM" Version="9.0.0-*" />
+    <!--<PackageReference Include="Microsoft.DotNet.ILCompiler.LLVM; runtime.win-x64.Microsoft.DotNet.ILCompiler.LLVM" Version="9.0.0-*" />-->
+    <PackageReference Include="Wasi.Sdk" Version="0.1.4-preview.10020" />
   </ItemGroup>
   </ItemGroup>
 
 
   <ItemGroup>
   <ItemGroup>