コード例 #1
0
        /// <summary>
        /// Instantiates the tables in the given WebAssembly file.
        /// </summary>
        /// <param name="File">The file whose tables are to be instantiated.</param>
        private void InstantiateTables(WasmFile File)
        {
            // Create module-defined tables.
            var allTableSections = File.GetSections <TableSection>();

            for (int i = 0; i < allTableSections.Count; i++)
            {
                foreach (var tableSpec in allTableSections[i].Tables)
                {
                    definedTables.Add(new FunctionTable(tableSpec.Limits));
                }
            }

            // Initialize tables by applying the segments defined by element sections.
            var allElementSections = File.GetSections <ElementSection>();

            for (int i = 0; i < allElementSections.Count; i++)
            {
                foreach (var segment in allElementSections[i].Segments)
                {
                    var table      = Tables[(int)segment.TableIndex];
                    var evalOffset = Evaluate <int>(segment.Offset);
                    for (int j = 0; j < segment.Elements.Count; j++)
                    {
                        table[(uint)(evalOffset + j)] = definedFuncs[(int)segment.Elements[j]];
                    }
                }
            }
        }
コード例 #2
0
ファイル: Program.cs プロジェクト: blinds52/cs-wasm
        public static int Main(string[] args)
        {
            CatArgs parsedArgs;

            if (!CatArgs.TryParse(args, out parsedArgs))
            {
                Console.Error.WriteLine("usage: wasm-cat file.wasm... [-o output.wasm]");
                return(1);
            }

            var file = new WasmFile();

            foreach (var path in parsedArgs.Inputs)
            {
                // Read the file and append its sections to the resulting file.
                var inputFile = WasmFile.ReadBinary(path);
                file.Sections.AddRange(inputFile.Sections);

                // Also, set the WebAssembly version number to the max of the
                // input files.
                if (inputFile.Header.Version > file.Header.Version)
                {
                    file.Header = inputFile.Header;
                }
            }

            // Now write the file to standard output.
            using (var outputStream = string.IsNullOrEmpty(parsedArgs.Output)
                ? Console.OpenStandardOutput()
                : File.OpenWrite(parsedArgs.Output))
            {
                file.WriteBinaryTo(outputStream);
            }
            return(0);
        }
コード例 #3
0
        /// <summary>
        /// Instantiates all function definitions from the given WebAssembly file.
        /// </summary>
        /// <param name="File">A WebAssembly file.</param>
        /// <param name="FunctionTypes">The list of all function types declared by the WebAssembly file.</param>
        private void InstantiateFunctionDefs(WasmFile File, List <FunctionType> FunctionTypes)
        {
            var funcSignatures = new List <FunctionType>();
            var funcBodies     = new List <FunctionBody>();

            var allFuncSections = File.GetSections <FunctionSection>();

            for (int i = 0; i < allFuncSections.Count; i++)
            {
                foreach (var funcSpec in allFuncSections[i].FunctionTypes)
                {
                    funcSignatures.Add(FunctionTypes[(int)funcSpec]);
                }
            }

            var allCodeSections = File.GetSections <CodeSection>();

            for (int i = 0; i < allCodeSections.Count; i++)
            {
                funcBodies.AddRange(allCodeSections[i].Bodies);
            }

            if (funcSignatures.Count != funcBodies.Count)
            {
                throw new WasmException(
                          "Function declaration/definition count mismatch: module declares " +
                          funcSignatures.Count + " functions and defines " + funcBodies.Count + ".");
            }

            for (int i = 0; i < funcSignatures.Count; i++)
            {
                DefineFunction(funcSignatures[i], funcBodies[i]);
            }
        }
コード例 #4
0
        private void InstantiateMemories(WasmFile File)
        {
            // Create module-defined memories.
            var allMemorySections = File.GetSections <MemorySection>();

            for (int i = 0; i < allMemorySections.Count; i++)
            {
                var memorySection = allMemorySections[i];
                foreach (var memorySpec in memorySection.Memories)
                {
                    definedMemories.Add(new LinearMemory(memorySpec.Limits));
                }
            }

            // Initialize memories by applying the segments defined by data sections.
            var allDataSections = File.GetSections <DataSection>();

            for (int i = 0; i < allDataSections.Count; i++)
            {
                var dataSection = allDataSections[i];
                foreach (var segment in dataSection.Segments)
                {
                    var memoryView = Memories[(int)segment.MemoryIndex].Int8;
                    var evalOffset = Evaluate <int>(segment.Offset);
                    for (int j = 0; j < segment.Data.Length; j++)
                    {
                        memoryView[(uint)(evalOffset + j)] = (sbyte)segment.Data[j];
                    }
                }
            }
        }
コード例 #5
0
ファイル: Program.cs プロジェクト: sassembla/cs-wasm
        public static int Main(string[] args)
        {
            if (args.Length > 1)
            {
                Console.Error.WriteLine("usage: wasm-dump [file.wasm]");
                return(1);
            }

            WasmFile file;

            if (args.Length == 0)
            {
                using (var input = ReadStdinToEnd())
                {
                    file = WasmFile.ReadBinary(input);
                }
            }
            else
            {
                file = WasmFile.ReadBinary(args[0]);
            }
            file.Dump(Console.Out);
            Console.WriteLine();
            return(0);
        }
コード例 #6
0
    private void LoadFromFile()
    {
        string   path = Application.streamingAssetsPath + "/test.wasm";
        WasmFile file = WasmFile.ReadBinary(path);

        Perform(file);
    }
コード例 #7
0
    // Start is called before the first frame update
    void Start()
    {
        // wasmファイルを読み込む
        string   path = Application.streamingAssetsPath + "/something.wasm";
        WasmFile file = WasmFile.ReadBinary(path);

        // importerを生成
        var importer = new PredefinedImporter();

        // 関数定義情報の注入
        importer.DefineFunction(
            "GetParam",                     // 関数名
            new DelegateFunctionDefinition( // 関数の定義
                new WasmValueType[] { },
                new[] { WasmValueType.Int32, },
                GetParam
                )
            );

        // wasmをインスタンス化
        ModuleInstance module = ModuleInstance.Instantiate(file, importer);

        // インスタンスから、定義済み関数の取得を試みる
        if (module.ExportedFunctions.TryGetValue("Something", out FunctionDefinition funcDef))
        {
            // 関数が見つかったらそれを実行
            IReadOnlyList <object> results = funcDef.Invoke(new object[] { 1, });
            Debug.Log("定義があったよ==〜" + results[0]);
        }
    }
コード例 #8
0
        /// <summary>
        /// Instantiates the given WebAssembly file. An importer is used to
        /// resolve module imports and an interpreter is used to interpret
        /// instructions.
        /// </summary>
        /// <param name="File">The file to instantiate.</param>
        /// <param name="Importer">Resolves module imports.</param>
        /// <param name="Interpreter">Interprets instructions.</param>
        /// <returns>A module instance.</returns>
        public static ModuleInstance Instantiate(
            WasmFile File,
            IImporter Importer,
            InstructionInterpreter Interpreter)
        {
            var instance = new ModuleInstance(Interpreter);

            // Extract the function types.
            var allFuncTypes = GetFunctionTypes(File);

            // Resolve all imports.
            instance.ResolveImports(File, Importer, allFuncTypes);

            // Instantiate global variables.
            instance.InstantiateGlobals(File);

            // Instantiate memories.
            instance.InstantiateMemories(File);

            // Instantiate function definitions.
            instance.InstantiateFunctionDefs(File, allFuncTypes);

            // Instantiate function tables.
            instance.InstantiateTables(File);

            // Export values.
            instance.RegisterExports(File);

            return(instance);
        }
コード例 #9
0
        /// <summary>
        /// Exports values specified by the given WebAssembly file.
        /// </summary>
        /// <param name="File">The file that specifies which values are to be exported and how.</param>
        private void RegisterExports(WasmFile File)
        {
            var allExportSections = File.GetSections <ExportSection>();

            for (int i = 0; i < allExportSections.Count; i++)
            {
                foreach (var export in allExportSections[i].Exports)
                {
                    switch (export.Kind)
                    {
                    case ExternalKind.Memory:
                        expMemories[export.Name] = Memories[(int)export.Index];
                        break;

                    case ExternalKind.Global:
                        expGlobals[export.Name] = Globals[(int)export.Index];
                        break;

                    case ExternalKind.Function:
                        expFuncs[export.Name] = Functions[(int)export.Index];
                        break;

                    case ExternalKind.Table:
                        expTables[export.Name] = Tables[(int)export.Index];
                        break;

                    default:
                        throw new WasmException("Unknown export kind: " + export.Kind);
                    }
                }
            }
        }
コード例 #10
0
        private object EvaluateConstExpr(SExpression expression, WasmValueType resultType)
        {
            var anonModule   = new WasmFile();
            var instructions = Assembler.AssembleInstructionExpression(expression, anonModule);
            var inst         = ModuleInstance.Instantiate(anonModule, new SpecTestImporter());

            return(inst.Evaluate(new InitializerExpression(instructions), resultType));
        }
コード例 #11
0
ファイル: BinaryWasmWriter.cs プロジェクト: sassembla/cs-wasm
 /// <summary>
 /// Writes a WebAssembly file.
 /// </summary>
 /// <param name="file">The WebAssembly file to write.</param>
 public void WriteFile(WasmFile file)
 {
     WriteVersionHeader(file.Header);
     foreach (var section in file.Sections)
     {
         WriteSection(section);
     }
 }
コード例 #12
0
ファイル: Program.cs プロジェクト: sassembla/cs-wasm
        public static void Main(string[] args)
        {
            // Create an empty WebAssembly file.
            var file = new WasmFile();

            // Define a type section.
            var typeSection = new TypeSection();

            file.Sections.Add(typeSection);

            // Write the file to a (memory) stream.
            var stream = new MemoryStream();

            file.WriteBinaryTo(stream);
            stream.Seek(0, SeekOrigin.Begin);

            // Read the file from a (memory) stream.
            file = WasmFile.ReadBinary(stream);
            stream.Seek(0, SeekOrigin.Begin);

            // Define a memory section if it doesn't exist already.
            var memSection = file.GetFirstSectionOrNull <MemorySection>();

            if (memSection == null)
            {
                // The file doesn't specify a memory section, so we'll
                // have to create one and add it to the file.
                memSection = new MemorySection();
                file.Sections.Add(memSection);
            }

            memSection.Memories.Clear();
            // Memory sizes are specified in WebAssembly pages,
            // which are regions of storage with size 64KiB.
            // `new ResizableLimits(1, 1)` creates a memory description
            // that is initially one page (first argument) in size and
            // is capped at one page of memory (second argument), so
            // there will always be exactly one page of linear memory.
            memSection.Memories.Add(
                new MemoryType(new ResizableLimits(1, 1)));

            // Print the memory size.
            List <MemoryType> memSections =
                file.GetFirstSectionOrNull <MemorySection>()
                .Memories;

            Console.WriteLine(
                "Memory size: {0}",
                memSections
                .Single <MemoryType>()
                .Limits);

            // Save the file again.
            file.WriteBinaryTo(stream);
            stream.Seek(0, SeekOrigin.Begin);
        }
コード例 #13
0
        /// <summary>
        /// Uses the given importer to resolve all imported values.
        /// </summary>
        /// <param name="Importer">The importer.</param>
        private void ResolveImports(
            WasmFile File,
            IImporter Importer,
            List <FunctionType> FunctionTypes)
        {
            var allImportSections = File.GetSections <ImportSection>();

            for (int i = 0; i < allImportSections.Count; i++)
            {
                var importSection = allImportSections[i];
                foreach (var import in importSection.Imports)
                {
                    if (import is ImportedMemory)
                    {
                        var memory = Importer.ImportMemory((ImportedMemory)import);
                        if (memory == null)
                        {
                            ThrowCannotResolveImport(import, "linear memory");
                        }
                        definedMemories.Add(memory);
                    }
                    else if (import is ImportedGlobal)
                    {
                        var globalVar = Importer.ImportGlobal((ImportedGlobal)import);
                        if (globalVar == null)
                        {
                            ThrowCannotResolveImport(import, "global variable");
                        }
                        definedGlobals.Add(globalVar);
                    }
                    else if (import is ImportedFunction)
                    {
                        var funcImport = (ImportedFunction)import;
                        var funcDef    = Importer.ImportFunction(funcImport, FunctionTypes[(int)funcImport.TypeIndex]);
                        if (funcDef == null)
                        {
                            ThrowCannotResolveImport(import, "function");
                        }
                        definedFuncs.Add(funcDef);
                    }
                    else if (import is ImportedTable)
                    {
                        var table = Importer.ImportTable((ImportedTable)import);
                        if (table == null)
                        {
                            ThrowCannotResolveImport(import, "table");
                        }
                        definedTables.Add(table);
                    }
                    else
                    {
                        throw new WasmException("Unknown import type: " + import.ToString());
                    }
                }
            }
        }
コード例 #14
0
        /// <summary>
        /// Gets a list of all function types declared by the given WebAssembly file.
        /// </summary>
        /// <param name="File">The WebAssembly file to examine.</param>
        /// <returns>The list of function types.</returns>
        private static List <FunctionType> GetFunctionTypes(WasmFile File)
        {
            var allFuncTypes    = new List <FunctionType>();
            var allTypeSections = File.GetSections <TypeSection>();

            for (int i = 0; i < allTypeSections.Count; i++)
            {
                allFuncTypes.AddRange(allTypeSections[i].FunctionTypes);
            }
            return(allFuncTypes);
        }
コード例 #15
0
        protected void LoadWasm(WasmFile file, ContentsStore store = null)
        {
            if (store == null)
            {
                store = new ContentsStore();
            }

            var importer = new PredefinedImporter();

            var wasiFunctions = new List <string>()
            {
                "proc_exit",
                "fd_write",
                "fd_prestat_get",
                "fd_prestat_dir_name",
                "environ_sizes_get",
                "environ_get",
                //"env.abort",
                "abort",
            };

            foreach (var wasiFunction in wasiFunctions)
            {
                importer.DefineFunction(wasiFunction,
                                        new DelegateFunctionDefinition(
                                            new WasmValueType[] { },
                                            new WasmValueType[] { },
                                            x => x
                                            ));
            }

            var gameObjectBinding = new GameObjectBinding(transform, store);

            importer.IncludeDefinitions(gameObjectBinding.Importer);

            var transformBinding = new TransformBinding(transform, store);

            importer.IncludeDefinitions(transformBinding.Importer);

            var physicsBinding = new PhysicsBinding(transform, store);

            importer.IncludeDefinitions(physicsBinding.Importer);

            var timeBinding = new TimeBinding();

            importer.IncludeDefinitions(timeBinding.Importer);

            module = ModuleInstance.Instantiate(file, importer);

            var exportedFunctions = module.ExportedFunctions;

            exportedFunctions.TryGetValue("update", out updateFunction);
            exportedFunctions.TryGetValue("on_touch_start", out onTouchStartFunction);
        }
コード例 #16
0
 /// <summary>
 /// Applies all known optimizations to the given WebAssembly file.
 /// </summary>
 /// <param name="file">The file to optimize.</param>
 public static void Optimize(this WasmFile file)
 {
     file.CompressFunctionTypes();
     foreach (var section in file.Sections)
     {
         if (section is CodeSection)
         {
             ((CodeSection)section).Optimize();
         }
     }
 }
コード例 #17
0
    private void LoadFromServer()
    {
        UnityWebRequest req = UnityWebRequest.Get(_url);

        req.SendWebRequest().completed += operation =>
        {
            MemoryStream stream = new MemoryStream();

            stream.Write(req.downloadHandler.data, 0, req.downloadHandler.data.Length);
            stream.Seek(0, SeekOrigin.Begin);

            WasmFile file = WasmFile.ReadBinary(stream);

            Perform(file);
        };
    }
コード例 #18
0
        /// <summary>
        /// Instantiates the given WebAssembly file.
        /// </summary>
        /// <param name="file">The file to instantiate.</param>
        /// <param name="importer">The importer to use to resolve module imports.</param>
        /// <param name="interpreter">
        /// Interprets instructions. A <c>null</c> interpreter indicates that the default interpreter should be used.
        /// </param>
        /// <param name="policy">
        /// The execution policy to adhere to for this module.
        /// A <c>null</c> execution policy indicates that the default policy should be used.
        /// </param>
        /// <param name="compiler">
        /// Creates a new instance of a module compiler to use.
        /// </param>
        /// <returns>A module instance.</returns>
        public static ModuleInstance Instantiate(
            WasmFile file,
            IImporter importer,
            InstructionInterpreter interpreter = null,
            ExecutionPolicy policy             = null,
            Func <ModuleCompiler> compiler     = null)
        {
            if (interpreter == null)
            {
                interpreter = DefaultInstructionInterpreter.Default;
            }
            if (policy == null)
            {
                policy = ExecutionPolicy.Create();
            }
            if (compiler == null)
            {
                compiler = () => new InterpreterCompiler();
            }

            var instance = new ModuleInstance(interpreter, policy);

            // Extract the function types.
            var allFuncTypes = GetFunctionTypes(file);

            instance.definedTypes.AddRange(allFuncTypes);

            // Resolve all imports.
            instance.ResolveImports(file, importer, allFuncTypes);

            // Instantiate global variables.
            instance.InstantiateGlobals(file);

            // Instantiate memories.
            instance.InstantiateMemories(file, policy.MaxMemorySize);

            // Instantiate function definitions.
            instance.InstantiateFunctionDefs(file, compiler(), allFuncTypes);

            // Instantiate function tables.
            instance.InstantiateTables(file);

            // Export values.
            instance.RegisterExports(file);

            return(instance);
        }
コード例 #19
0
        private void InstantiateGlobals(WasmFile File)
        {
            // Create module-defined globals.
            var allGlobalSections = File.GetSections <GlobalSection>();

            for (int i = 0; i < allGlobalSections.Count; i++)
            {
                var globalSection = allGlobalSections[i];
                foreach (var globalSpec in globalSection.GlobalVariables)
                {
                    definedGlobals.Add(
                        Variable.Create <object>(
                            globalSpec.Type.ContentType,
                            globalSpec.Type.IsMutable,
                            Evaluate <object>(globalSpec.InitialValue)));
                }
            }
        }
コード例 #20
0
        private void InstantiateMemories(WasmFile file, uint maxMemorySize)
        {
            // Create module-defined memories.
            var allMemorySections = file.GetSections <MemorySection>();

            for (int i = 0; i < allMemorySections.Count; i++)
            {
                var memorySection = allMemorySections[i];
                foreach (var memorySpec in memorySection.Memories)
                {
                    if (maxMemorySize == 0)
                    {
                        definedMemories.Add(new LinearMemory(memorySpec.Limits));
                    }
                    else
                    {
                        definedMemories.Add(
                            new LinearMemory(
                                new ResizableLimits(
                                    memorySpec.Limits.Initial,
                                    memorySpec.Limits.HasMaximum
                                        ? Math.Min(memorySpec.Limits.Maximum.Value, maxMemorySize)
                                        : maxMemorySize)));
                    }
                }
            }

            // Initialize memories by applying the segments defined by data sections.
            var allDataSections = file.GetSections <DataSection>();

            for (int i = 0; i < allDataSections.Count; i++)
            {
                var dataSection = allDataSections[i];
                foreach (var segment in dataSection.Segments)
                {
                    var memoryView = Memories[(int)segment.MemoryIndex].Int8;
                    var evalOffset = Evaluate <int>(segment.Offset);
                    for (int j = 0; j < segment.Data.Length; j++)
                    {
                        memoryView[(uint)(evalOffset + j)] = (sbyte)segment.Data[j];
                    }
                }
            }
        }
コード例 #21
0
    private void Perform(WasmFile file)
    {
        var importer = new PredefinedImporter();

        importer.DefineFunction(
            "GetParam",
            new DelegateFunctionDefinition(
                new WasmValueType[] { },
                new[] { WasmValueType.Int32, },
                GetParam));

        ModuleInstance module = ModuleInstance.Instantiate(file, importer);

        if (module.ExportedFunctions.TryGetValue("Test", out FunctionDefinition funcDef2))
        {
            IReadOnlyList <object> results = funcDef2.Invoke(new object[] { 1, });
            Debug.Log(results[0]);
            _text.text = results[0].ToString();
        }
    }
コード例 #22
0
        /// <summary>
        /// Rewrites function type references in the given WebAssembly file
        /// by replacing keys from the rewrite map with their corresponding
        /// values.
        /// </summary>
        /// <param name="File">The WebAssembly file to rewrite.</param>
        /// <param name="RewriteMap">A mapping of original type indices to new type indices.</param>
        public static void RewriteFunctionTypeReferences(
            this WasmFile File,
            IReadOnlyDictionary <uint, uint> RewriteMap)
        {
            // Type references occur only in the import and function sections.
            var importSections = File.GetSections <ImportSection>();

            for (int i = 0; i < importSections.Count; i++)
            {
                var importSec = importSections[i];
                for (int j = 0; j < importSec.Imports.Count; j++)
                {
                    var  importDecl = importSec.Imports[j] as ImportedFunction;
                    uint newIndex;
                    if (importDecl != null && RewriteMap.TryGetValue(importDecl.TypeIndex, out newIndex))
                    {
                        importDecl.TypeIndex = newIndex;
                    }
                }
            }

            var funcSections = File.GetSections <FunctionSection>();

            for (int i = 0; i < funcSections.Count; i++)
            {
                var funcSec = funcSections[i];
                for (int j = 0; j < funcSec.FunctionTypes.Count; j++)
                {
                    uint newIndex;
                    if (RewriteMap.TryGetValue(funcSec.FunctionTypes[j], out newIndex))
                    {
                        funcSec.FunctionTypes[j] = newIndex;
                    }
                }
            }
        }
コード例 #23
0
        /// <summary>
        /// Compresses function types in the given WebAssembly file
        /// by including only unique function types.
        /// </summary>
        /// <param name="File">The WebAssembly file to modify.</param>
        public static void CompressFunctionTypes(
            this WasmFile File)
        {
            // Grab the first type section.
            var typeSection = File.GetFirstSectionOrNull <TypeSection>();

            if (typeSection == null)
            {
                return;
            }

            // Make all types from the first type section distinct.
            IReadOnlyList <FunctionType>     newTypes;
            IReadOnlyDictionary <uint, uint> typeIndexMap;

            MakeFunctionTypesDistinct(typeSection.FunctionTypes, out newTypes, out typeIndexMap);

            // Rewrite the type section's function types.
            typeSection.FunctionTypes.Clear();
            typeSection.FunctionTypes.AddRange(newTypes);

            // Rewrite type indices.
            File.RewriteFunctionTypeReferences(typeIndexMap);
        }
コード例 #24
0
        /// <summary>
        /// Instantiates all function definitions from the given WebAssembly file.
        /// </summary>
        /// <param name="file">A WebAssembly file.</param>
        /// <param name="compiler">A compiler to use for instantiating function definitions.</param>
        /// <param name="functionTypes">The list of all function types declared by the WebAssembly file.</param>
        private void InstantiateFunctionDefs(WasmFile file, ModuleCompiler compiler, List <FunctionType> functionTypes)
        {
            var funcSignatures = new List <FunctionType>();
            var funcBodies     = new List <FunctionBody>();

            var allFuncSections = file.GetSections <FunctionSection>();

            for (int i = 0; i < allFuncSections.Count; i++)
            {
                foreach (var funcSpec in allFuncSections[i].FunctionTypes)
                {
                    funcSignatures.Add(functionTypes[(int)funcSpec]);
                }
            }

            var allCodeSections = file.GetSections <CodeSection>();

            for (int i = 0; i < allCodeSections.Count; i++)
            {
                funcBodies.AddRange(allCodeSections[i].Bodies);
            }

            if (funcSignatures.Count != funcBodies.Count)
            {
                throw new WasmException(
                          "Function declaration/definition count mismatch: module declares " +
                          funcSignatures.Count + " functions and defines " + funcBodies.Count + ".");
            }

            compiler.Initialize(this, definedFuncs.Count, funcSignatures);
            for (int i = 0; i < funcSignatures.Count; i++)
            {
                DefineFunction(compiler.Compile(i, funcBodies[i]));
            }
            compiler.Finish();
        }
コード例 #25
0
ファイル: Program.cs プロジェクト: sassembla/cs-wasm
        public static int Main(string[] args)
        {
            OptArgs parsedArgs;

            if (!OptArgs.TryParse(args, out parsedArgs))
            {
                Console.Error.WriteLine("usage: wasm-opt file.wasm [-o output.wasm]");
                return(1);
            }

            // Read the file.
            var file = WasmFile.ReadBinary(parsedArgs.Input);

            file.Optimize();

            // Now write the file to standard output.
            using (var outputStream = string.IsNullOrEmpty(parsedArgs.Output)
                ? Console.OpenStandardOutput()
                : File.OpenWrite(parsedArgs.Output))
            {
                file.WriteBinaryTo(outputStream);
            }
            return(0);
        }
コード例 #26
0
ファイル: Program.cs プロジェクト: sassembla/cs-wasm
        public static int Main(string[] args)
        {
            // Read command-line arguments.
            InterpreterArguments parsedArgs;

            if (!InterpreterArguments.TryRead(args, out parsedArgs))
            {
                return(PrintUsage());
            }

            IImporter importer;

            if (!parsedArgs.TryGetImporter(out importer))
            {
                Console.Error.WriteLine("error: there is no importer named '" + parsedArgs.ImporterName + "'");
                return(1);
            }

            // Read and instantiate the module.
            var wasmFile = WasmFile.ReadBinary(parsedArgs.WasmFilePath);
            InstructionInterpreter interp = DefaultInstructionInterpreter.Default;

            if (parsedArgs.TraceExecution)
            {
                interp = new TracingInstructionInterpreter(interp, Console.Error);
            }
            var module = ModuleInstance.Instantiate(wasmFile, importer, interp);

            // Figure out which function to run.
            FunctionDefinition funcToRun = null;

            if (parsedArgs.FunctionToRun != null)
            {
                if (!module.ExportedFunctions.TryGetValue(parsedArgs.FunctionToRun, out funcToRun))
                {
                    Console.Error.WriteLine(
                        "error: module does not export a function named '" +
                        parsedArgs.FunctionToRun + "'");
                    return(1);
                }
            }
            else
            {
                var startSec = wasmFile.GetFirstSectionOrNull <StartSection>();
                if (startSec == null)
                {
                    Console.Error.WriteLine(
                        "error: module does not define a 'start' section " +
                        " and '--run exported_func_name' was not specified.");
                    return(1);
                }
                else
                {
                    IReadOnlyList <FunctionDefinition> funcs = module.Functions;
                    funcToRun = funcs[(int)startSec.StartFunctionIndex];
                }
            }

            // Run that function.
            int exitCode = 0;

            try
            {
                IReadOnlyList <object> output = funcToRun.Invoke(parsedArgs.FunctionArgs);
                if (output.Count > 0)
                {
                    for (int i = 0; i < output.Count; i++)
                    {
                        if (i > 0)
                        {
                            Console.Write(" ");
                        }
                        Console.Write(output[i]);
                    }
                    Console.WriteLine();
                }
            }
            catch (WasmException ex)
            {
                Console.Error.WriteLine("error: " + ex.Message);
                exitCode = 1;
            }
            return(exitCode);
        }
コード例 #27
0
        protected void LoadWasm(WasmFile file, ContentsStore store = null, List <string> args = null)
        {
            if (store == null)
            {
                store = new ContentsStore();
            }

            var importer = new PredefinedImporter();

            var wasiFunctions = new List <string>()
            {
                "proc_exit",
                "fd_read",
                "fd_write",
                "fd_prestat_get",
                "fd_prestat_dir_name",
                "environ_sizes_get",
                "environ_get",
                // "random_get",
                //"env.abort",
                "abort",
            };

            foreach (var wasiFunction in wasiFunctions)
            {
                importer.DefineFunction(wasiFunction,
                                        new DelegateFunctionDefinition(
                                            new WasmValueType[] { },
                                            new WasmValueType[] { },
                                            x => x
                                            ));
            }
            importer.DefineFunction("random_get",
                                    new DelegateFunctionDefinition(
                                        ValueType.PointerAndPointer,
                                        ValueType.Int,
                                        x => ReturnValue.FromObject(0)
                                        ));

            var element = new Element()
            {
                GameObject = gameObject
            };

            if (args == null)
            {
                args = new List <string>();
            }
            var scriptName = "";

            args.Insert(0, scriptName);

            var argsBinding = new ArgsBinding(element, store, args);

            importer.IncludeDefinitions(argsBinding.Importer);

            var debugBinding = new DebugBinding(element, store);

            importer.IncludeDefinitions(debugBinding.Importer);

            var gameObjectBinding = new GameObjectBinding(element, store);

            importer.IncludeDefinitions(gameObjectBinding.Importer);

            var transformBinding = new TransformBinding(element, store);

            importer.IncludeDefinitions(transformBinding.Importer);

            var physicsBinding = new PhysicsBinding(element, store);

            importer.IncludeDefinitions(physicsBinding.Importer);

            var timeBinding = new TimeBinding(element, store);

            importer.IncludeDefinitions(timeBinding.Importer);

            module = ModuleInstance.Instantiate(file, importer);

            argsBinding.ModuleInstance       = module;
            gameObjectBinding.ModuleInstance = module;
            debugBinding.ModuleInstance      = module;

            var exportedFunctions = module.ExportedFunctions;

            exportedFunctions.TryGetValue("start", out startFunction);
            exportedFunctions.TryGetValue("update", out updateFunction);
            exportedFunctions.TryGetValue("on_touch_start", out onTouchStartFunction);
            exportedFunctions.TryGetValue("on_use", out onUseFunction);
        }
コード例 #28
0
        public void LoadWasm(Stream stream, ContentsStore store = null, List <string> args = null)
        {
            var file = WasmFile.ReadBinary(stream);

            LoadWasm(file, store, args);
        }
コード例 #29
0
        public void LoadWasm(Stream stream, ContentsStore store = null)
        {
            var file = WasmFile.ReadBinary(stream);

            LoadWasm(file, store);
        }
コード例 #30
0
        public void LoadWasm(string path, ContentsStore store = null)
        {
            var file = WasmFile.ReadBinary(path);

            LoadWasm(file, store);
        }