Просмотр исходного кода

Add memory instance support apis (#3786)

Now that WAMR supports multiple memory instances, this PR adds some APIs
to access them in a standard way.

This involves moving some existing utility functions out from the
`WASM_ENABLE_MULTI_MODULE` blocks they were nested in, but multi-memory
and multi-module seem independent as far as I can tell so I assume that's okay.

APIs added:
```C
wasm_runtime_lookup_memory
wasm_runtime_get_default_memory
wasm_runtime_get_memory
wasm_memory_get_cur_page_count
wasm_memory_get_max_page_count
wasm_memory_get_bytes_per_page
wasm_memory_get_shared
wasm_memory_get_base_address
wasm_memory_enlarge
```
Benbuck Nason 1 год назад
Родитель
Сommit
926f662231

+ 26 - 1
core/iwasm/aot/aot_runtime.c

@@ -1058,7 +1058,24 @@ fail1:
     return NULL;
 }
 
-static AOTMemoryInstance *
+AOTMemoryInstance *
+aot_lookup_memory(AOTModuleInstance *module_inst, char const *name)
+{
+#if WASM_ENABLE_MULTI_MEMORY != 0
+    uint32 i;
+    for (i = 0; i < module_inst->export_memory_count; i++)
+        if (!strcmp(module_inst->export_memories[i].name, name))
+            return module_inst->export_memories[i].memory;
+    return NULL;
+#else
+    (void)module_inst->export_memories;
+    if (!module_inst->memories)
+        return NULL;
+    return module_inst->memories[0];
+#endif
+}
+
+AOTMemoryInstance *
 aot_get_default_memory(AOTModuleInstance *module_inst)
 {
     if (module_inst->memories)
@@ -1067,6 +1084,14 @@ aot_get_default_memory(AOTModuleInstance *module_inst)
         return NULL;
 }
 
+AOTMemoryInstance *
+aot_get_memory_with_index(AOTModuleInstance *module_inst, uint32 index)
+{
+    if ((index >= module_inst->memory_count) || !module_inst->memories)
+        return NULL;
+    return module_inst->memories[index];
+}
+
 static bool
 memories_instantiate(AOTModuleInstance *module_inst, AOTModuleInstance *parent,
                      AOTModule *module, uint32 heap_size,

+ 9 - 0
core/iwasm/aot/aot_runtime.h

@@ -532,6 +532,15 @@ aot_deinstantiate(AOTModuleInstance *module_inst, bool is_sub_inst);
 AOTFunctionInstance *
 aot_lookup_function(const AOTModuleInstance *module_inst, const char *name);
 
+AOTMemoryInstance *
+aot_lookup_memory(AOTModuleInstance *module_inst, char const *name);
+
+AOTMemoryInstance *
+aot_get_default_memory(AOTModuleInstance *module_inst);
+
+AOTMemoryInstance *
+aot_get_memory_with_index(AOTModuleInstance *module_inst, uint32 index);
+
 /**
  * Get a function in the AOT module instance.
  *

+ 116 - 21
core/iwasm/common/wasm_memory.c

@@ -673,11 +673,9 @@ wasm_get_default_memory(WASMModuleInstance *module_inst)
 WASMMemoryInstance *
 wasm_get_memory_with_idx(WASMModuleInstance *module_inst, uint32 index)
 {
-    bh_assert(index < module_inst->memory_count);
-    if (module_inst->memories)
-        return module_inst->memories[index];
-    else
+    if ((index >= module_inst->memory_count) || !module_inst->memories)
         return NULL;
+    return module_inst->memories[index];
 }
 
 void
@@ -756,15 +754,10 @@ wasm_mmap_linear_memory(uint64_t map_size, uint64 commit_size)
     return wasm_mremap_linear_memory(NULL, 0, map_size, commit_size);
 }
 
-bool
-wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count,
-                             uint32 memidx)
+static bool
+wasm_enlarge_memory_internal(WASMModuleInstanceCommon *module,
+                             WASMMemoryInstance *memory, uint32 inc_page_count)
 {
-#if WASM_ENABLE_MULTI_MEMORY != 0
-    WASMMemoryInstance *memory = wasm_get_memory_with_idx(module, memidx);
-#else
-    WASMMemoryInstance *memory = wasm_get_default_memory(module);
-#endif
     uint8 *memory_data_old, *memory_data_new, *heap_data_old;
     uint32 num_bytes_per_page, heap_size;
     uint32 cur_page_count, max_page_count, total_page_count;
@@ -913,7 +906,7 @@ wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count,
     wasm_runtime_set_mem_bound_check_bytes(memory, total_size_new);
 
 return_func:
-    if (!ret && enlarge_memory_error_cb) {
+    if (!ret && module && enlarge_memory_error_cb) {
         WASMExecEnv *exec_env = NULL;
 
 #if WASM_ENABLE_INTERP != 0
@@ -926,8 +919,7 @@ return_func:
 #endif
 
         enlarge_memory_error_cb(inc_page_count, total_size_old, 0,
-                                failure_reason,
-                                (WASMModuleInstanceCommon *)module, exec_env,
+                                failure_reason, module, exec_env,
                                 enlarge_memory_error_user_data);
     }
 
@@ -971,15 +963,16 @@ wasm_enlarge_memory(WASMModuleInstance *module, uint32 inc_page_count)
 {
     bool ret = false;
 
+    if (module->memory_count > 0) {
 #if WASM_ENABLE_SHARED_MEMORY != 0
-    if (module->memory_count > 0)
         shared_memory_lock(module->memories[0]);
 #endif
-    ret = wasm_enlarge_memory_internal(module, inc_page_count, 0);
+        ret = wasm_enlarge_memory_internal((WASMModuleInstanceCommon *)module,
+                                           module->memories[0], inc_page_count);
 #if WASM_ENABLE_SHARED_MEMORY != 0
-    if (module->memory_count > 0)
         shared_memory_unlock(module->memories[0]);
 #endif
+    }
 
     return ret;
 }
@@ -990,15 +983,117 @@ wasm_enlarge_memory_with_idx(WASMModuleInstance *module, uint32 inc_page_count,
 {
     bool ret = false;
 
+    if (memidx < module->memory_count) {
 #if WASM_ENABLE_SHARED_MEMORY != 0
-    if (memidx < module->memory_count)
         shared_memory_lock(module->memories[memidx]);
 #endif
-    ret = wasm_enlarge_memory_internal(module, inc_page_count, memidx);
+        ret = wasm_enlarge_memory_internal((WASMModuleInstanceCommon *)module,
+                                           module->memories[memidx],
+                                           inc_page_count);
 #if WASM_ENABLE_SHARED_MEMORY != 0
-    if (memidx < module->memory_count)
         shared_memory_unlock(module->memories[memidx]);
 #endif
+    }
+
+    return ret;
+}
+
+WASMMemoryInstance *
+wasm_runtime_lookup_memory(WASMModuleInstanceCommon *module_inst,
+                           const char *name)
+{
+#if WASM_ENABLE_INTERP != 0
+    if (module_inst->module_type == Wasm_Module_Bytecode)
+        return wasm_lookup_memory((WASMModuleInstance *)module_inst, name);
+#endif
+
+#if WASM_ENABLE_AOT != 0
+    if (module_inst->module_type == Wasm_Module_AoT)
+        return aot_lookup_memory((WASMModuleInstance *)module_inst, name);
+#endif
+
+    return NULL;
+}
+
+WASMMemoryInstance *
+wasm_runtime_get_default_memory(WASMModuleInstanceCommon *module_inst)
+{
+#if WASM_ENABLE_INTERP != 0
+    if (module_inst->module_type == Wasm_Module_Bytecode)
+        return wasm_get_default_memory((WASMModuleInstance *)module_inst);
+#endif
+
+#if WASM_ENABLE_AOT != 0
+    if (module_inst->module_type == Wasm_Module_AoT)
+        return aot_get_default_memory((AOTModuleInstance *)module_inst);
+#endif
+
+    return NULL;
+}
+
+WASMMemoryInstance *
+wasm_runtime_get_memory(WASMModuleInstanceCommon *module_inst, uint32 index)
+{
+#if WASM_ENABLE_INTERP != 0
+    if (module_inst->module_type == Wasm_Module_Bytecode)
+        return wasm_get_memory_with_idx((WASMModuleInstance *)module_inst,
+                                        index);
+#endif
+
+#if WASM_ENABLE_AOT != 0
+    if (module_inst->module_type == Wasm_Module_AoT)
+        return aot_get_memory_with_index((AOTModuleInstance *)module_inst,
+                                         index);
+#endif
+
+    return NULL;
+}
+
+uint64
+wasm_memory_get_cur_page_count(WASMMemoryInstance *memory)
+{
+    return memory->cur_page_count;
+}
+
+uint64
+wasm_memory_get_max_page_count(WASMMemoryInstance *memory)
+{
+    return memory->max_page_count;
+}
+
+uint64
+wasm_memory_get_bytes_per_page(WASMMemoryInstance *memory)
+{
+    return memory->num_bytes_per_page;
+}
+
+bool
+wasm_memory_get_shared(WASMMemoryInstance *memory)
+{
+    return memory->is_shared_memory;
+}
+
+void *
+wasm_memory_get_base_address(WASMMemoryInstance *memory)
+{
+    return memory->memory_data;
+}
+
+bool
+wasm_memory_enlarge(WASMMemoryInstance *memory, uint64 inc_page_count)
+{
+    bool ret = false;
+
+    if (memory) {
+#if WASM_ENABLE_SHARED_MEMORY != 0
+        shared_memory_lock(memory);
+#endif
+        ret =
+            wasm_enlarge_memory_internal(NULL, memory, (uint32)inc_page_count);
+#if WASM_ENABLE_SHARED_MEMORY != 0
+        shared_memory_unlock(memory);
+#endif
+    }
 
     return ret;
 }

+ 98 - 0
core/iwasm/include/wasm_export.h

@@ -120,6 +120,10 @@ typedef struct WASMModuleInstanceCommon *wasm_module_inst_t;
 typedef void WASMFunctionInstanceCommon;
 typedef WASMFunctionInstanceCommon *wasm_function_inst_t;
 
+/* Memory instance */
+struct WASMMemoryInstance;
+typedef struct WASMMemoryInstance *wasm_memory_inst_t;
+
 /* WASM section */
 typedef struct wasm_section_t {
     struct wasm_section_t *next;
@@ -939,6 +943,100 @@ WASM_RUNTIME_API_EXTERN void
 wasm_runtime_set_module_inst(wasm_exec_env_t exec_env,
                              const wasm_module_inst_t module_inst);
 
+/**
+ * @brief Lookup a memory instance by name
+ *
+ * @param module_inst The module instance
+ * @param name The name of the memory instance
+ *
+ * @return The memory instance if found, NULL otherwise
+ */
+WASM_RUNTIME_API_EXTERN wasm_memory_inst_t
+wasm_runtime_lookup_memory(const wasm_module_inst_t module_inst,
+                           const char *name);
+
+/**
+ * @brief Get the default memory instance
+ *
+ * @param module_inst The module instance
+ *
+ * @return The memory instance if found, NULL otherwise
+ */
+WASM_RUNTIME_API_EXTERN wasm_memory_inst_t
+wasm_runtime_get_default_memory(const wasm_module_inst_t module_inst);
+
+/**
+ * @brief Get a memory instance by index
+ *
+ * @param module_inst The module instance
+ * @param index The index of the memory instance
+ *
+ * @return The memory instance if found, NULL otherwise
+ */
+WASM_RUNTIME_API_EXTERN wasm_memory_inst_t
+wasm_runtime_get_memory(const wasm_module_inst_t module_inst, uint32_t index);
+
+/**
+ * @brief Get the current number of pages for a memory instance
+ *
+ * @param memory_inst The memory instance
+ *
+ * @return The current number of pages
+ */
+WASM_RUNTIME_API_EXTERN uint64_t
+wasm_memory_get_cur_page_count(const wasm_memory_inst_t memory_inst);
+
+/**
+ * @brief Get the maximum number of pages for a memory instance
+ *
+ * @param memory_inst The memory instance
+ *
+ * @return The maximum number of pages
+ */
+WASM_RUNTIME_API_EXTERN uint64_t
+wasm_memory_get_max_page_count(const wasm_memory_inst_t memory_inst);
+
+/**
+ * @brief Get the number of bytes per page for a memory instance
+ *
+ * @param memory_inst The memory instance
+ *
+ * @return The number of bytes per page
+ */
+WASM_RUNTIME_API_EXTERN uint64_t
+wasm_memory_get_bytes_per_page(const wasm_memory_inst_t memory_inst);
+
+/**
+ * @brief Get the shared status for a memory instance
+ *
+ * @param memory_inst The memory instance
+ *
+ * @return True if shared, false otherwise
+ */
+WASM_RUNTIME_API_EXTERN bool
+wasm_memory_get_shared(const wasm_memory_inst_t memory_inst);
+
+/**
+ * @brief Get the base address for a memory instance
+ *
+ * @param memory_inst The memory instance
+ *
+ * @return The base address on success, false otherwise
+ */
+WASM_RUNTIME_API_EXTERN void *
+wasm_memory_get_base_address(const wasm_memory_inst_t memory_inst);
+
+/**
+ * @brief Enlarge a memory instance by a number of pages
+ *
+ * @param memory_inst The memory instance
+ * @param inc_page_count The number of pages to add
+ *
+ * @return True if successful, false otherwise
+ */
+WASM_RUNTIME_API_EXTERN bool
+wasm_memory_enlarge(wasm_memory_inst_t memory_inst, uint64_t inc_page_count);
+
 /**
  * Call the given WASM function of a WASM module instance with
  * arguments (bytecode and AoT).

+ 55 - 51
core/iwasm/interpreter/wasm_runtime.c

@@ -1323,42 +1323,6 @@ export_tags_instantiate(const WASMModule *module,
 }
 #endif /* end of WASM_ENABLE_TAGS != 0 */
 
-#if WASM_ENABLE_MULTI_MODULE != 0
-static void
-export_globals_deinstantiate(WASMExportGlobInstance *globals)
-{
-    if (globals)
-        wasm_runtime_free(globals);
-}
-
-static WASMExportGlobInstance *
-export_globals_instantiate(const WASMModule *module,
-                           WASMModuleInstance *module_inst,
-                           uint32 export_glob_count, char *error_buf,
-                           uint32 error_buf_size)
-{
-    WASMExportGlobInstance *export_globals, *export_global;
-    WASMExport *export = module->exports;
-    uint32 i;
-    uint64 total_size =
-        sizeof(WASMExportGlobInstance) * (uint64)export_glob_count;
-
-    if (!(export_global = export_globals =
-              runtime_malloc(total_size, error_buf, error_buf_size))) {
-        return NULL;
-    }
-
-    for (i = 0; i < module->export_count; i++, export ++)
-        if (export->kind == EXPORT_KIND_GLOBAL) {
-            export_global->name = export->name;
-            export_global->global = &module_inst->e->globals[export->index];
-            export_global++;
-        }
-
-    bh_assert((uint32)(export_global - export_globals) == export_glob_count);
-    return export_globals;
-}
-
 #if WASM_ENABLE_MULTI_MEMORY != 0
 static void
 export_memories_deinstantiate(WASMExportMemInstance *memories)
@@ -1396,6 +1360,42 @@ export_memories_instantiate(const WASMModule *module,
 }
 #endif /* end of if WASM_ENABLE_MULTI_MEMORY != 0 */
 
+#if WASM_ENABLE_MULTI_MODULE != 0
+static void
+export_globals_deinstantiate(WASMExportGlobInstance *globals)
+{
+    if (globals)
+        wasm_runtime_free(globals);
+}
+
+static WASMExportGlobInstance *
+export_globals_instantiate(const WASMModule *module,
+                           WASMModuleInstance *module_inst,
+                           uint32 export_glob_count, char *error_buf,
+                           uint32 error_buf_size)
+{
+    WASMExportGlobInstance *export_globals, *export_global;
+    WASMExport *export = module->exports;
+    uint32 i;
+    uint64 total_size =
+        sizeof(WASMExportGlobInstance) * (uint64)export_glob_count;
+
+    if (!(export_global = export_globals =
+              runtime_malloc(total_size, error_buf, error_buf_size))) {
+        return NULL;
+    }
+
+    for (i = 0; i < module->export_count; i++, export ++)
+        if (export->kind == EXPORT_KIND_GLOBAL) {
+            export_global->name = export->name;
+            export_global->global = &module_inst->e->globals[export->index];
+            export_global++;
+        }
+
+    bh_assert((uint32)(export_global - export_globals) == export_glob_count);
+    return export_globals;
+}
+
 #endif /* end of if WASM_ENABLE_MULTI_MODULE != 0 */
 
 static WASMFunctionInstance *
@@ -2388,11 +2388,13 @@ wasm_instantiate(WASMModule *module, WASMModuleInstance *parent,
 
     /* export */
     module_inst->export_func_count = get_export_count(module, EXPORT_KIND_FUNC);
+#if WASM_ENABLE_MULTI_MEMORY != 0
+    module_inst->export_memory_count =
+        get_export_count(module, EXPORT_KIND_MEMORY);
+#endif
 #if WASM_ENABLE_MULTI_MODULE != 0
     module_inst->export_table_count =
         get_export_count(module, EXPORT_KIND_TABLE);
-    module_inst->export_memory_count =
-        get_export_count(module, EXPORT_KIND_MEMORY);
 #if WASM_ENABLE_TAGS != 0
     module_inst->e->export_tag_count =
         get_export_count(module, EXPORT_KIND_TAG);
@@ -2432,7 +2434,7 @@ wasm_instantiate(WASMModule *module, WASMModuleInstance *parent,
                      module, module_inst, module_inst->export_global_count,
                      error_buf, error_buf_size)))
 #endif
-#if WASM_ENABLE_MULTI_MODULE != 0 && WASM_ENABLE_MULTI_MEMORY != 0
+#if WASM_ENABLE_MULTI_MEMORY != 0
         || (module_inst->export_memory_count > 0
             && !(module_inst->export_memories = export_memories_instantiate(
                      module, module_inst, module_inst->export_memory_count,
@@ -3240,7 +3242,7 @@ wasm_deinstantiate(WASMModuleInstance *module_inst, bool is_sub_inst)
     export_globals_deinstantiate(module_inst->export_globals);
 #endif
 
-#if WASM_ENABLE_MULTI_MODULE != 0 && WASM_ENABLE_MULTI_MEMORY != 0
+#if WASM_ENABLE_MULTI_MEMORY != 0
     export_memories_deinstantiate(module_inst->export_memories);
 #endif
 
@@ -3292,17 +3294,6 @@ wasm_lookup_function(const WASMModuleInstance *module_inst, const char *name)
     return NULL;
 }
 
-#if WASM_ENABLE_MULTI_MODULE != 0
-WASMGlobalInstance *
-wasm_lookup_global(const WASMModuleInstance *module_inst, const char *name)
-{
-    uint32 i;
-    for (i = 0; i < module_inst->export_global_count; i++)
-        if (!strcmp(module_inst->export_globals[i].name, name))
-            return module_inst->export_globals[i].global;
-    return NULL;
-}
-
 WASMMemoryInstance *
 wasm_lookup_memory(const WASMModuleInstance *module_inst, const char *name)
 {
@@ -3314,10 +3305,23 @@ wasm_lookup_memory(const WASMModuleInstance *module_inst, const char *name)
     return NULL;
 #else
     (void)module_inst->export_memories;
+    if (!module_inst->memories)
+        return NULL;
     return module_inst->memories[0];
 #endif
 }
 
+#if WASM_ENABLE_MULTI_MODULE != 0
+WASMGlobalInstance *
+wasm_lookup_global(const WASMModuleInstance *module_inst, const char *name)
+{
+    uint32 i;
+    for (i = 0; i < module_inst->export_global_count; i++)
+        if (!strcmp(module_inst->export_globals[i].name, name))
+            return module_inst->export_globals[i].global;
+    return NULL;
+}
+
 WASMTableInstance *
 wasm_lookup_table(const WASMModuleInstance *module_inst, const char *name)
 {

+ 3 - 3
core/iwasm/interpreter/wasm_runtime.h

@@ -539,13 +539,13 @@ wasm_set_running_mode(WASMModuleInstance *module_inst,
 WASMFunctionInstance *
 wasm_lookup_function(const WASMModuleInstance *module_inst, const char *name);
 
+WASMMemoryInstance *
+wasm_lookup_memory(const WASMModuleInstance *module_inst, const char *name);
+
 #if WASM_ENABLE_MULTI_MODULE != 0
 WASMGlobalInstance *
 wasm_lookup_global(const WASMModuleInstance *module_inst, const char *name);
 
-WASMMemoryInstance *
-wasm_lookup_memory(const WASMModuleInstance *module_inst, const char *name);
-
 WASMTableInstance *
 wasm_lookup_table(const WASMModuleInstance *module_inst, const char *name);