WebAssembly Micro Runtime first version
This commit is contained in:
38
core/iwasm/runtime/include/ext-lib-export.h
Normal file
38
core/iwasm/runtime/include/ext-lib-export.h
Normal file
@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _EXT_LIB_EXPORT_H_
|
||||
#define _EXT_LIB_EXPORT_H_
|
||||
|
||||
#include "lib-export.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
int
|
||||
get_ext_lib_export_apis(NativeSymbol **p_ext_lib_apis)
|
||||
{
|
||||
*p_ext_lib_apis = extended_native_symbol_defs;
|
||||
return sizeof(extended_native_symbol_defs) / sizeof(NativeSymbol);
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _EXT_LIB_EXPORT_H_ */
|
||||
|
||||
57
core/iwasm/runtime/include/lib-export.h
Normal file
57
core/iwasm/runtime/include/lib-export.h
Normal file
@ -0,0 +1,57 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _LIB_EXPORT_H_
|
||||
#define _LIB_EXPORT_H_
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct NativeSymbol {
|
||||
const char *symbol;
|
||||
void *func_ptr;
|
||||
} NativeSymbol;
|
||||
|
||||
#define EXPORT_WASM_API(symbol) {#symbol, symbol}
|
||||
#define EXPORT_WASM_API2(symbol) {#symbol, symbol##_wrapper}
|
||||
|
||||
/**
|
||||
* Get the exported APIs of base lib
|
||||
*
|
||||
* @param p_base_lib_apis return the exported API array of base lib
|
||||
*
|
||||
* @return the number of the exported API
|
||||
*/
|
||||
int
|
||||
get_base_lib_export_apis(NativeSymbol **p_base_lib_apis);
|
||||
|
||||
/**
|
||||
* Get the exported APIs of extend lib
|
||||
*
|
||||
* @param p_base_lib_apis return the exported API array of extend lib
|
||||
*
|
||||
* @return the number of the exported API
|
||||
*/
|
||||
int
|
||||
get_extend_lib_export_apis(NativeSymbol **p_base_lib_apis);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
421
core/iwasm/runtime/include/wasm-export.h
Normal file
421
core/iwasm/runtime/include/wasm-export.h
Normal file
@ -0,0 +1,421 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_EXPORT_H
|
||||
#define _WASM_EXPORT_H
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* Uninstantiated WASM module loaded from WASM binary file */
|
||||
struct WASMModule;
|
||||
typedef struct WASMModule *wasm_module_t;
|
||||
|
||||
/* Instantiated WASM module */
|
||||
struct WASMModuleInstance;
|
||||
typedef struct WASMModuleInstance *wasm_module_inst_t;
|
||||
|
||||
/* Function instance */
|
||||
struct WASMFunctionInstance;
|
||||
typedef struct WASMFunctionInstance *wasm_function_inst_t;
|
||||
|
||||
/* WASM section */
|
||||
typedef struct wasm_section {
|
||||
struct wasm_section *next;
|
||||
/* section type */
|
||||
int section_type;
|
||||
/* section body, not include type and size */
|
||||
uint8_t *section_body;
|
||||
/* section body size */
|
||||
uint32_t section_body_size;
|
||||
} wasm_section_t, *wasm_section_list_t;
|
||||
|
||||
/* Execution environment, e.g. stack info */
|
||||
typedef struct WASMExecEnv {
|
||||
uint8_t *stack;
|
||||
uint32_t stack_size;
|
||||
} *wasm_exec_env_t;
|
||||
|
||||
/* Package Type */
|
||||
typedef enum {
|
||||
Wasm_Module_Bytecode = 0,
|
||||
Wasm_Module_AoT,
|
||||
Package_Type_Unknown = 0xFFFF
|
||||
} package_type_t;
|
||||
|
||||
/**
|
||||
* Initialize the WASM runtime environment.
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_init();
|
||||
|
||||
/**
|
||||
* Destroy the WASM runtime environment.
|
||||
*/
|
||||
void
|
||||
wasm_runtime_destroy();
|
||||
|
||||
/**
|
||||
* Get the package type of a buffer.
|
||||
*
|
||||
* @param buf the package buffer
|
||||
* @param size the package buffer size
|
||||
*
|
||||
* @return the package type, return Package_Type_Unknown if the type is unknown
|
||||
*/
|
||||
package_type_t
|
||||
get_package_type(const uint8_t *buf, uint32_t size);
|
||||
|
||||
/**
|
||||
* Load a WASM module from a specified byte buffer.
|
||||
*
|
||||
* @param buf the byte buffer which contains the WASM binary data
|
||||
* @param size the size of the buffer
|
||||
* @param error_buf output of the exception info
|
||||
* @param error_buf_size the size of the exception string
|
||||
*
|
||||
* @return return WASM module loaded, NULL if failed
|
||||
*/
|
||||
wasm_module_t
|
||||
wasm_runtime_load(const uint8_t *buf, uint32_t size,
|
||||
char *error_buf, uint32_t error_buf_size);
|
||||
|
||||
/**
|
||||
* Load a WASM module from a specified WASM section list.
|
||||
*
|
||||
* @param section_list the section list which contains each section data
|
||||
* @param error_buf output of the exception info
|
||||
* @param error_buf_size the size of the exception string
|
||||
*
|
||||
* @return return WASM module loaded, NULL if failed
|
||||
*/
|
||||
wasm_module_t
|
||||
wasm_runtime_load_from_sections(wasm_section_list_t section_list,
|
||||
char *error_buf, uint32_t error_buf_size);
|
||||
|
||||
/**
|
||||
* Unload a WASM module.
|
||||
*
|
||||
* @param module the module to be unloaded
|
||||
*/
|
||||
void
|
||||
wasm_runtime_unload(wasm_module_t module);
|
||||
|
||||
/**
|
||||
* Instantiate a WASM module.
|
||||
*
|
||||
* @param module the WASM module to instantiate
|
||||
* @param stack_size the default stack size of the module instance, a stack
|
||||
* will be created when function wasm_runtime_call_wasm() is called
|
||||
* to run WASM function and the exec_env argument passed to
|
||||
* wasm_runtime_call_wasm() is NULL. That means this parameter is
|
||||
* ignored if exec_env is not NULL.
|
||||
* @param heap_size the default heap size of the module instance, a heap will
|
||||
* be created besides the app memory space. Both wasm app and native
|
||||
* function can allocate memory from the heap. If heap_size is 0, the
|
||||
* default heap size will be used.
|
||||
* @param error_buf buffer to output the error info if failed
|
||||
* @param error_buf_size the size of the error buffer
|
||||
*
|
||||
* @return return the instantiated WASM module instance, NULL if failed
|
||||
*/
|
||||
wasm_module_inst_t
|
||||
wasm_runtime_instantiate(const wasm_module_t module,
|
||||
uint32_t stack_size, uint32_t heap_size,
|
||||
char *error_buf, uint32_t error_buf_size);
|
||||
|
||||
/**
|
||||
* Deinstantiate a WASM module instance, destroy the resources.
|
||||
*
|
||||
* @param module_inst the WASM module instance to destroy
|
||||
*/
|
||||
void
|
||||
wasm_runtime_deinstantiate(wasm_module_inst_t module_inst);
|
||||
|
||||
/**
|
||||
* Load WASM module instance from AOT file.
|
||||
*
|
||||
* @param aot_file the AOT file of a WASM module
|
||||
* @param aot_file_size the AOT file size
|
||||
* @param heap_size the default heap size of the module instance, a heap will
|
||||
* be created besides the app memory space. Both wasm app and native
|
||||
* function can allocate memory from the heap. If heap_size is 0, the
|
||||
* default heap size will be used.
|
||||
* @param error_buf buffer to output the error info if failed
|
||||
* @param error_buf_size the size of the error buffer
|
||||
*
|
||||
* @return the instantiated WASM module instance, NULL if failed
|
||||
*/
|
||||
wasm_module_inst_t
|
||||
wasm_runtime_load_aot(uint8_t *aot_file, uint32_t aot_file_size,
|
||||
uint32_t heap_size,
|
||||
char *error_buf, uint32_t error_buf_size);
|
||||
|
||||
/**
|
||||
* Lookup an exported function in the WASM module instance.
|
||||
*
|
||||
* @param module_inst the module instance
|
||||
* @param name the name of the function
|
||||
* @param signature the signature of the function, use "i32"/"i64"/"f32"/"f64"
|
||||
* to represent the type of i32/i64/f32/f64, e.g. "(i32i64)" "(i32)f32"
|
||||
*
|
||||
* @return the function instance found, if the module instance is loaded from
|
||||
* the AOT file, the return value is the function pointer
|
||||
*/
|
||||
wasm_function_inst_t
|
||||
wasm_runtime_lookup_function(const wasm_module_inst_t module_inst,
|
||||
const char *name, const char *signature);
|
||||
|
||||
/**
|
||||
* Create execution environment.
|
||||
*
|
||||
* @param stack_size the stack size to execute a WASM function
|
||||
*
|
||||
* @return the execution environment
|
||||
*/
|
||||
wasm_exec_env_t
|
||||
wasm_runtime_create_exec_env(uint32_t stack_size);
|
||||
|
||||
/**
|
||||
* Destroy the execution environment.
|
||||
*
|
||||
* @param env the execution environment to destroy
|
||||
*/
|
||||
void
|
||||
wasm_runtime_destory_exec_env(wasm_exec_env_t env);
|
||||
|
||||
/**
|
||||
* Call the given WASM function of a WASM module instance with
|
||||
* arguments (bytecode and AoT).
|
||||
*
|
||||
* @param module_inst the WASM module instance which the function belongs to
|
||||
* @param exec_env the execution environment to call the function. If the module
|
||||
* instance is created by AoT mode, it is ignored and just set it to NULL.
|
||||
* If the module instance is created by bytecode mode and it is NULL,
|
||||
* a temporary env object will be created
|
||||
* @param function the function to be called
|
||||
* @param argc the number of arguments
|
||||
* @param argv the arguments. If the function method has return value,
|
||||
* the first (or first two in case 64-bit return value) element of
|
||||
* argv stores the return value of the called WASM function after this
|
||||
* function returns.
|
||||
*
|
||||
* @return true if success, false otherwise and exception will be thrown,
|
||||
* the caller can call wasm_runtime_get_exception to get exception info.
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_call_wasm(wasm_module_inst_t module_inst,
|
||||
wasm_exec_env_t exec_env,
|
||||
wasm_function_inst_t function,
|
||||
uint32_t argc, uint32_t argv[]);
|
||||
|
||||
/**
|
||||
* Get exception info of the WASM module instance.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
*
|
||||
* @return the exception string
|
||||
*/
|
||||
const char*
|
||||
wasm_runtime_get_exception(wasm_module_inst_t module_inst);
|
||||
|
||||
/**
|
||||
* Clear exception info of the WASM module instance.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
*/
|
||||
void
|
||||
wasm_runtime_clear_exception(wasm_module_inst_t module_inst);
|
||||
|
||||
/**
|
||||
* Attach the current native thread to a WASM module instance.
|
||||
* A native thread cannot be attached simultaneously to two WASM module
|
||||
* instances. The WASM module instance will be attached to the native
|
||||
* thread which it is instantiated in by default.
|
||||
*
|
||||
* @param module_inst the WASM module instance to attach
|
||||
* @param thread_data the thread data that current native thread requires
|
||||
* the WASM module instance to store
|
||||
*
|
||||
* @return true if SUCCESS, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_attach_current_thread(wasm_module_inst_t module_inst,
|
||||
void *thread_data);
|
||||
|
||||
/**
|
||||
* Detach the current native thread from a WASM module instance.
|
||||
*
|
||||
* @param module_inst the WASM module instance to detach
|
||||
*/
|
||||
void
|
||||
wasm_runtime_detach_current_thread(wasm_module_inst_t module_inst);
|
||||
|
||||
/**
|
||||
* Get the thread data that the current native thread requires the WASM
|
||||
* module instance to store when attaching.
|
||||
*
|
||||
* @return the thread data stored when attaching
|
||||
*/
|
||||
void*
|
||||
wasm_runtime_get_current_thread_data();
|
||||
|
||||
/**
|
||||
* Get current WASM module instance of the current native thread
|
||||
*
|
||||
* @return current WASM module instance of the current native thread, NULL
|
||||
* if not found
|
||||
*/
|
||||
wasm_module_inst_t
|
||||
wasm_runtime_get_current_module_inst();
|
||||
|
||||
/**
|
||||
* Allocate memory from the heap of WASM module instance
|
||||
*
|
||||
* @param module_inst the WASM module instance which contains heap
|
||||
* @param size the size bytes to allocate
|
||||
*
|
||||
* @return the allocated memory address, which is a relative offset to the
|
||||
* base address of the module instance's memory space, the value range
|
||||
* is (-heap_size, 0). Note that it is not an absolute address.
|
||||
* Return non-zero if success, zero if failed.
|
||||
*/
|
||||
int32_t
|
||||
wasm_runtime_module_malloc(wasm_module_inst_t module_inst, uint32_t size);
|
||||
|
||||
/**
|
||||
* Free memory to the heap of WASM module instance
|
||||
*
|
||||
* @param module_inst the WASM module instance which contains heap
|
||||
* @param ptr the pointer to free
|
||||
*/
|
||||
void
|
||||
wasm_runtime_module_free(wasm_module_inst_t module_inst, int32_t ptr);
|
||||
|
||||
/**
|
||||
* Allocate memory from the heap of WASM module instance and initialize
|
||||
* the memory with src
|
||||
*
|
||||
* @param module_inst the WASM module instance which contains heap
|
||||
* @param src the source data to copy
|
||||
* @param size the size of the source data
|
||||
*
|
||||
* @return the allocated memory address, which is a relative offset to the
|
||||
* base address of the module instance's memory space, the value range
|
||||
* is (-heap_size, 0). Note that it is not an absolute address.
|
||||
* Return non-zero if success, zero if failed.
|
||||
*/
|
||||
int32_t
|
||||
wasm_runtime_module_dup_data(wasm_module_inst_t module_inst,
|
||||
const char *src, uint32_t size);
|
||||
|
||||
/**
|
||||
* Validate the app address, check whether it belongs to WASM module
|
||||
* instance's address space, or in its heap space or memory space.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param app_offset the app address to validate, which is a relative address
|
||||
* @param size the size bytes of the app address
|
||||
*
|
||||
* @return true if success, false otherwise. If failed, an exception will
|
||||
* be thrown.
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_validate_app_addr(wasm_module_inst_t module_inst,
|
||||
int32_t app_offset, uint32_t size);
|
||||
|
||||
/**
|
||||
* Validate the native address, check whether it belongs to WASM module
|
||||
* instance's address space, or in its heap space or memory space.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param native_ptr the native address to validate, which is an absolute
|
||||
* address
|
||||
* @param size the size bytes of the app address
|
||||
*
|
||||
* @return true if success, false otherwise. If failed, an exception will
|
||||
* be thrown.
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_validate_native_addr(wasm_module_inst_t module_inst,
|
||||
void *native_ptr, uint32_t size);
|
||||
|
||||
/**
|
||||
* Convert app address(relative address) to native address(absolute address)
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param app_offset the app adress
|
||||
*
|
||||
* @return the native address converted
|
||||
*/
|
||||
void *
|
||||
wasm_runtime_addr_app_to_native(wasm_module_inst_t module_inst,
|
||||
int32_t app_offset);
|
||||
|
||||
/**
|
||||
* Convert native address(absolute address) to app address(relative address)
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param native_ptr the native address
|
||||
*
|
||||
* @return the app address converted
|
||||
*/
|
||||
int32_t
|
||||
wasm_runtime_addr_native_to_app(wasm_module_inst_t module_inst,
|
||||
void *native_ptr);
|
||||
|
||||
/**
|
||||
* Find the unique main function from a WASM module instance
|
||||
* and execute that function.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param argc the number of arguments
|
||||
* @param argv the arguments array
|
||||
*
|
||||
* @return true if the main function is called, false otherwise.
|
||||
*/
|
||||
bool
|
||||
wasm_application_execute_main(wasm_module_inst_t module_inst,
|
||||
int argc, char *argv[]);
|
||||
|
||||
/**
|
||||
* Find the specified function in argv[0] from WASM module of current instance
|
||||
* and execute that function.
|
||||
*
|
||||
* @param module_inst the WASM module instance
|
||||
* @param name the name of the function to execute
|
||||
* @param argc the number of arguments
|
||||
* @param argv the arguments array
|
||||
*
|
||||
* @return true if the specified function is called, false otherwise.
|
||||
*/
|
||||
bool
|
||||
wasm_application_execute_func(wasm_module_inst_t module_inst,
|
||||
const char *name, int argc, char *argv[]);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_EXPORT_H */
|
||||
144
core/iwasm/runtime/include/wasm_hashmap.h
Normal file
144
core/iwasm/runtime/include/wasm_hashmap.h
Normal file
@ -0,0 +1,144 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef WASM_HASHMAP_H
|
||||
#define WASM_HASHMAP_H
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* Maximum initial size of hash map */
|
||||
#define HASH_MAP_MAX_SIZE 65536
|
||||
|
||||
struct HashMap;
|
||||
typedef struct HashMap HashMap;
|
||||
|
||||
/* Hash function: to get the hash value of key. */
|
||||
typedef uint32 (*HashFunc)(const void *key);
|
||||
|
||||
/* Key equal function: to check whether two keys are equal. */
|
||||
typedef bool (*KeyEqualFunc)(void *key1, void *key2);
|
||||
|
||||
/* Key destroy function: to destroy the key, auto called
|
||||
when an hash element is removed. */
|
||||
typedef void (*KeyDestroyFunc)(void *key);
|
||||
|
||||
/* Value destroy function: to destroy the value, auto called
|
||||
when an hash element is removed. */
|
||||
typedef void (*ValueDestroyFunc)(void *key);
|
||||
|
||||
/**
|
||||
* Create a hash map.
|
||||
*
|
||||
* @param size: the initial size of the hash map
|
||||
* @param use_lock whether to lock the hash map when operating on it
|
||||
* @param hash_func hash function of the key, must be specified
|
||||
* @param key_equal_func key equal function, check whether two keys
|
||||
* are equal, must be specified
|
||||
* @param key_destroy_func key destroy function, called when an hash element
|
||||
* is removed if it is not NULL
|
||||
* @param value_destroy_func value destroy function, called when an hash
|
||||
* element is removed if it is not NULL
|
||||
*
|
||||
* @return the hash map created, NULL if failed
|
||||
*/
|
||||
HashMap*
|
||||
wasm_hash_map_create(uint32 size, bool use_lock,
|
||||
HashFunc hash_func,
|
||||
KeyEqualFunc key_equal_func,
|
||||
KeyDestroyFunc key_destroy_func,
|
||||
ValueDestroyFunc value_destroy_func);
|
||||
|
||||
/**
|
||||
* Insert an element to the hash map
|
||||
*
|
||||
* @param map the hash map to insert element
|
||||
* @key the key of the element
|
||||
* @value the value of the element
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
* Note: fail if key is NULL or duplicated key exists in the hash map,
|
||||
*/
|
||||
bool
|
||||
wasm_hash_map_insert(HashMap *map, void *key, void *value);
|
||||
|
||||
/**
|
||||
* Find an element in the hash map
|
||||
*
|
||||
* @param map the hash map to find element
|
||||
* @key the key of the element
|
||||
*
|
||||
* @return the value of the found element if success, NULL otherwise
|
||||
*/
|
||||
void*
|
||||
wasm_hash_map_find(HashMap *map, void *key);
|
||||
|
||||
/**
|
||||
* Update an element in the hash map with new value
|
||||
*
|
||||
* @param map the hash map to update element
|
||||
* @key the key of the element
|
||||
* @value the new value of the element
|
||||
* @p_old_value if not NULL, copies the old value to it
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
* Note: the old value won't be destroyed by value destory function,
|
||||
* it will be copied to p_old_value for user to process.
|
||||
*/
|
||||
bool
|
||||
wasm_hash_map_update(HashMap *map, void *key, void *value,
|
||||
void **p_old_value);
|
||||
|
||||
/**
|
||||
* Remove an element from the hash map
|
||||
*
|
||||
* @param map the hash map to remove element
|
||||
* @key the key of the element
|
||||
* @p_old_key if not NULL, copies the old key to it
|
||||
* @p_old_value if not NULL, copies the old value to it
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
* Note: the old key and old value won't be destroyed by key destroy
|
||||
* function and value destroy function, they will be copied to
|
||||
* p_old_key and p_old_value for user to process.
|
||||
*/
|
||||
bool
|
||||
wasm_hash_map_remove(HashMap *map, void *key,
|
||||
void **p_old_key, void **p_old_value);
|
||||
|
||||
/**
|
||||
* Destroy the hashmap
|
||||
*
|
||||
* @param map the hash map to destroy
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
* Note: the key destroy function and value destroy function will be
|
||||
* called to destroy each element's key and value if they are
|
||||
* not NULL.
|
||||
*/
|
||||
bool
|
||||
wasm_hash_map_destroy(HashMap *map);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* endof WASM_HASHMAP_H */
|
||||
|
||||
94
core/iwasm/runtime/include/wasm_log.h
Normal file
94
core/iwasm/runtime/include/wasm_log.h
Normal file
@ -0,0 +1,94 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief This log system supports wrapping multiple outputs into one
|
||||
* log message. This is useful for outputting variable-length logs
|
||||
* without additional memory overhead (the buffer for concatenating
|
||||
* the message), e.g. exception stack trace, which cannot be printed
|
||||
* by a single log calling without the help of an additional buffer.
|
||||
* Avoiding additional memory buffer is useful for resource-constraint
|
||||
* systems. It can minimize the impact of log system on applications
|
||||
* and logs can be printed even when no enough memory is available.
|
||||
* Functions with prefix "_" are private functions. Only macros that
|
||||
* are not start with "_" are exposed and can be used.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_LOG_H
|
||||
#define _WASM_LOG_H
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
* The following functions are the primitive operations of this log system.
|
||||
* A normal usage of the log system is to call wasm_log_begin and then call
|
||||
* wasm_log_printf or wasm_log_vprintf one or multiple times and then call
|
||||
* wasm_log_end to wrap (mark) the previous outputs into one log message.
|
||||
* The wasm_log and macros LOG_ERROR etc. can be used to output log messages
|
||||
* by one log calling.
|
||||
*/
|
||||
int _wasm_log_init (void);
|
||||
void _wasm_log_set_verbose_level (int level);
|
||||
bool _wasm_log_begin (int level);
|
||||
void _wasm_log_printf (const char *fmt, ...);
|
||||
void _wasm_log_vprintf (const char *fmt, va_list ap);
|
||||
void _wasm_log_end (void);
|
||||
void _wasm_log (int level, const char *file, int line,
|
||||
const char *fmt, ...);
|
||||
|
||||
#if WASM_ENABLE_LOG != 0
|
||||
# define wasm_log_init() _wasm_log_init ()
|
||||
# define wasm_log_set_verbose_level(l) _wasm_log_set_verbose_level (l)
|
||||
# define wasm_log_begin(l) _wasm_log_begin (l)
|
||||
# define wasm_log_printf(...) _wasm_log_printf (__VA_ARGS__)
|
||||
# define wasm_log_vprintf(...) _wasm_log_vprintf (__VA_ARGS__)
|
||||
# define wasm_log_end() _wasm_log_end ()
|
||||
# define wasm_log(...) _wasm_log (__VA_ARGS__)
|
||||
#else /* WASM_ENABLE_LOG != 0 */
|
||||
# define wasm_log_init() 0
|
||||
# define wasm_log_set_verbose_level(l) (void)0
|
||||
# define wasm_log_begin() false
|
||||
# define wasm_log_printf(...) (void)0
|
||||
# define wasm_log_vprintf(...) (void)0
|
||||
# define wasm_log_end() (void)0
|
||||
# define wasm_log(...) (void)0
|
||||
#endif /* WASM_ENABLE_LOG != 0 */
|
||||
|
||||
#define LOG_ERROR(...) wasm_log (0, NULL, 0, __VA_ARGS__)
|
||||
#define LOG_WARNING(...) wasm_log (1, NULL, 0, __VA_ARGS__)
|
||||
#define LOG_VERBOSE(...) wasm_log (2, NULL, 0, __VA_ARGS__)
|
||||
|
||||
#if defined(WASM_DEBUG)
|
||||
# define LOG_DEBUG(...) _wasm_log (1, __FILE__, __LINE__, __VA_ARGS__)
|
||||
#else /* defined(WASM_DEBUG) */
|
||||
# define LOG_DEBUG(...) (void)0
|
||||
#endif /* defined(WASM_DEBUG) */
|
||||
|
||||
#define LOG_PROFILE_HEAP_GC(heap, size) \
|
||||
LOG_VERBOSE("PROF.HEAP.GC: HEAP=%08X SIZE=%d", heap, size)
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#endif /* _WASM_LOG_H */
|
||||
137
core/iwasm/runtime/include/wasm_vector.h
Normal file
137
core/iwasm/runtime/include/wasm_vector.h
Normal file
@ -0,0 +1,137 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_VECTOR_H
|
||||
#define _WASM_VECTOR_H
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define DEFAULT_VECTOR_INIT_SIZE 8
|
||||
|
||||
typedef struct Vector {
|
||||
/* size of each element */
|
||||
uint32 size_elem;
|
||||
/* max element number */
|
||||
uint32 max_elements;
|
||||
/* current element num */
|
||||
uint32 num_elements;
|
||||
/* vector data allocated */
|
||||
uint8 *data;
|
||||
} Vector;
|
||||
|
||||
/**
|
||||
* Initialize vector
|
||||
*
|
||||
* @param vector the vector to init
|
||||
* @param init_length the initial length of the vector
|
||||
* @param size_elem size of each element
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_init(Vector *vector, uint32 init_length, uint32 size_elem);
|
||||
|
||||
/**
|
||||
* Set element of vector
|
||||
*
|
||||
* @param vector the vector to set
|
||||
* @param index the index of the element to set
|
||||
* @param elem_buf the element buffer which stores the element data
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_set(Vector *vector, uint32 index, const void *elem_buf);
|
||||
|
||||
/**
|
||||
* Get element of vector
|
||||
*
|
||||
* @param vector the vector to get
|
||||
* @param index the index of the element to get
|
||||
* @param elem_buf the element buffer to store the element data,
|
||||
* whose length must be no less than element size
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_get(const Vector *vector, uint32 index, void *elem_buf);
|
||||
|
||||
/**
|
||||
* Insert element of vector
|
||||
*
|
||||
* @param vector the vector to insert
|
||||
* @param index the index of the element to insert
|
||||
* @param elem_buf the element buffer which stores the element data
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_insert(Vector *vector, uint32 index, const void *elem_buf);
|
||||
|
||||
/**
|
||||
* Append element to the end of vector
|
||||
*
|
||||
* @param vector the vector to append
|
||||
* @param elem_buf the element buffer which stores the element data
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_append(Vector *vector, const void *elem_buf);
|
||||
|
||||
/**
|
||||
* Remove element from vector
|
||||
*
|
||||
* @param vector the vector to remove element
|
||||
* @param index the index of the element to remove
|
||||
* @param old_elem_buf if not NULL, copies the element data to the buffer
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_remove(Vector *vector, uint32 index, void *old_elem_buf);
|
||||
|
||||
/**
|
||||
* Return the size of the vector
|
||||
*
|
||||
* @param vector the vector to get size
|
||||
*
|
||||
* @return return the size of the vector
|
||||
*/
|
||||
uint32
|
||||
wasm_vector_size(const Vector *vector);
|
||||
|
||||
/**
|
||||
* Destroy the vector
|
||||
*
|
||||
* @param vector the vector to destroy
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_vector_destroy(Vector *vector);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* endof _WASM_VECTOR_H */
|
||||
|
||||
34
core/iwasm/runtime/platform/include/wasm_assert.h
Normal file
34
core/iwasm/runtime/platform/include/wasm_assert.h
Normal file
@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_ASSERT_H
|
||||
#define _WASM_ASSERT_H
|
||||
|
||||
#include "bh_assert.h"
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define wasm_assert bh_assert
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_ASSERT_H */
|
||||
|
||||
23
core/iwasm/runtime/platform/include/wasm_config.h
Normal file
23
core/iwasm/runtime/platform/include/wasm_config.h
Normal file
@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_CONFIG_H
|
||||
#define _WASM_CONFIG_H
|
||||
|
||||
#include "config.h"
|
||||
|
||||
#endif /* end of _WASM_CONFIG_H */
|
||||
|
||||
34
core/iwasm/runtime/platform/include/wasm_memory.h
Normal file
34
core/iwasm/runtime/platform/include/wasm_memory.h
Normal file
@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_MEMORY_H
|
||||
#define _WASM_MEMORY_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include "bh_memory.h"
|
||||
|
||||
#define wasm_malloc bh_malloc
|
||||
#define wasm_free bh_free
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_MEMORY_H */
|
||||
|
||||
24
core/iwasm/runtime/platform/include/wasm_platform_log.h
Normal file
24
core/iwasm/runtime/platform/include/wasm_platform_log.h
Normal file
@ -0,0 +1,24 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_PLATFORM_LOG
|
||||
#define _WASM_PLATFORM_LOG
|
||||
|
||||
#define wasm_printf printf
|
||||
|
||||
#define wasm_vprintf vprintf
|
||||
|
||||
#endif /* _WASM_PLATFORM_LOG */
|
||||
63
core/iwasm/runtime/platform/include/wasm_thread.h
Normal file
63
core/iwasm/runtime/platform/include/wasm_thread.h
Normal file
@ -0,0 +1,63 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file wasm_thread.h
|
||||
* @brief This file contains Beihai platform abstract layer interface for
|
||||
* thread relative function.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_THREAD_H
|
||||
#define _WASM_THREAD_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include "bh_thread.h"
|
||||
|
||||
|
||||
#define ws_thread_sys_init vm_thread_sys_init
|
||||
|
||||
#define ws_thread_sys_destroy vm_thread_sys_destroy
|
||||
|
||||
#define ws_self_thread vm_self_thread
|
||||
|
||||
#define ws_tls_put(ptr) vm_tls_put(0, ptr)
|
||||
|
||||
#define ws_tls_get() vm_tls_get(0)
|
||||
|
||||
static inline int
|
||||
ws_mutex_init(korp_mutex *mutex, bool is_recursive)
|
||||
{
|
||||
if (is_recursive)
|
||||
return vm_recursive_mutex_init(mutex);
|
||||
else
|
||||
return vm_mutex_init(mutex);
|
||||
}
|
||||
|
||||
#define ws_mutex_destroy vm_mutex_destroy
|
||||
|
||||
#define ws_mutex_lock vm_mutex_lock
|
||||
|
||||
#define ws_mutex_unlock vm_mutex_unlock
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_THREAD_H */
|
||||
|
||||
38
core/iwasm/runtime/platform/include/wasm_types.h
Normal file
38
core/iwasm/runtime/platform/include/wasm_types.h
Normal file
@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_TYPES_H
|
||||
#define _WASM_TYPES_H
|
||||
|
||||
#include "wasm_config.h"
|
||||
|
||||
typedef unsigned char uint8;
|
||||
typedef char int8;
|
||||
typedef unsigned short uint16;
|
||||
typedef short int16;
|
||||
typedef unsigned int uint32;
|
||||
typedef int int32;
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
#ifndef __cplusplus
|
||||
#define true 1
|
||||
#define false 0
|
||||
#define inline __inline
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_TYPES_H */
|
||||
|
||||
25
core/iwasm/runtime/platform/linux/platform.cmake
Normal file
25
core/iwasm/runtime/platform/linux/platform.cmake
Normal file
@ -0,0 +1,25 @@
|
||||
# Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
add_definitions (-D__POSIX__ -D_XOPEN_SOURCE=600 -D_POSIX_C_SOURCE=199309L)
|
||||
|
||||
set (PLATFORM_LIB_DIR ${CMAKE_CURRENT_LIST_DIR})
|
||||
|
||||
include_directories(${PLATFORM_LIB_DIR})
|
||||
include_directories(${PLATFORM_LIB_DIR}/../include)
|
||||
|
||||
file (GLOB_RECURSE source_all ${PLATFORM_LIB_DIR}/*.c)
|
||||
|
||||
set (WASM_PLATFORM_LIB_SOURCE ${source_all})
|
||||
|
||||
333
core/iwasm/runtime/platform/linux/wasm-native.c
Normal file
333
core/iwasm/runtime/platform/linux/wasm-native.c
Normal file
@ -0,0 +1,333 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _GNU_SOURCE
|
||||
#define _GNU_SOURCE /* for O_DIRECT */
|
||||
#endif
|
||||
|
||||
#include "wasm-native.h"
|
||||
#include "wasm-runtime.h"
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_memory.h"
|
||||
#include "wasm_platform_log.h"
|
||||
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/uio.h>
|
||||
#include <sys/syscall.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <unistd.h>
|
||||
#include <pwd.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
|
||||
|
||||
#define get_module_inst() \
|
||||
wasm_runtime_get_current_module_inst()
|
||||
|
||||
#define validate_app_addr(offset, size) \
|
||||
wasm_runtime_validate_app_addr(module_inst, offset, size)
|
||||
|
||||
#define addr_app_to_native(offset) \
|
||||
wasm_runtime_addr_app_to_native(module_inst, offset)
|
||||
|
||||
#define addr_native_to_app(ptr) \
|
||||
wasm_runtime_addr_native_to_app(module_inst, ptr)
|
||||
|
||||
#define module_malloc(size) \
|
||||
wasm_runtime_module_malloc(module_inst, size)
|
||||
|
||||
#define module_free(offset) \
|
||||
wasm_runtime_module_free(module_inst, offset)
|
||||
|
||||
|
||||
static int32
|
||||
__syscall0_wrapper(int32 arg0)
|
||||
{
|
||||
switch (arg0) {
|
||||
case 199: /* getuid */
|
||||
/* TODO */
|
||||
default:
|
||||
printf("##_syscall0 called, syscall id: %d\n", arg0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32
|
||||
__syscall1_wrapper(int32 arg0, int32 arg1)
|
||||
{
|
||||
switch (arg0) {
|
||||
case 6: /* close */
|
||||
/* TODO */
|
||||
default:
|
||||
printf("##_syscall1 called, syscall id: %d\n", arg0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32
|
||||
__syscall2_wrapper(int32 arg0, int32 arg1, int32 arg2)
|
||||
{
|
||||
switch (arg0) {
|
||||
case 183: /* getcwd */
|
||||
/* TODO */
|
||||
default:
|
||||
printf("##_syscall2 called, syscall id: %d\n", arg0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32
|
||||
__syscall3_wrapper(int32 arg0, int32 arg1, int32 arg2, int32 arg3)
|
||||
{
|
||||
WASMModuleInstance *module_inst = get_module_inst();
|
||||
|
||||
switch (arg0) {
|
||||
case 54: /* ioctl */
|
||||
{
|
||||
/* Implement syscall 54 and syscall 146 to support printf()
|
||||
for non SIDE_MODULE=1 mode */
|
||||
struct winsize *wsz;
|
||||
|
||||
if (!validate_app_addr(arg3, sizeof(struct winsize)))
|
||||
return 0;
|
||||
|
||||
wsz = (struct winsize*)addr_app_to_native(arg3);
|
||||
return syscall(54, arg1, arg2, wsz);
|
||||
}
|
||||
|
||||
case 145: /* readv */
|
||||
case 146: /* writev */
|
||||
{
|
||||
/* Implement syscall 54 and syscall 146 to support printf()
|
||||
for non SIDE_MODULE=1 mode */
|
||||
uint32 iovcnt = arg3, i;
|
||||
struct iovec *vec_begin, *vec;
|
||||
|
||||
if (!validate_app_addr(arg2, sizeof(struct iovec)))
|
||||
return 0;
|
||||
|
||||
vec_begin = vec = (struct iovec*)addr_app_to_native(arg2);
|
||||
for (i = 0; i < iovcnt; i++, vec++) {
|
||||
if (vec->iov_len > 0) {
|
||||
if (!validate_app_addr((int32)vec->iov_base, 1))
|
||||
return 0;
|
||||
vec->iov_base = addr_app_to_native((int32)vec->iov_base);
|
||||
}
|
||||
}
|
||||
if (arg0 == 145)
|
||||
return syscall(145, arg1, vec_begin, arg3);
|
||||
else
|
||||
return syscall(146, arg1, vec_begin, arg3);
|
||||
}
|
||||
|
||||
case 3: /* read*/
|
||||
case 5: /* open */
|
||||
case 221: /* fcntl */
|
||||
/* TODO */
|
||||
default:
|
||||
printf("##_syscall3 called, syscall id: %d\n", arg0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32
|
||||
__syscall4_wrapper(int32 arg0, int32 arg1, int32 arg2,
|
||||
int32 arg3, int32 arg4)
|
||||
{
|
||||
printf("##_syscall4 called, syscall id: %d\n", arg0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32
|
||||
__syscall5_wrapper(int32 arg0, int32 arg1, int32 arg2,
|
||||
int32 arg3, int32 arg4, int32 arg5)
|
||||
{
|
||||
switch (arg0) {
|
||||
case 140: /* llseek */
|
||||
/* TODO */
|
||||
default:
|
||||
printf("##_syscall5 called, args[0]: %d\n", arg0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define GET_EMCC_SYSCALL_ARGS() \
|
||||
WASMModuleInstance *module_inst = get_module_inst(); \
|
||||
int32 *args; \
|
||||
if (!validate_app_addr(args_off, 1)) \
|
||||
return 0; \
|
||||
args = addr_app_to_native(args_off) \
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER0(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id) { \
|
||||
return __syscall0_wrapper(id); \
|
||||
}
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER1(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id, int32 args_off) {\
|
||||
GET_EMCC_SYSCALL_ARGS(); \
|
||||
return __syscall1_wrapper(id, args[0]); \
|
||||
}
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER2(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id, int32 args_off) {\
|
||||
GET_EMCC_SYSCALL_ARGS(); \
|
||||
return __syscall2_wrapper(id, args[0], args[1]); \
|
||||
}
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER3(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id, int32 args_off) {\
|
||||
GET_EMCC_SYSCALL_ARGS(); \
|
||||
return __syscall3_wrapper(id, args[0], args[1], args[2]); \
|
||||
}
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER4(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id, int32 args_off) {\
|
||||
GET_EMCC_SYSCALL_ARGS(); \
|
||||
return __syscall4_wrapper(id, args[0], args[1], args[2], args[3]);\
|
||||
}
|
||||
|
||||
#define EMCC_SYSCALL_WRAPPER5(id) \
|
||||
static int32 ___syscall##id##_wrapper(int32 _id, int32 args_off) {\
|
||||
GET_EMCC_SYSCALL_ARGS(); \
|
||||
return __syscall5_wrapper(id, args[0], args[1], args[2], \
|
||||
args[3], args[4]); \
|
||||
}
|
||||
|
||||
EMCC_SYSCALL_WRAPPER0(199)
|
||||
|
||||
EMCC_SYSCALL_WRAPPER1(6)
|
||||
|
||||
EMCC_SYSCALL_WRAPPER2(183)
|
||||
|
||||
EMCC_SYSCALL_WRAPPER3(3)
|
||||
EMCC_SYSCALL_WRAPPER3(5)
|
||||
EMCC_SYSCALL_WRAPPER3(54)
|
||||
EMCC_SYSCALL_WRAPPER3(145)
|
||||
EMCC_SYSCALL_WRAPPER3(146)
|
||||
EMCC_SYSCALL_WRAPPER3(221)
|
||||
|
||||
EMCC_SYSCALL_WRAPPER5(140)
|
||||
|
||||
static int32
|
||||
getTotalMemory_wrapper()
|
||||
{
|
||||
WASMModuleInstance *module_inst = wasm_runtime_get_current_module_inst();
|
||||
WASMMemoryInstance *memory = module_inst->default_memory;
|
||||
return NumBytesPerPage * memory->cur_page_count;
|
||||
}
|
||||
|
||||
static int32
|
||||
enlargeMemory_wrapper()
|
||||
{
|
||||
bool ret;
|
||||
WASMModuleInstance *module_inst = wasm_runtime_get_current_module_inst();
|
||||
WASMMemoryInstance *memory = module_inst->default_memory;
|
||||
uint32 DYNAMICTOP_PTR_offset = module_inst->DYNAMICTOP_PTR_offset;
|
||||
uint32 addr_data_offset = *(uint32*)(memory->global_data + DYNAMICTOP_PTR_offset);
|
||||
uint32 *DYNAMICTOP_PTR = (uint32*)(memory->memory_data + addr_data_offset);
|
||||
uint32 memory_size_expected = *DYNAMICTOP_PTR;
|
||||
uint32 total_page_count = (memory_size_expected + NumBytesPerPage - 1) / NumBytesPerPage;
|
||||
|
||||
if (total_page_count < memory->cur_page_count) {
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
ret = wasm_runtime_enlarge_memory(module_inst, total_page_count -
|
||||
memory->cur_page_count);
|
||||
return ret ? 1 : 0;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_abort_wrapper(int32 code)
|
||||
{
|
||||
WASMModuleInstance *module_inst = wasm_runtime_get_current_module_inst();
|
||||
char buf[32];
|
||||
|
||||
snprintf(buf, sizeof(buf), "env.abort(%i)", code);
|
||||
wasm_runtime_set_exception(module_inst, buf);
|
||||
}
|
||||
|
||||
static void
|
||||
abortOnCannotGrowMemory_wrapper()
|
||||
{
|
||||
WASMModuleInstance *module_inst = wasm_runtime_get_current_module_inst();
|
||||
wasm_runtime_set_exception(module_inst, "abort on cannot grow memory");
|
||||
}
|
||||
|
||||
static void
|
||||
___setErrNo_wrapper(int32 error_no)
|
||||
{
|
||||
errno = error_no;
|
||||
}
|
||||
|
||||
/* TODO: add function parameter/result types check */
|
||||
#define REG_NATIVE_FUNC(module_name, func_name) \
|
||||
{#module_name, #func_name, func_name##_wrapper}
|
||||
|
||||
typedef struct WASMNativeFuncDef {
|
||||
const char *module_name;
|
||||
const char *func_name;
|
||||
void *func_ptr;
|
||||
} WASMNativeFuncDef;
|
||||
|
||||
static WASMNativeFuncDef native_func_defs[] = {
|
||||
REG_NATIVE_FUNC(env, __syscall0),
|
||||
REG_NATIVE_FUNC(env, __syscall1),
|
||||
REG_NATIVE_FUNC(env, __syscall2),
|
||||
REG_NATIVE_FUNC(env, __syscall3),
|
||||
REG_NATIVE_FUNC(env, __syscall4),
|
||||
REG_NATIVE_FUNC(env, __syscall5),
|
||||
REG_NATIVE_FUNC(env, ___syscall3),
|
||||
REG_NATIVE_FUNC(env, ___syscall5),
|
||||
REG_NATIVE_FUNC(env, ___syscall6),
|
||||
REG_NATIVE_FUNC(env, ___syscall54),
|
||||
REG_NATIVE_FUNC(env, ___syscall140),
|
||||
REG_NATIVE_FUNC(env, ___syscall145),
|
||||
REG_NATIVE_FUNC(env, ___syscall146),
|
||||
REG_NATIVE_FUNC(env, ___syscall183),
|
||||
REG_NATIVE_FUNC(env, ___syscall199),
|
||||
REG_NATIVE_FUNC(env, ___syscall221),
|
||||
REG_NATIVE_FUNC(env, _abort),
|
||||
REG_NATIVE_FUNC(env, abortOnCannotGrowMemory),
|
||||
REG_NATIVE_FUNC(env, enlargeMemory),
|
||||
REG_NATIVE_FUNC(env, getTotalMemory),
|
||||
REG_NATIVE_FUNC(env, ___setErrNo),
|
||||
};
|
||||
|
||||
void*
|
||||
wasm_platform_native_func_lookup(const char *module_name,
|
||||
const char *func_name)
|
||||
{
|
||||
uint32 size = sizeof(native_func_defs) / sizeof(WASMNativeFuncDef);
|
||||
WASMNativeFuncDef *func_def = native_func_defs;
|
||||
WASMNativeFuncDef *func_def_end = func_def + size;
|
||||
|
||||
if (!module_name || !func_name)
|
||||
return NULL;
|
||||
|
||||
while (func_def < func_def_end) {
|
||||
if (!strcmp(func_def->module_name, module_name)
|
||||
&& !strcmp(func_def->func_name, func_name))
|
||||
return (void*)(uintptr_t)func_def->func_ptr;
|
||||
func_def++;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
96
core/iwasm/runtime/platform/linux/wasm_platform.c
Normal file
96
core/iwasm/runtime/platform/linux/wasm_platform.c
Normal file
@ -0,0 +1,96 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_platform.h"
|
||||
#include "wasm_memory.h"
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <dlfcn.h>
|
||||
|
||||
bool is_little_endian = false;
|
||||
|
||||
bool __is_little_endian()
|
||||
{
|
||||
union w
|
||||
{
|
||||
int a;
|
||||
char b;
|
||||
}c;
|
||||
|
||||
c.a = 1;
|
||||
return (c.b == 1);
|
||||
}
|
||||
|
||||
int
|
||||
wasm_platform_init()
|
||||
{
|
||||
if (__is_little_endian())
|
||||
is_little_endian = true;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
char*
|
||||
wasm_read_file_to_buffer(const char *filename, int *ret_size)
|
||||
{
|
||||
char *buffer;
|
||||
int file;
|
||||
int file_size, read_size;
|
||||
struct stat stat_buf;
|
||||
|
||||
if (!filename || !ret_size) {
|
||||
LOG_ERROR("Read file to buffer failed: invalid filename or ret size.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((file = open(filename, O_RDONLY, 0)) == -1) {
|
||||
LOG_ERROR("Read file to buffer failed: open file %s failed.\n",
|
||||
filename);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (fstat(file, &stat_buf) != 0) {
|
||||
LOG_ERROR("Read file to buffer failed: fstat file %s failed.\n",
|
||||
filename);
|
||||
close(file);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
file_size = stat_buf.st_size;
|
||||
|
||||
if (!(buffer = wasm_malloc(file_size))) {
|
||||
LOG_ERROR("Read file to buffer failed: alloc memory failed.\n");
|
||||
close(file);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
read_size = read(file, buffer, file_size);
|
||||
close(file);
|
||||
|
||||
if (read_size < file_size) {
|
||||
LOG_ERROR("Read file to buffer failed: read file content failed.\n");
|
||||
wasm_free(buffer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*ret_size = file_size;
|
||||
return buffer;
|
||||
}
|
||||
|
||||
104
core/iwasm/runtime/platform/linux/wasm_platform.h
Normal file
104
core/iwasm/runtime/platform/linux/wasm_platform.h
Normal file
@ -0,0 +1,104 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_PLATFORM_H
|
||||
#define _WASM_PLATFORM_H
|
||||
|
||||
#include "wasm_config.h"
|
||||
#include "wasm_types.h"
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdbool.h>
|
||||
typedef uint64_t uint64;
|
||||
typedef int64_t int64;
|
||||
typedef float float32;
|
||||
typedef double float64;
|
||||
|
||||
#ifndef NULL
|
||||
# define NULL ((void*) 0)
|
||||
#endif
|
||||
|
||||
#define WASM_PLATFORM "Linux"
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <ctype.h>
|
||||
#include <pthread.h>
|
||||
#include <limits.h>
|
||||
#include <semaphore.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <math.h>
|
||||
|
||||
/**
|
||||
* Return the offset of the given field in the given type.
|
||||
*
|
||||
* @param Type the type containing the filed
|
||||
* @param field the field in the type
|
||||
*
|
||||
* @return the offset of field in Type
|
||||
*/
|
||||
#ifndef offsetof
|
||||
#define offsetof(Type, field) ((size_t)(&((Type *)0)->field))
|
||||
#endif
|
||||
|
||||
typedef pthread_t korp_tid;
|
||||
typedef pthread_mutex_t korp_mutex;
|
||||
|
||||
int wasm_platform_init();
|
||||
|
||||
extern bool is_little_endian;
|
||||
|
||||
#include <string.h>
|
||||
|
||||
/* The following operations declared in string.h may be defined as
|
||||
macros on Linux, so don't declare them as functions here. */
|
||||
/* memset */
|
||||
/* memcpy */
|
||||
/* memmove */
|
||||
|
||||
/* #include <stdio.h> */
|
||||
|
||||
/* Unit test framework is based on C++, where the declaration of
|
||||
snprintf is different. */
|
||||
#ifndef __cplusplus
|
||||
int snprintf(char *buffer, size_t count, const char *format, ...);
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* #include <math.h> */
|
||||
|
||||
#ifndef __cplusplus
|
||||
double sqrt(double x);
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
extern int fopen_s(FILE ** pFile, const char *filename, const char *mode);
|
||||
|
||||
char*
|
||||
wasm_read_file_to_buffer(const char *filename, int *ret_size);
|
||||
|
||||
void*
|
||||
wasm_dlsym(void *handle, const char *symbol);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
126
core/iwasm/runtime/platform/zephyr/COPYRIGHT
Normal file
126
core/iwasm/runtime/platform/zephyr/COPYRIGHT
Normal file
@ -0,0 +1,126 @@
|
||||
# $FreeBSD$
|
||||
# @(#)COPYRIGHT 8.2 (Berkeley) 3/21/94
|
||||
|
||||
The compilation of software known as FreeBSD is distributed under the
|
||||
following terms:
|
||||
|
||||
Copyright (c) 1992-2019 The FreeBSD Project.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions
|
||||
are met:
|
||||
1. Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright
|
||||
notice, this list of conditions and the following disclaimer in the
|
||||
documentation and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
SUCH DAMAGE.
|
||||
|
||||
The 4.4BSD and 4.4BSD-Lite software is distributed under the following
|
||||
terms:
|
||||
|
||||
All of the documentation and software included in the 4.4BSD and 4.4BSD-Lite
|
||||
Releases is copyrighted by The Regents of the University of California.
|
||||
|
||||
Copyright 1979, 1980, 1983, 1986, 1988, 1989, 1991, 1992, 1993, 1994
|
||||
The Regents of the University of California. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions
|
||||
are met:
|
||||
1. Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright
|
||||
notice, this list of conditions and the following disclaimer in the
|
||||
documentation and/or other materials provided with the distribution.
|
||||
3. All advertising materials mentioning features or use of this software
|
||||
must display the following acknowledgement:
|
||||
This product includes software developed by the University of
|
||||
California, Berkeley and its contributors.
|
||||
4. Neither the name of the University nor the names of its contributors
|
||||
may be used to endorse or promote products derived from this software
|
||||
without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
SUCH DAMAGE.
|
||||
|
||||
The Institute of Electrical and Electronics Engineers and the American
|
||||
National Standards Committee X3, on Information Processing Systems have
|
||||
given us permission to reprint portions of their documentation.
|
||||
|
||||
In the following statement, the phrase ``this text'' refers to portions
|
||||
of the system documentation.
|
||||
|
||||
Portions of this text are reprinted and reproduced in electronic form in
|
||||
the second BSD Networking Software Release, from IEEE Std 1003.1-1988, IEEE
|
||||
Standard Portable Operating System Interface for Computer Environments
|
||||
(POSIX), copyright C 1988 by the Institute of Electrical and Electronics
|
||||
Engineers, Inc. In the event of any discrepancy between these versions
|
||||
and the original IEEE Standard, the original IEEE Standard is the referee
|
||||
document.
|
||||
|
||||
In the following statement, the phrase ``This material'' refers to portions
|
||||
of the system documentation.
|
||||
|
||||
This material is reproduced with permission from American National
|
||||
Standards Committee X3, on Information Processing Systems. Computer and
|
||||
Business Equipment Manufacturers Association (CBEMA), 311 First St., NW,
|
||||
Suite 500, Washington, DC 20001-2178. The developmental work of
|
||||
Programming Language C was completed by the X3J11 Technical Committee.
|
||||
|
||||
The views and conclusions contained in the software and documentation are
|
||||
those of the authors and should not be interpreted as representing official
|
||||
policies, either expressed or implied, of the Regents of the University
|
||||
of California.
|
||||
|
||||
|
||||
NOTE: The copyright of UC Berkeley's Berkeley Software Distribution ("BSD")
|
||||
source has been updated. The copyright addendum may be found at
|
||||
ftp://ftp.cs.berkeley.edu/pub/4bsd/README.Impt.License.Change and is
|
||||
included below.
|
||||
|
||||
July 22, 1999
|
||||
|
||||
To All Licensees, Distributors of Any Version of BSD:
|
||||
|
||||
As you know, certain of the Berkeley Software Distribution ("BSD") source
|
||||
code files require that further distributions of products containing all or
|
||||
portions of the software, acknowledge within their advertising materials
|
||||
that such products contain software developed by UC Berkeley and its
|
||||
contributors.
|
||||
|
||||
Specifically, the provision reads:
|
||||
|
||||
" * 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors."
|
||||
|
||||
Effective immediately, licensees and distributors are no longer required to
|
||||
include the acknowledgement within advertising materials. Accordingly, the
|
||||
foregoing paragraph of those BSD Unix files containing it is hereby deleted
|
||||
in its entirety.
|
||||
|
||||
William Hoskins
|
||||
Director, Office of Technology Licensing
|
||||
University of California, Berkeley
|
||||
26
core/iwasm/runtime/platform/zephyr/wasm-native.c
Normal file
26
core/iwasm/runtime/platform/zephyr/wasm-native.c
Normal file
@ -0,0 +1,26 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm-native.h"
|
||||
|
||||
|
||||
void*
|
||||
wasm_platform_native_func_lookup(const char *module_name,
|
||||
const char *func_name)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
581
core/iwasm/runtime/platform/zephyr/wasm_math.c
Normal file
581
core/iwasm/runtime/platform/zephyr/wasm_math.c
Normal file
@ -0,0 +1,581 @@
|
||||
/*-
|
||||
* SPDX-License-Identifier: BSD-2-Clause-FreeBSD
|
||||
*
|
||||
* Copyright (c) 2004 David Schultz <das@FreeBSD.ORG>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $FreeBSD$
|
||||
*/
|
||||
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_platform.h"
|
||||
#include "wasm_platform_log.h"
|
||||
#include "wasm_memory.h"
|
||||
|
||||
#define __FDLIBM_STDC__
|
||||
|
||||
typedef uint32_t u_int32_t;
|
||||
typedef uint64_t u_int64_t;
|
||||
|
||||
typedef union u32double_tag {
|
||||
int *pint;
|
||||
double *pdouble;
|
||||
} U32DOUBLE;
|
||||
|
||||
static inline int *
|
||||
pdouble2pint(double *pdouble)
|
||||
{
|
||||
U32DOUBLE u;
|
||||
u.pdouble = pdouble;
|
||||
return u.pint;
|
||||
}
|
||||
|
||||
typedef union
|
||||
{
|
||||
double value;
|
||||
struct
|
||||
{
|
||||
u_int32_t lsw;
|
||||
u_int32_t msw;
|
||||
} parts;
|
||||
struct
|
||||
{
|
||||
u_int64_t w;
|
||||
} xparts;
|
||||
} ieee_double_shape_type_little;
|
||||
|
||||
typedef union
|
||||
{
|
||||
double value;
|
||||
struct
|
||||
{
|
||||
u_int32_t msw;
|
||||
u_int32_t lsw;
|
||||
} parts;
|
||||
struct
|
||||
{
|
||||
u_int64_t w;
|
||||
} xparts;
|
||||
} ieee_double_shape_type_big;
|
||||
|
||||
typedef union {
|
||||
double d;
|
||||
struct {
|
||||
unsigned int manl :32;
|
||||
unsigned int manh :20;
|
||||
unsigned int exp :11;
|
||||
unsigned int sign :1;
|
||||
} bits;
|
||||
} IEEEd2bits_L;
|
||||
|
||||
typedef union {
|
||||
double d;
|
||||
struct {
|
||||
unsigned int sign :1;
|
||||
unsigned int exp :11;
|
||||
unsigned int manh :20;
|
||||
unsigned int manl :32;
|
||||
} bits;
|
||||
} IEEEd2bits_B;
|
||||
|
||||
#define __HIL(x) *(1+pdouble2pint(&x))
|
||||
#define __LOL(x) *(pdouble2pint(&x))
|
||||
#define __HIB(x) *(int*)&x
|
||||
#define __LOB(x) *(1+(int*)&x)
|
||||
|
||||
/* Get two 32 bit ints from a double. */
|
||||
|
||||
#define EXTRACT_WORDS_L(ix0,ix1,d) \
|
||||
do { \
|
||||
ieee_double_shape_type_little ew_u; \
|
||||
ew_u.value = (d); \
|
||||
(ix0) = ew_u.parts.msw; \
|
||||
(ix1) = ew_u.parts.lsw; \
|
||||
} while (0)
|
||||
|
||||
/* Set a double from two 32 bit ints. */
|
||||
|
||||
#define INSERT_WORDS_L(d,ix0,ix1) \
|
||||
do { \
|
||||
ieee_double_shape_type_little iw_u; \
|
||||
iw_u.parts.msw = (ix0); \
|
||||
iw_u.parts.lsw = (ix1); \
|
||||
(d) = iw_u.value; \
|
||||
} while (0)
|
||||
|
||||
/* Get two 32 bit ints from a double. */
|
||||
|
||||
#define EXTRACT_WORDS_B(ix0,ix1,d) \
|
||||
do { \
|
||||
ieee_double_shape_type_big ew_u; \
|
||||
ew_u.value = (d); \
|
||||
(ix0) = ew_u.parts.msw; \
|
||||
(ix1) = ew_u.parts.lsw; \
|
||||
} while (0)
|
||||
|
||||
/* Set a double from two 32 bit ints. */
|
||||
|
||||
#define INSERT_WORDS_B(d,ix0,ix1) \
|
||||
do { \
|
||||
ieee_double_shape_type_big iw_u; \
|
||||
iw_u.parts.msw = (ix0); \
|
||||
iw_u.parts.lsw = (ix1); \
|
||||
(d) = iw_u.value; \
|
||||
} while (0)
|
||||
|
||||
/* Get the more significant 32 bit int from a double. */
|
||||
#define GET_HIGH_WORD_L(i,d) \
|
||||
do { \
|
||||
ieee_double_shape_type_little gh_u; \
|
||||
gh_u.value = (d); \
|
||||
(i) = gh_u.parts.msw; \
|
||||
} while (0)
|
||||
|
||||
/* Get the more significant 32 bit int from a double. */
|
||||
#define GET_HIGH_WORD_B(i,d) \
|
||||
do { \
|
||||
ieee_double_shape_type_big gh_u; \
|
||||
gh_u.value = (d); \
|
||||
(i) = gh_u.parts.msw; \
|
||||
} while (0)
|
||||
|
||||
/* Set the more significant 32 bits of a double from an int. */
|
||||
#define SET_HIGH_WORD_L(d,v) \
|
||||
do { \
|
||||
ieee_double_shape_type_little sh_u; \
|
||||
sh_u.value = (d); \
|
||||
sh_u.parts.msw = (v); \
|
||||
(d) = sh_u.value; \
|
||||
} while (0)
|
||||
|
||||
/* Set the more significant 32 bits of a double from an int. */
|
||||
#define SET_HIGH_WORD_B(d,v) \
|
||||
do { \
|
||||
ieee_double_shape_type_big sh_u; \
|
||||
sh_u.value = (d); \
|
||||
sh_u.parts.msw = (v); \
|
||||
(d) = sh_u.value; \
|
||||
} while (0)
|
||||
|
||||
/* Macro wrappers. */
|
||||
#define EXTRACT_WORDS(ix0,ix1,d) do { \
|
||||
if (is_little_endian) \
|
||||
EXTRACT_WORDS_L(ix0,ix1,d); \
|
||||
else \
|
||||
EXTRACT_WORDS_B(ix0,ix1,d); \
|
||||
} while (0)
|
||||
|
||||
#define INSERT_WORDS(d,ix0,ix1) do { \
|
||||
if (is_little_endian) \
|
||||
INSERT_WORDS_L(d,ix0,ix1); \
|
||||
else \
|
||||
INSERT_WORDS_B(d,ix0,ix1); \
|
||||
} while (0)
|
||||
|
||||
#define GET_HIGH_WORD(i,d) \
|
||||
do { \
|
||||
if (is_little_endian) \
|
||||
GET_HIGH_WORD_L(i,d); \
|
||||
else \
|
||||
GET_HIGH_WORD_B(i,d); \
|
||||
} while (0)
|
||||
|
||||
#define SET_HIGH_WORD(d,v) \
|
||||
do { \
|
||||
if (is_little_endian) \
|
||||
SET_HIGH_WORD_L(d,v); \
|
||||
else \
|
||||
SET_HIGH_WORD_B(d,v); \
|
||||
} while (0)
|
||||
|
||||
#define __HI(x) (is_little_endian ? __HIL(x) : __HIB(x))
|
||||
|
||||
#define __LO(x) (is_little_endian ? __LOL(x) : __LOB(x))
|
||||
|
||||
/*
|
||||
* Attempt to get strict C99 semantics for assignment with non-C99 compilers.
|
||||
*/
|
||||
#if FLT_EVAL_METHOD == 0 || __GNUC__ == 0
|
||||
#define STRICT_ASSIGN(type, lval, rval) ((lval) = (rval))
|
||||
#else
|
||||
#define STRICT_ASSIGN(type, lval, rval) do { \
|
||||
volatile type __lval; \
|
||||
\
|
||||
if (sizeof(type) >= sizeof(long double)) \
|
||||
(lval) = (rval); \
|
||||
else { \
|
||||
__lval = (rval); \
|
||||
(lval) = __lval; \
|
||||
} \
|
||||
} while (0)
|
||||
#endif
|
||||
|
||||
#ifdef __FDLIBM_STDC__
|
||||
static const double huge = 1.0e300;
|
||||
#else
|
||||
static double huge = 1.0e300;
|
||||
#endif
|
||||
|
||||
#ifdef __STDC__
|
||||
static const double
|
||||
#else
|
||||
static double
|
||||
#endif
|
||||
tiny = 1.0e-300;
|
||||
|
||||
#ifdef __STDC__
|
||||
static const double
|
||||
#else
|
||||
static double
|
||||
#endif
|
||||
one= 1.00000000000000000000e+00; /* 0x3FF00000, 0x00000000 */
|
||||
|
||||
#ifdef __STDC__
|
||||
static const double
|
||||
#else
|
||||
static double
|
||||
#endif
|
||||
TWO52[2]={
|
||||
4.50359962737049600000e+15, /* 0x43300000, 0x00000000 */
|
||||
-4.50359962737049600000e+15, /* 0xC3300000, 0x00000000 */
|
||||
};
|
||||
|
||||
static double freebsd_sqrt(double x);
|
||||
static double freebsd_floor(double x);
|
||||
static double freebsd_ceil(double x);
|
||||
static double freebsd_fabs(double x);
|
||||
static double freebsd_rint(double x);
|
||||
static int freebsd_isnan(double x);
|
||||
|
||||
static double freebsd_sqrt(double x) /* wrapper sqrt */
|
||||
{
|
||||
double z;
|
||||
int32_t sign = (int)0x80000000;
|
||||
int32_t ix0,s0,q,m,t,i;
|
||||
u_int32_t r,t1,s1,ix1,q1;
|
||||
|
||||
EXTRACT_WORDS(ix0,ix1,x);
|
||||
|
||||
/* take care of Inf and NaN */
|
||||
if((ix0&0x7ff00000)==0x7ff00000) {
|
||||
return x*x+x; /* sqrt(NaN)=NaN, sqrt(+inf)=+inf
|
||||
sqrt(-inf)=sNaN */
|
||||
}
|
||||
/* take care of zero */
|
||||
if(ix0<=0) {
|
||||
if(((ix0&(~sign))|ix1)==0) return x;/* sqrt(+-0) = +-0 */
|
||||
else if(ix0<0)
|
||||
return (x-x)/(x-x); /* sqrt(-ve) = sNaN */
|
||||
}
|
||||
/* normalize x */
|
||||
m = (ix0>>20);
|
||||
if(m==0) { /* subnormal x */
|
||||
while(ix0==0) {
|
||||
m -= 21;
|
||||
ix0 |= (ix1>>11); ix1 <<= 21;
|
||||
}
|
||||
for(i=0;(ix0&0x00100000)==0;i++) ix0<<=1;
|
||||
m -= i-1;
|
||||
ix0 |= (ix1>>(32-i));
|
||||
ix1 <<= i;
|
||||
}
|
||||
m -= 1023; /* unbias exponent */
|
||||
ix0 = (ix0&0x000fffff)|0x00100000;
|
||||
if(m&1){ /* odd m, double x to make it even */
|
||||
ix0 += ix0 + ((ix1&sign)>>31);
|
||||
ix1 += ix1;
|
||||
}
|
||||
m >>= 1; /* m = [m/2] */
|
||||
|
||||
/* generate sqrt(x) bit by bit */
|
||||
ix0 += ix0 + ((ix1&sign)>>31);
|
||||
ix1 += ix1;
|
||||
q = q1 = s0 = s1 = 0; /* [q,q1] = sqrt(x) */
|
||||
r = 0x00200000; /* r = moving bit from right to left */
|
||||
|
||||
while(r!=0) {
|
||||
t = s0+r;
|
||||
if(t<=ix0) {
|
||||
s0 = t+r;
|
||||
ix0 -= t;
|
||||
q += r;
|
||||
}
|
||||
ix0 += ix0 + ((ix1&sign)>>31);
|
||||
ix1 += ix1;
|
||||
r>>=1;
|
||||
}
|
||||
|
||||
r = sign;
|
||||
while(r!=0) {
|
||||
t1 = s1+r;
|
||||
t = s0;
|
||||
if((t<ix0)||((t==ix0)&&(t1<=ix1))) {
|
||||
s1 = t1+r;
|
||||
if(((t1&sign)==sign)&&(s1&sign)==0) s0 += 1;
|
||||
ix0 -= t;
|
||||
if (ix1 < t1) ix0 -= 1;
|
||||
ix1 -= t1;
|
||||
q1 += r;
|
||||
}
|
||||
ix0 += ix0 + ((ix1&sign)>>31);
|
||||
ix1 += ix1;
|
||||
r>>=1;
|
||||
}
|
||||
|
||||
/* use floating add to find out rounding direction */
|
||||
if((ix0|ix1)!=0) {
|
||||
z = one-tiny; /* trigger inexact flag */
|
||||
if (z>=one) {
|
||||
z = one+tiny;
|
||||
if (q1==(u_int32_t)0xffffffff) { q1=0; q += 1;}
|
||||
else if (z>one) {
|
||||
if (q1==(u_int32_t)0xfffffffe) q+=1;
|
||||
q1+=2;
|
||||
} else
|
||||
q1 += (q1&1);
|
||||
}
|
||||
}
|
||||
ix0 = (q>>1)+0x3fe00000;
|
||||
ix1 = q1>>1;
|
||||
if ((q&1)==1) ix1 |= sign;
|
||||
ix0 += (m <<20);
|
||||
|
||||
INSERT_WORDS(z,ix0,ix1);
|
||||
|
||||
return z;
|
||||
}
|
||||
|
||||
static double freebsd_floor(double x)
|
||||
{
|
||||
int32_t i0,i1,j0;
|
||||
u_int32_t i,j;
|
||||
|
||||
EXTRACT_WORDS(i0,i1,x);
|
||||
|
||||
j0 = ((i0>>20)&0x7ff)-0x3ff;
|
||||
if(j0<20) {
|
||||
if(j0<0) { /* raise inexact if x != 0 */
|
||||
if(huge+x>0.0) {/* return 0*sign(x) if |x|<1 */
|
||||
if(i0>=0) {i0=i1=0;}
|
||||
else if(((i0&0x7fffffff)|i1)!=0)
|
||||
{ i0=0xbff00000;i1=0;}
|
||||
}
|
||||
} else {
|
||||
i = (0x000fffff)>>j0;
|
||||
if(((i0&i)|i1)==0) return x; /* x is integral */
|
||||
if(huge+x>0.0) { /* raise inexact flag */
|
||||
if(i0<0) i0 += (0x00100000)>>j0;
|
||||
i0 &= (~i); i1=0;
|
||||
}
|
||||
}
|
||||
} else if (j0>51) {
|
||||
if(j0==0x400) return x+x; /* inf or NaN */
|
||||
else return x; /* x is integral */
|
||||
} else {
|
||||
i = ((u_int32_t)(0xffffffff))>>(j0-20);
|
||||
if((i1&i)==0) return x; /* x is integral */
|
||||
if(huge+x>0.0) { /* raise inexact flag */
|
||||
if(i0<0) {
|
||||
if(j0==20) i0+=1;
|
||||
else {
|
||||
j = i1+(1<<(52-j0));
|
||||
if(j<i1) i0 +=1 ; /* got a carry */
|
||||
i1=j;
|
||||
}
|
||||
}
|
||||
i1 &= (~i);
|
||||
}
|
||||
}
|
||||
|
||||
INSERT_WORDS(x,i0,i1);
|
||||
|
||||
return x;
|
||||
}
|
||||
|
||||
static double freebsd_ceil(double x)
|
||||
{
|
||||
int32_t i0,i1,j0;
|
||||
u_int32_t i,j;
|
||||
EXTRACT_WORDS(i0,i1,x);
|
||||
j0 = ((i0>>20)&0x7ff)-0x3ff;
|
||||
if(j0<20) {
|
||||
if(j0<0) { /* raise inexact if x != 0 */
|
||||
if(huge+x>0.0) {/* return 0*sign(x) if |x|<1 */
|
||||
if(i0<0) {i0=0x80000000;i1=0;}
|
||||
else if((i0|i1)!=0) { i0=0x3ff00000;i1=0;}
|
||||
}
|
||||
} else {
|
||||
i = (0x000fffff)>>j0;
|
||||
if(((i0&i)|i1)==0) return x; /* x is integral */
|
||||
if(huge+x>0.0) { /* raise inexact flag */
|
||||
if(i0>0) i0 += (0x00100000)>>j0;
|
||||
i0 &= (~i); i1=0;
|
||||
}
|
||||
}
|
||||
} else if (j0>51) {
|
||||
if(j0==0x400) return x+x; /* inf or NaN */
|
||||
else return x; /* x is integral */
|
||||
} else {
|
||||
i = ((u_int32_t)(0xffffffff))>>(j0-20);
|
||||
if((i1&i)==0) return x; /* x is integral */
|
||||
if(huge+x>0.0) { /* raise inexact flag */
|
||||
if(i0>0) {
|
||||
if(j0==20) i0+=1;
|
||||
else {
|
||||
j = i1 + (1<<(52-j0));
|
||||
if(j<i1) i0+=1; /* got a carry */
|
||||
i1 = j;
|
||||
}
|
||||
}
|
||||
i1 &= (~i);
|
||||
}
|
||||
}
|
||||
INSERT_WORDS(x,i0,i1);
|
||||
return x;
|
||||
}
|
||||
|
||||
static double freebsd_rint(double x)
|
||||
{
|
||||
int32_t i0,j0,sx;
|
||||
u_int32_t i,i1;
|
||||
double w,t;
|
||||
EXTRACT_WORDS(i0,i1,x);
|
||||
sx = (i0>>31)&1;
|
||||
j0 = ((i0>>20)&0x7ff)-0x3ff;
|
||||
if(j0<20) {
|
||||
if(j0<0) {
|
||||
if(((i0&0x7fffffff)|i1)==0) return x;
|
||||
i1 |= (i0&0x0fffff);
|
||||
i0 &= 0xfffe0000;
|
||||
i0 |= ((i1|-i1)>>12)&0x80000;
|
||||
SET_HIGH_WORD(x,i0);
|
||||
STRICT_ASSIGN(double,w,TWO52[sx]+x);
|
||||
t = w-TWO52[sx];
|
||||
GET_HIGH_WORD(i0,t);
|
||||
SET_HIGH_WORD(t,(i0&0x7fffffff)|(sx<<31));
|
||||
return t;
|
||||
} else {
|
||||
i = (0x000fffff)>>j0;
|
||||
if(((i0&i)|i1)==0) return x; /* x is integral */
|
||||
i>>=1;
|
||||
if(((i0&i)|i1)!=0) {
|
||||
/*
|
||||
* Some bit is set after the 0.5 bit. To avoid the
|
||||
* possibility of errors from double rounding in
|
||||
* w = TWO52[sx]+x, adjust the 0.25 bit to a lower
|
||||
* guard bit. We do this for all j0<=51. The
|
||||
* adjustment is trickiest for j0==18 and j0==19
|
||||
* since then it spans the word boundary.
|
||||
*/
|
||||
if(j0==19) i1 = 0x40000000; else
|
||||
if(j0==18) i1 = 0x80000000; else
|
||||
i0 = (i0&(~i))|((0x20000)>>j0);
|
||||
}
|
||||
}
|
||||
} else if (j0>51) {
|
||||
if(j0==0x400) return x+x; /* inf or NaN */
|
||||
else return x; /* x is integral */
|
||||
} else {
|
||||
i = ((u_int32_t)(0xffffffff))>>(j0-20);
|
||||
if((i1&i)==0) return x; /* x is integral */
|
||||
i>>=1;
|
||||
if((i1&i)!=0) i1 = (i1&(~i))|((0x40000000)>>(j0-20));
|
||||
}
|
||||
INSERT_WORDS(x,i0,i1);
|
||||
STRICT_ASSIGN(double,w,TWO52[sx]+x);
|
||||
return w-TWO52[sx];
|
||||
}
|
||||
|
||||
static int freebsd_isnan(double d)
|
||||
{
|
||||
if (is_little_endian) {
|
||||
IEEEd2bits_L u;
|
||||
u.d = d;
|
||||
return (u.bits.exp == 2047 && (u.bits.manl != 0 || u.bits.manh != 0));
|
||||
}
|
||||
else {
|
||||
IEEEd2bits_B u;
|
||||
u.d = d;
|
||||
return (u.bits.exp == 2047 && (u.bits.manl != 0 || u.bits.manh != 0));
|
||||
}
|
||||
}
|
||||
|
||||
static double freebsd_fabs(double x)
|
||||
{
|
||||
u_int32_t high;
|
||||
GET_HIGH_WORD(high,x);
|
||||
SET_HIGH_WORD(x,high&0x7fffffff);
|
||||
return x;
|
||||
}
|
||||
|
||||
double sqrt(double x)
|
||||
{
|
||||
return freebsd_sqrt(x);
|
||||
}
|
||||
|
||||
double floor(double x)
|
||||
{
|
||||
return freebsd_floor(x);
|
||||
}
|
||||
|
||||
double ceil(double x)
|
||||
{
|
||||
return freebsd_ceil(x);
|
||||
}
|
||||
|
||||
double fmin(double x, double y)
|
||||
{
|
||||
return x < y ? x : y;
|
||||
}
|
||||
|
||||
double fmax(double x, double y)
|
||||
{
|
||||
return x > y ? x : y;
|
||||
}
|
||||
|
||||
double rint(double x)
|
||||
{
|
||||
return freebsd_rint(x);
|
||||
}
|
||||
|
||||
double fabs(double x)
|
||||
{
|
||||
return freebsd_fabs(x);
|
||||
}
|
||||
|
||||
int isnan(double x)
|
||||
{
|
||||
return freebsd_isnan(x);
|
||||
}
|
||||
|
||||
double trunc(double x)
|
||||
{
|
||||
return (x > 0) ? freebsd_floor(x) : freebsd_ceil(x);
|
||||
}
|
||||
|
||||
int signbit(double x)
|
||||
{
|
||||
return ((__HI(x) & 0x80000000) >> 31);
|
||||
}
|
||||
|
||||
56
core/iwasm/runtime/platform/zephyr/wasm_platform.c
Normal file
56
core/iwasm/runtime/platform/zephyr/wasm_platform.c
Normal file
@ -0,0 +1,56 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
#ifndef CONFIG_AEE_ENABLE
|
||||
static int
|
||||
_stdout_hook_iwasm(int c)
|
||||
{
|
||||
printk("%c", (char)c);
|
||||
return 1;
|
||||
}
|
||||
|
||||
extern void __stdout_hook_install(int (*hook)(int));
|
||||
#endif
|
||||
|
||||
bool is_little_endian = false;
|
||||
|
||||
bool __is_little_endian()
|
||||
{
|
||||
union w
|
||||
{
|
||||
int a;
|
||||
char b;
|
||||
}c;
|
||||
|
||||
c.a = 1;
|
||||
return (c.b == 1);
|
||||
}
|
||||
|
||||
int wasm_platform_init()
|
||||
{
|
||||
if (__is_little_endian())
|
||||
is_little_endian = true;
|
||||
|
||||
#ifndef CONFIG_AEE_ENABLE
|
||||
/* Enable printf() in Zephyr */
|
||||
__stdout_hook_install(_stdout_hook_iwasm);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
105
core/iwasm/runtime/platform/zephyr/wasm_platform.h
Normal file
105
core/iwasm/runtime/platform/zephyr/wasm_platform.h
Normal file
@ -0,0 +1,105 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_PLATFORM_H
|
||||
#define _WASM_PLATFORM_H
|
||||
|
||||
#include "wasm_config.h"
|
||||
#include "wasm_types.h"
|
||||
#include <autoconf.h>
|
||||
#include <zephyr.h>
|
||||
#include <kernel.h>
|
||||
#include <inttypes.h>
|
||||
|
||||
#include <stdbool.h>
|
||||
typedef uint64_t uint64;
|
||||
typedef int64_t int64;
|
||||
typedef float float32;
|
||||
typedef double float64;
|
||||
|
||||
#ifndef NULL
|
||||
# define NULL ((void*) 0)
|
||||
#endif
|
||||
|
||||
#define WASM_PLATFORM "Zephyr"
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <ctype.h>
|
||||
#include <limits.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
/**
|
||||
* Return the offset of the given field in the given type.
|
||||
*
|
||||
* @param Type the type containing the filed
|
||||
* @param field the field in the type
|
||||
*
|
||||
* @return the offset of field in Type
|
||||
*/
|
||||
#ifndef offsetof
|
||||
#define offsetof(Type, field) ((size_t)(&((Type *)0)->field))
|
||||
#endif
|
||||
|
||||
typedef struct k_thread korp_thread;
|
||||
typedef korp_thread *korp_tid;
|
||||
typedef struct k_mutex korp_mutex;
|
||||
|
||||
int wasm_platform_init();
|
||||
|
||||
extern bool is_little_endian;
|
||||
|
||||
#include <string.h>
|
||||
|
||||
/* The following operations declared in string.h may be defined as
|
||||
macros on Linux, so don't declare them as functions here. */
|
||||
/* memset */
|
||||
/* memcpy */
|
||||
/* memmove */
|
||||
|
||||
/* #include <stdio.h> */
|
||||
|
||||
/* Unit test framework is based on C++, where the declaration of
|
||||
snprintf is different. */
|
||||
#ifndef __cplusplus
|
||||
int snprintf(char *buffer, size_t count, const char *format, ...);
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* math functions */
|
||||
double sqrt(double x);
|
||||
double floor(double x);
|
||||
double ceil(double x);
|
||||
double fmin(double x, double y);
|
||||
double fmax(double x, double y);
|
||||
double rint(double x);
|
||||
double fabs(double x);
|
||||
double trunc(double x);
|
||||
int signbit(double x);
|
||||
int isnan(double x);
|
||||
|
||||
void*
|
||||
wasm_dlsym(void *handle, const char *symbol);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
22
core/iwasm/runtime/utils/utils.cmake
Normal file
22
core/iwasm/runtime/utils/utils.cmake
Normal file
@ -0,0 +1,22 @@
|
||||
# Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
set (UTILS_LIB_DIR ${CMAKE_CURRENT_LIST_DIR})
|
||||
|
||||
include_directories(${UTILS_LIB_DIR})
|
||||
|
||||
file (GLOB_RECURSE source_all ${UTILS_LIB_DIR}/*.c )
|
||||
|
||||
set (WASM_UTILS_LIB_SOURCE ${source_all})
|
||||
|
||||
107
core/iwasm/runtime/utils/wasm_dlfcn.c
Normal file
107
core/iwasm/runtime/utils/wasm_dlfcn.c
Normal file
@ -0,0 +1,107 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_platform.h"
|
||||
|
||||
|
||||
static bool sort_flag = false;
|
||||
|
||||
typedef struct NativeSymbol {
|
||||
const char *symbol;
|
||||
void *func_ptr;
|
||||
} NativeSymbol;
|
||||
|
||||
static bool
|
||||
sort_symbol_ptr(NativeSymbol *ptr, int len)
|
||||
{
|
||||
int i, j;
|
||||
NativeSymbol temp;
|
||||
|
||||
for (i = 0; i < len - 1; ++i) {
|
||||
for (j = i + 1; j < len; ++j) {
|
||||
if (strcmp((ptr+i)->symbol, (ptr+j)->symbol) > 0) {
|
||||
temp = ptr[i];
|
||||
ptr[i] = ptr[j];
|
||||
ptr[j] = temp;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static void *
|
||||
lookup_symbol(NativeSymbol *ptr, int len, const char *symbol)
|
||||
{
|
||||
int low = 0, mid, ret;
|
||||
int high = len - 1;
|
||||
|
||||
while (low <= high) {
|
||||
mid = (low + high) / 2;
|
||||
ret = strcmp(symbol, ptr[mid].symbol);
|
||||
|
||||
if (ret == 0)
|
||||
return ptr[mid].func_ptr;
|
||||
else if (ret < 0)
|
||||
high = mid - 1;
|
||||
else
|
||||
low = mid + 1;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int
|
||||
get_base_lib_export_apis(NativeSymbol **p_base_lib_apis);
|
||||
|
||||
int
|
||||
get_ext_lib_export_apis(NativeSymbol **p_ext_lib_apis);
|
||||
|
||||
static NativeSymbol *base_native_symbol_defs;
|
||||
static NativeSymbol *ext_native_symbol_defs;
|
||||
static int base_native_symbol_len;
|
||||
static int ext_native_symbol_len;
|
||||
|
||||
void *
|
||||
wasm_dlsym(void *handle, const char *symbol)
|
||||
{
|
||||
void *ret;
|
||||
|
||||
if (!sort_flag) {
|
||||
base_native_symbol_len = get_base_lib_export_apis(&base_native_symbol_defs);
|
||||
ext_native_symbol_len = get_ext_lib_export_apis(&ext_native_symbol_defs);
|
||||
|
||||
if (base_native_symbol_len > 0)
|
||||
sort_symbol_ptr(base_native_symbol_defs, base_native_symbol_len);
|
||||
|
||||
if (ext_native_symbol_len > 0)
|
||||
sort_symbol_ptr(ext_native_symbol_defs, ext_native_symbol_len);
|
||||
|
||||
sort_flag = true;
|
||||
}
|
||||
|
||||
if (!symbol)
|
||||
return NULL;
|
||||
|
||||
if ((ret = lookup_symbol(base_native_symbol_defs, base_native_symbol_len,
|
||||
symbol))
|
||||
|| (ret = lookup_symbol(ext_native_symbol_defs, ext_native_symbol_len,
|
||||
symbol)))
|
||||
return ret;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
301
core/iwasm/runtime/utils/wasm_hashmap.c
Normal file
301
core/iwasm/runtime/utils/wasm_hashmap.c
Normal file
@ -0,0 +1,301 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_hashmap.h"
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_thread.h"
|
||||
#include "wasm_memory.h"
|
||||
|
||||
|
||||
typedef struct HashMapElem {
|
||||
void *key;
|
||||
void *value;
|
||||
struct HashMapElem *next;
|
||||
} HashMapElem;
|
||||
|
||||
struct HashMap {
|
||||
/* size of element array */
|
||||
uint32 size;
|
||||
/* lock for elements */
|
||||
korp_mutex *lock;
|
||||
/* hash function of key */
|
||||
HashFunc hash_func;
|
||||
/* key equal function */
|
||||
KeyEqualFunc key_equal_func;
|
||||
KeyDestroyFunc key_destroy_func;
|
||||
ValueDestroyFunc value_destroy_func;
|
||||
HashMapElem *elements[1];
|
||||
};
|
||||
|
||||
HashMap*
|
||||
wasm_hash_map_create(uint32 size, bool use_lock,
|
||||
HashFunc hash_func,
|
||||
KeyEqualFunc key_equal_func,
|
||||
KeyDestroyFunc key_destroy_func,
|
||||
ValueDestroyFunc value_destroy_func)
|
||||
{
|
||||
HashMap *map;
|
||||
uint32 total_size;
|
||||
|
||||
if (size > HASH_MAP_MAX_SIZE) {
|
||||
LOG_ERROR("HashMap create failed: size is too large.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!hash_func || !key_equal_func) {
|
||||
LOG_ERROR("HashMap create failed: hash function or key equal function "
|
||||
" is NULL.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
total_size = offsetof(HashMap, elements) +
|
||||
sizeof(HashMapElem) * size +
|
||||
(use_lock ? sizeof(korp_mutex) : 0);
|
||||
|
||||
if (!(map = wasm_malloc(total_size))) {
|
||||
LOG_ERROR("HashMap create failed: alloc memory failed.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memset(map, 0, total_size);
|
||||
|
||||
if (use_lock) {
|
||||
map->lock = (korp_mutex*)
|
||||
((uint8*)map + offsetof(HashMap, elements) + sizeof(HashMapElem) * size);
|
||||
if (ws_mutex_init(map->lock, false)) {
|
||||
LOG_ERROR("HashMap create failed: init map lock failed.\n");
|
||||
wasm_free(map);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
map->size = size;
|
||||
map->hash_func = hash_func;
|
||||
map->key_equal_func = key_equal_func;
|
||||
map->key_destroy_func = key_destroy_func;
|
||||
map->value_destroy_func = value_destroy_func;
|
||||
return map;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_hash_map_insert(HashMap *map, void *key, void *value)
|
||||
{
|
||||
uint32 index;
|
||||
HashMapElem *elem;
|
||||
|
||||
if (!map || !key) {
|
||||
LOG_ERROR("HashMap insert elem failed: map or key is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_lock(map->lock);
|
||||
}
|
||||
|
||||
index = map->hash_func(key) % map->size;
|
||||
elem = map->elements[index];
|
||||
while (elem) {
|
||||
if (map->key_equal_func(elem->key, key)) {
|
||||
LOG_ERROR("HashMap insert elem failed: duplicated key found.\n");
|
||||
goto fail;
|
||||
}
|
||||
elem = elem->next;
|
||||
}
|
||||
|
||||
if (!(elem = wasm_malloc(sizeof(HashMapElem)))) {
|
||||
LOG_ERROR("HashMap insert elem failed: alloc memory failed.\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
elem->key = key;
|
||||
elem->value = value;
|
||||
elem->next = map->elements[index];
|
||||
map->elements[index] = elem;
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return true;
|
||||
|
||||
fail:
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void*
|
||||
wasm_hash_map_find(HashMap *map, void *key)
|
||||
{
|
||||
uint32 index;
|
||||
HashMapElem *elem;
|
||||
void *value;
|
||||
|
||||
if (!map || !key) {
|
||||
LOG_ERROR("HashMap find elem failed: map or key is NULL.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_lock(map->lock);
|
||||
}
|
||||
|
||||
index = map->hash_func(key) % map->size;
|
||||
elem = map->elements[index];
|
||||
|
||||
while (elem) {
|
||||
if (map->key_equal_func(elem->key, key)) {
|
||||
value = elem->value;
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
elem = elem->next;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_hash_map_update(HashMap *map, void *key, void *value,
|
||||
void **p_old_value)
|
||||
{
|
||||
uint32 index;
|
||||
HashMapElem *elem;
|
||||
|
||||
if (!map || !key) {
|
||||
LOG_ERROR("HashMap update elem failed: map or key is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_lock(map->lock);
|
||||
}
|
||||
|
||||
index = map->hash_func(key) % map->size;
|
||||
elem = map->elements[index];
|
||||
|
||||
while (elem) {
|
||||
if (map->key_equal_func(elem->key, key)) {
|
||||
if (p_old_value)
|
||||
*p_old_value = elem->value;
|
||||
elem->value = value;
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
elem = elem->next;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_hash_map_remove(HashMap *map, void *key,
|
||||
void **p_old_key, void **p_old_value)
|
||||
{
|
||||
uint32 index;
|
||||
HashMapElem *elem, *prev;
|
||||
|
||||
if (!map || !key) {
|
||||
LOG_ERROR("HashMap remove elem failed: map or key is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_lock(map->lock);
|
||||
}
|
||||
|
||||
index = map->hash_func(key) % map->size;
|
||||
prev = elem = map->elements[index];
|
||||
|
||||
while (elem) {
|
||||
if (map->key_equal_func(elem->key, key)) {
|
||||
if (p_old_key)
|
||||
*p_old_key = elem->key;
|
||||
if (p_old_value)
|
||||
*p_old_value = elem->value;
|
||||
|
||||
if (elem == map->elements[index])
|
||||
map->elements[index] = elem->next;
|
||||
else
|
||||
prev->next = elem->next;
|
||||
|
||||
wasm_free(elem);
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
prev = elem;
|
||||
elem = elem->next;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_hash_map_destroy(HashMap *map)
|
||||
{
|
||||
uint32 index;
|
||||
HashMapElem *elem, *next;
|
||||
|
||||
if (!map) {
|
||||
LOG_ERROR("HashMap destroy failed: map is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_lock(map->lock);
|
||||
}
|
||||
|
||||
for (index = 0; index < map->size; index++) {
|
||||
elem = map->elements[index];
|
||||
while (elem) {
|
||||
next = elem->next;
|
||||
|
||||
if (map->key_destroy_func) {
|
||||
map->key_destroy_func(elem->key);
|
||||
}
|
||||
if (map->value_destroy_func) {
|
||||
map->value_destroy_func(elem->value);
|
||||
}
|
||||
wasm_free(elem);
|
||||
|
||||
elem = next;
|
||||
}
|
||||
}
|
||||
|
||||
if (map->lock) {
|
||||
ws_mutex_unlock(map->lock);
|
||||
ws_mutex_destroy(map->lock);
|
||||
}
|
||||
wasm_free(map);
|
||||
return true;
|
||||
}
|
||||
102
core/iwasm/runtime/utils/wasm_log.c
Normal file
102
core/iwasm/runtime/utils/wasm_log.c
Normal file
@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_log.h"
|
||||
|
||||
#include "wasm_platform_log.h"
|
||||
#include "wasm_thread.h"
|
||||
|
||||
|
||||
/**
|
||||
* The verbose level of the log system. Only those verbose logs whose
|
||||
* levels are less than or equal to this value are outputed.
|
||||
*/
|
||||
static int log_verbose_level;
|
||||
|
||||
/**
|
||||
* The lock for protecting the global output stream of logs.
|
||||
*/
|
||||
static korp_mutex log_stream_lock;
|
||||
|
||||
|
||||
int
|
||||
_wasm_log_init ()
|
||||
{
|
||||
log_verbose_level = 1;
|
||||
return ws_mutex_init (&log_stream_lock, false);
|
||||
}
|
||||
|
||||
void
|
||||
_wasm_log_set_verbose_level (int level)
|
||||
{
|
||||
log_verbose_level = level;
|
||||
}
|
||||
|
||||
bool
|
||||
_wasm_log_begin (int level)
|
||||
{
|
||||
korp_tid self;
|
||||
|
||||
if (level > log_verbose_level) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Try to own the log stream and start the log output. */
|
||||
ws_mutex_lock (&log_stream_lock);
|
||||
self = ws_self_thread ();
|
||||
wasm_printf ("[%X]: ", (int)self);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
_wasm_log_vprintf (const char *fmt, va_list ap)
|
||||
{
|
||||
wasm_vprintf (fmt, ap);
|
||||
}
|
||||
|
||||
void
|
||||
_wasm_log_printf (const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
va_start (ap, fmt);
|
||||
_wasm_log_vprintf (fmt, ap);
|
||||
va_end (ap);
|
||||
}
|
||||
|
||||
void
|
||||
_wasm_log_end ()
|
||||
{
|
||||
ws_mutex_unlock (&log_stream_lock);
|
||||
}
|
||||
|
||||
void
|
||||
_wasm_log (int level, const char *file, int line,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
if (_wasm_log_begin (level)) {
|
||||
va_list ap;
|
||||
|
||||
if (file)
|
||||
_wasm_log_printf ("%s:%d ", file, line);
|
||||
|
||||
va_start (ap, fmt);
|
||||
_wasm_log_vprintf (fmt, ap);
|
||||
va_end (ap);
|
||||
|
||||
_wasm_log_end ();
|
||||
}
|
||||
}
|
||||
217
core/iwasm/runtime/utils/wasm_vector.c
Normal file
217
core/iwasm/runtime/utils/wasm_vector.c
Normal file
@ -0,0 +1,217 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_vector.h"
|
||||
#include "wasm_memory.h"
|
||||
|
||||
|
||||
static uint8*
|
||||
alloc_vector_data(uint32 length, uint32 size_elem)
|
||||
{
|
||||
uint64 total_size = ((uint64)size_elem) * length;
|
||||
uint8 *data;
|
||||
|
||||
if (total_size > UINT32_MAX) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((data = wasm_malloc((uint32)total_size))) {
|
||||
memset(data, 0, (uint32)total_size);
|
||||
}
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
static bool
|
||||
extend_vector(Vector *vector, uint32 length)
|
||||
{
|
||||
uint8 *data;
|
||||
|
||||
if (length <= vector->max_elements)
|
||||
return true;
|
||||
|
||||
if (length < vector->size_elem * 3 / 2)
|
||||
length = vector->size_elem * 3 / 2;
|
||||
|
||||
if (!(data = alloc_vector_data(length, vector->size_elem))) {
|
||||
return false;
|
||||
}
|
||||
|
||||
memcpy(data, vector->data, vector->size_elem * vector->max_elements);
|
||||
free(vector->data);
|
||||
vector->data = data;
|
||||
vector->max_elements = length;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_vector_init(Vector *vector, uint32 init_length, uint32 size_elem)
|
||||
{
|
||||
if (!vector) {
|
||||
LOG_ERROR("Init vector failed: vector is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (init_length == 0) {
|
||||
init_length = 4;
|
||||
}
|
||||
|
||||
if (!(vector->data = alloc_vector_data(init_length, size_elem))) {
|
||||
LOG_ERROR("Init vector failed: alloc memory failed.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
vector->size_elem = size_elem;
|
||||
vector->max_elements = init_length;
|
||||
vector->num_elements = 0;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_vector_set(Vector *vector, uint32 index, const void *elem_buf)
|
||||
{
|
||||
if (!vector || !elem_buf) {
|
||||
LOG_ERROR("Set vector elem failed: vector or elem buf is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index >= vector->num_elements) {
|
||||
LOG_ERROR("Set vector elem failed: invalid elem index.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
memcpy(vector->data + vector->size_elem * index,
|
||||
elem_buf, vector->size_elem);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool wasm_vector_get(const Vector *vector, uint32 index, void *elem_buf)
|
||||
{
|
||||
if (!vector || !elem_buf) {
|
||||
LOG_ERROR("Get vector elem failed: vector or elem buf is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index >= vector->num_elements) {
|
||||
LOG_ERROR("Get vector elem failed: invalid elem index.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
memcpy(elem_buf, vector->data + vector->size_elem * index,
|
||||
vector->size_elem);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool wasm_vector_insert(Vector *vector, uint32 index, const void *elem_buf)
|
||||
{
|
||||
uint32 i;
|
||||
uint8 *p;
|
||||
|
||||
if (!vector || !elem_buf) {
|
||||
LOG_ERROR("Insert vector elem failed: vector or elem buf is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index >= vector->num_elements) {
|
||||
LOG_ERROR("Insert vector elem failed: invalid elem index.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!extend_vector(vector, vector->num_elements + 1)) {
|
||||
LOG_ERROR("Insert vector elem failed: extend vector failed.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
p = vector->data + vector->size_elem * vector->num_elements;
|
||||
for (i = vector->num_elements - 1; i > index; i--) {
|
||||
memcpy(p, p - vector->size_elem, vector->size_elem);
|
||||
p -= vector->size_elem;
|
||||
}
|
||||
|
||||
memcpy(p, elem_buf, vector->size_elem);
|
||||
vector->num_elements++;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool wasm_vector_append(Vector *vector, const void *elem_buf)
|
||||
{
|
||||
if (!vector || !elem_buf) {
|
||||
LOG_ERROR("Append vector elem failed: vector or elem buf is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!extend_vector(vector, vector->num_elements + 1)) {
|
||||
LOG_ERROR("Append ector elem failed: extend vector failed.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
memcpy(vector->data + vector->size_elem * vector->num_elements,
|
||||
elem_buf, vector->size_elem);
|
||||
vector->num_elements++;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_vector_remove(Vector *vector, uint32 index, void *old_elem_buf)
|
||||
{
|
||||
uint32 i;
|
||||
uint8 *p;
|
||||
|
||||
if (!vector) {
|
||||
LOG_ERROR("Remove vector elem failed: vector is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index >= vector->num_elements) {
|
||||
LOG_ERROR("Remove vector elem failed: invalid elem index.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
p = vector->data + vector->size_elem * index;
|
||||
|
||||
if (old_elem_buf) {
|
||||
memcpy(old_elem_buf, p, vector->size_elem);
|
||||
}
|
||||
|
||||
for (i = index; i < vector->num_elements - 1; i++) {
|
||||
memcpy(p, p + vector->size_elem, vector->size_elem);
|
||||
p += vector->size_elem;
|
||||
}
|
||||
|
||||
vector->num_elements--;
|
||||
return true;
|
||||
}
|
||||
|
||||
uint32
|
||||
wasm_vector_size(const Vector *vector)
|
||||
{
|
||||
return vector ? vector->num_elements : 0;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_vector_destroy(Vector *vector)
|
||||
{
|
||||
if (!vector) {
|
||||
LOG_ERROR("Destroy vector elem failed: vector is NULL.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (vector->data)
|
||||
wasm_free(vector->data);
|
||||
memset(vector, 0, sizeof(Vector));
|
||||
return true;
|
||||
}
|
||||
92
core/iwasm/runtime/vmcore_wasm/invokeNative_general.c
Normal file
92
core/iwasm/runtime/vmcore_wasm/invokeNative_general.c
Normal file
@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "wasm-runtime.h"
|
||||
|
||||
void invokeNative(uint32 argv[], uint32 argc, void (*native_code)())
|
||||
{
|
||||
WASMThread *self;
|
||||
switch(argc) {
|
||||
case 0:
|
||||
native_code();
|
||||
break;
|
||||
case 1:
|
||||
native_code(argv[0]);
|
||||
break;
|
||||
case 2:
|
||||
native_code(argv[0], argv[1]);
|
||||
break;
|
||||
case 3:
|
||||
native_code(argv[0], argv[1], argv[2]);
|
||||
break;
|
||||
case 4:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3]);
|
||||
break;
|
||||
case 5:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4]);
|
||||
break;
|
||||
case 6:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5]);
|
||||
break;
|
||||
case 7:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6]);
|
||||
break;
|
||||
case 8:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7]);
|
||||
break;
|
||||
case 9:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8]);
|
||||
break;
|
||||
case 10:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9]);
|
||||
break;
|
||||
case 11:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10]);
|
||||
break;
|
||||
case 12:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11]);
|
||||
break;
|
||||
case 13:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12]);
|
||||
break;
|
||||
case 14:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13]);
|
||||
break;
|
||||
case 15:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14]);
|
||||
break;
|
||||
case 16:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14], argv[15]);
|
||||
break;
|
||||
case 17:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14], argv[15], argv[16]);
|
||||
break;
|
||||
case 18:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14], argv[15], argv[16], argv[17]);
|
||||
break;
|
||||
case 19:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14], argv[15], argv[16], argv[17], argv[18]);
|
||||
break;
|
||||
case 20:
|
||||
native_code(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5], argv[6], argv[7], argv[8], argv[9], argv[10], argv[11], argv[12], argv[13], argv[14], argv[15], argv[16], argv[17], argv[18], argv[19]);
|
||||
break;
|
||||
default:
|
||||
/* FIXME: If this happen, add more cases. */
|
||||
self = wasm_runtime_get_self();
|
||||
wasm_runtime_set_exception(self->module_inst, "the argument number of native function exceeds maximum");
|
||||
return;
|
||||
}
|
||||
}
|
||||
56
core/iwasm/runtime/vmcore_wasm/invokeNative_ia32.s
Normal file
56
core/iwasm/runtime/vmcore_wasm/invokeNative_ia32.s
Normal file
@ -0,0 +1,56 @@
|
||||
// Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
// contributor license agreements. See the NOTICE file distributed with
|
||||
// this work for additional information regarding copyright ownership.
|
||||
// The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
// (the "License"); you may not use this file except in compliance with
|
||||
// the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
// Author: Ivan Volosyuk
|
||||
//
|
||||
.text
|
||||
.align 2
|
||||
.globl invokeNative
|
||||
.type invokeNative, @function
|
||||
invokeNative:
|
||||
|
||||
push %ebp
|
||||
movl %esp, %ebp
|
||||
push %ecx
|
||||
movl 8(%ebp), %eax /* eax = argv */
|
||||
movl 12(%ebp), %ecx /* ecx = argc */
|
||||
test %ecx, %ecx
|
||||
je restore_ecx /* if ecx == 0, skip pushing arguments */
|
||||
leal -4(%eax,%ecx,4), %eax /* eax = eax + ecx * 4 - 4 */
|
||||
subl %esp, %eax /* eax = eax - esp */
|
||||
1:
|
||||
push 0(%esp,%eax)
|
||||
loop 1b /* loop ecx counts */
|
||||
restore_ecx:
|
||||
movl -4(%ebp), %ecx /* restore ecx */
|
||||
movl 16(%ebp), %eax /* eax = func_ptr */
|
||||
call *%eax
|
||||
leave
|
||||
ret
|
||||
|
||||
28
core/iwasm/runtime/vmcore_wasm/vmcore.cmake
Normal file
28
core/iwasm/runtime/vmcore_wasm/vmcore.cmake
Normal file
@ -0,0 +1,28 @@
|
||||
# Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
set (VMCORE_LIB_DIR ${CMAKE_CURRENT_LIST_DIR})
|
||||
|
||||
include_directories(${VMCORE_LIB_DIR})
|
||||
include_directories(${VMCORE_LIB_DIR}/../include)
|
||||
|
||||
if (${BUILD_AS_64BIT_SUPPORT} STREQUAL "YES")
|
||||
file (GLOB_RECURSE source_all ${VMCORE_LIB_DIR}/*.c)
|
||||
else ()
|
||||
file (GLOB_RECURSE source_all ${VMCORE_LIB_DIR}/*.c ${VMCORE_LIB_DIR}/*.s)
|
||||
list (REMOVE_ITEM source_all ${VMCORE_LIB_DIR}/invokeNative_general.c)
|
||||
endif ()
|
||||
|
||||
set (VMCORE_LIB_SOURCE ${source_all})
|
||||
|
||||
390
core/iwasm/runtime/vmcore_wasm/wasm-application.c
Normal file
390
core/iwasm/runtime/vmcore_wasm/wasm-application.c
Normal file
@ -0,0 +1,390 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "wasm.h"
|
||||
#include "wasm-interp.h"
|
||||
#include "wasm-runtime.h"
|
||||
#include "wasm-thread.h"
|
||||
#include "wasm_assert.h"
|
||||
#include "wasm_log.h"
|
||||
#include "wasm_memory.h"
|
||||
#include "wasm_platform_log.h"
|
||||
|
||||
|
||||
static WASMFunctionInstance*
|
||||
resolve_main_function(const WASMModuleInstance *module_inst)
|
||||
{
|
||||
uint32 i;
|
||||
for (i = 0; i < module_inst->export_func_count; i++)
|
||||
if (!strcmp(module_inst->export_functions[i].name, "_main")
|
||||
|| !strcmp(module_inst->export_functions[i].name, "main"))
|
||||
return module_inst->export_functions[i].function;
|
||||
|
||||
LOG_ERROR("WASM execute application failed: main function not found.\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static bool
|
||||
check_main_func_type(const WASMType *type)
|
||||
{
|
||||
if (!(type->param_count == 0 || type->param_count == 2)
|
||||
||type->result_count > 1) {
|
||||
LOG_ERROR("WASM execute application failed: invalid main function type.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (type->param_count == 2
|
||||
&& !(type->types[0] == VALUE_TYPE_I32
|
||||
&& type->types[1] == VALUE_TYPE_I32)) {
|
||||
LOG_ERROR("WASM execute application failed: invalid main function type.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (type->result_count
|
||||
&& type->types[type->param_count] != VALUE_TYPE_I32) {
|
||||
LOG_ERROR("WASM execute application failed: invalid main function type.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
wasm_application_execute_main(WASMModuleInstance *module_inst,
|
||||
int argc, char *argv[])
|
||||
{
|
||||
WASMFunctionInstance *func = resolve_main_function(module_inst);
|
||||
uint32 argc1 = 0, argv1[2] = { 0 };
|
||||
uint32 total_argv_size = 0, total_size;
|
||||
int32 argv_buf_offset, i;
|
||||
char *argv_buf, *p;
|
||||
int32 *argv_offsets;
|
||||
|
||||
if (!func || func->is_import_func)
|
||||
return false;
|
||||
|
||||
if (!check_main_func_type(func->u.func->func_type))
|
||||
return false;
|
||||
|
||||
if (func->u.func->func_type->param_count) {
|
||||
for (i = 0; i < argc; i++)
|
||||
total_argv_size += strlen(argv[i]) + 1;
|
||||
total_argv_size = align_uint(total_argv_size, 4);
|
||||
|
||||
total_size = total_argv_size + sizeof(int32) * argc;
|
||||
|
||||
if (!(argv_buf_offset = wasm_runtime_module_malloc(module_inst, total_size)))
|
||||
return false;
|
||||
|
||||
argv_buf = p = wasm_runtime_addr_app_to_native(module_inst, argv_buf_offset);
|
||||
argv_offsets = (int32*)(p + total_argv_size);
|
||||
|
||||
for (i = 0; i < argc; i++) {
|
||||
memcpy(p, argv[i], strlen(argv[i]) + 1);
|
||||
argv_offsets[i] = argv_buf_offset + (p - argv_buf);
|
||||
p += strlen(argv[i]) + 1;
|
||||
}
|
||||
|
||||
argc1 = 2;
|
||||
argv1[0] = argc;
|
||||
argv1[1] = (uint32)wasm_runtime_addr_native_to_app(module_inst, argv_offsets);
|
||||
}
|
||||
|
||||
return wasm_runtime_call_wasm(module_inst, NULL, func, argc1, argv1);
|
||||
}
|
||||
|
||||
static WASMFunctionInstance*
|
||||
resolve_function(const WASMModuleInstance *module_inst, char *name)
|
||||
{
|
||||
uint32 i;
|
||||
for (i = 0; i < module_inst->export_func_count; i++)
|
||||
if (!strcmp(module_inst->export_functions[i].name, name))
|
||||
return module_inst->export_functions[i].function;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
union ieee754_float {
|
||||
float f;
|
||||
|
||||
/* This is the IEEE 754 single-precision format. */
|
||||
union {
|
||||
struct {
|
||||
unsigned int negative:1;
|
||||
unsigned int exponent:8;
|
||||
unsigned int mantissa:23;
|
||||
} ieee_big_endian;
|
||||
struct {
|
||||
unsigned int mantissa:23;
|
||||
unsigned int exponent:8;
|
||||
unsigned int negative:1;
|
||||
} ieee_little_endian;
|
||||
} ieee;
|
||||
};
|
||||
|
||||
union ieee754_double {
|
||||
double d;
|
||||
|
||||
/* This is the IEEE 754 double-precision format. */
|
||||
union {
|
||||
struct {
|
||||
unsigned int negative:1;
|
||||
unsigned int exponent:11;
|
||||
/* Together these comprise the mantissa. */
|
||||
unsigned int mantissa0:20;
|
||||
unsigned int mantissa1:32;
|
||||
} ieee_big_endian;
|
||||
|
||||
struct {
|
||||
/* Together these comprise the mantissa. */
|
||||
unsigned int mantissa1:32;
|
||||
unsigned int mantissa0:20;
|
||||
unsigned int exponent:11;
|
||||
unsigned int negative:1;
|
||||
} ieee_little_endian;
|
||||
} ieee;
|
||||
};
|
||||
|
||||
bool
|
||||
wasm_application_execute_func(WASMModuleInstance *module_inst,
|
||||
char *name, int argc, char *argv[])
|
||||
{
|
||||
WASMFunctionInstance *func;
|
||||
WASMType *type;
|
||||
uint32 argc1, *argv1;
|
||||
int32 i, p;
|
||||
const char *exception;
|
||||
|
||||
wasm_assert(argc >= 0);
|
||||
func = resolve_function(module_inst, name);
|
||||
if (!func || func->is_import_func) {
|
||||
LOG_ERROR("Wasm lookup function %s failed.\n", name);
|
||||
return false;
|
||||
}
|
||||
|
||||
type = func->u.func->func_type;
|
||||
if (type->param_count != (uint32)argc) {
|
||||
LOG_ERROR("Wasm prepare param failed: invalid param count.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
argc1 = func->param_cell_num;
|
||||
argv1 = wasm_malloc(sizeof(uint32) * (argc1 > 2 ? argc1 : 2));
|
||||
if (argv1 == NULL) {
|
||||
LOG_ERROR("Wasm prepare param failed: malloc failed.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Parse arguments */
|
||||
for (i = 0, p = 0; i < argc; i++) {
|
||||
char *endptr;
|
||||
wasm_assert(argv[i] != NULL);
|
||||
if (argv[i][0] == '\0') {
|
||||
LOG_ERROR("Wasm prepare param failed: invalid num (%s).\n", argv[i]);
|
||||
goto fail;
|
||||
}
|
||||
switch (type->types[i]) {
|
||||
case VALUE_TYPE_I32:
|
||||
argv1[p++] = strtoul(argv[i], &endptr, 0);
|
||||
break;
|
||||
case VALUE_TYPE_I64:
|
||||
{
|
||||
union { uint64 val; uint32 parts[2]; } u;
|
||||
u.val = strtoull(argv[i], &endptr, 0);
|
||||
argv1[p++] = u.parts[0];
|
||||
argv1[p++] = u.parts[1];
|
||||
break;
|
||||
}
|
||||
case VALUE_TYPE_F32:
|
||||
{
|
||||
float32 f32 = strtof(argv[i], &endptr);
|
||||
if (isnan(f32)) {
|
||||
if (argv[i][0] == '-') {
|
||||
f32 = -f32;
|
||||
}
|
||||
if (endptr[0] == ':') {
|
||||
uint32 sig;
|
||||
union ieee754_float u;
|
||||
sig = strtoul(endptr + 1, &endptr, 0);
|
||||
u.f = f32;
|
||||
if (is_little_endian)
|
||||
u.ieee.ieee_little_endian.mantissa = sig;
|
||||
else
|
||||
u.ieee.ieee_big_endian.mantissa = sig;
|
||||
f32 = u.f;
|
||||
}
|
||||
}
|
||||
*(float32*)&argv1[p++] = f32;
|
||||
break;
|
||||
}
|
||||
case VALUE_TYPE_F64:
|
||||
{
|
||||
union { float64 val; uint32 parts[2]; } u;
|
||||
u.val = strtod(argv[i], &endptr);
|
||||
if (isnan(u.val)) {
|
||||
if (argv[i][0] == '-') {
|
||||
u.val = -u.val;
|
||||
}
|
||||
if (endptr[0] == ':') {
|
||||
uint64 sig;
|
||||
union ieee754_double ud;
|
||||
sig = strtoull(endptr + 1, &endptr, 0);
|
||||
ud.d = u.val;
|
||||
if (is_little_endian) {
|
||||
ud.ieee.ieee_little_endian.mantissa0 = sig >> 32;
|
||||
ud.ieee.ieee_little_endian.mantissa1 = sig;
|
||||
}
|
||||
else {
|
||||
ud.ieee.ieee_big_endian.mantissa0 = sig >> 32;
|
||||
ud.ieee.ieee_big_endian.mantissa1 = sig;
|
||||
}
|
||||
u.val = ud.d;
|
||||
}
|
||||
}
|
||||
argv1[p++] = u.parts[0];
|
||||
argv1[p++] = u.parts[1];
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (*endptr != '\0' && *endptr != '_') {
|
||||
LOG_ERROR("Wasm prepare param failed: invalid num (%s).\n", argv[i]);
|
||||
goto fail;
|
||||
}
|
||||
if (errno != 0) {
|
||||
LOG_ERROR("Wasm prepare param failed: errno %d.\n", errno);
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
wasm_assert(p == (int32)argc1);
|
||||
|
||||
wasm_runtime_set_exception(module_inst, NULL);
|
||||
if (!wasm_runtime_call_wasm(module_inst, NULL, func, argc1, argv1)) {
|
||||
exception = wasm_runtime_get_exception(module_inst);
|
||||
wasm_printf("%s\n", exception);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/* print return value */
|
||||
switch (type->types[type->param_count]) {
|
||||
case VALUE_TYPE_I32:
|
||||
wasm_printf("0x%x:i32", argv1[0]);
|
||||
break;
|
||||
case VALUE_TYPE_I64:
|
||||
{
|
||||
union { uint64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
wasm_printf("0x%llx:i64", u.val);
|
||||
break;
|
||||
}
|
||||
case VALUE_TYPE_F32:
|
||||
wasm_printf("%.7g:f32", *(float32*)argv1);
|
||||
break;
|
||||
case VALUE_TYPE_F64:
|
||||
{
|
||||
union { float64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
wasm_printf("%.7g:f64", u.val);
|
||||
break;
|
||||
}
|
||||
}
|
||||
wasm_printf("\n");
|
||||
|
||||
wasm_free(argv1);
|
||||
return true;
|
||||
|
||||
fail:
|
||||
wasm_free(argv1);
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool
|
||||
check_type(uint8 type, const char *p)
|
||||
{
|
||||
const char *str = "i32";
|
||||
|
||||
if (strlen(p) < 3)
|
||||
return false;
|
||||
|
||||
switch (type) {
|
||||
case VALUE_TYPE_I32:
|
||||
str = "i32";
|
||||
break;
|
||||
case VALUE_TYPE_I64:
|
||||
str = "i64";
|
||||
break;
|
||||
case VALUE_TYPE_F32:
|
||||
str = "f32";
|
||||
break;
|
||||
case VALUE_TYPE_F64:
|
||||
str = "f64";
|
||||
break;
|
||||
}
|
||||
if (strncmp(p, str, 3))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
check_function_type(const WASMType *type,
|
||||
const char *signature)
|
||||
{
|
||||
uint32 i;
|
||||
const char *p = signature;
|
||||
|
||||
if (!p || *p++ != '(')
|
||||
return false;
|
||||
|
||||
for (i = 0; i < type->param_count; i++) {
|
||||
if (!check_type(type->types[i], p))
|
||||
return false;
|
||||
p += 3;
|
||||
}
|
||||
|
||||
if (*p++ != ')')
|
||||
return false;
|
||||
|
||||
if (type->result_count) {
|
||||
if (!check_type(type->types[type->param_count], p))
|
||||
return false;
|
||||
p += 3;
|
||||
}
|
||||
|
||||
if (*p != '\0')
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
WASMFunctionInstance*
|
||||
wasm_runtime_lookup_function(const WASMModuleInstance *module_inst,
|
||||
const char *name,
|
||||
const char *signature)
|
||||
{
|
||||
uint32 i;
|
||||
for (i = 0; i < module_inst->export_func_count; i++)
|
||||
if (!strcmp(module_inst->export_functions[i].name, name)
|
||||
&& check_function_type(
|
||||
module_inst->export_functions[i].function->u.func->func_type,
|
||||
signature))
|
||||
return module_inst->export_functions[i].function;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
2160
core/iwasm/runtime/vmcore_wasm/wasm-interp.c
Normal file
2160
core/iwasm/runtime/vmcore_wasm/wasm-interp.c
Normal file
File diff suppressed because it is too large
Load Diff
79
core/iwasm/runtime/vmcore_wasm/wasm-interp.h
Normal file
79
core/iwasm/runtime/vmcore_wasm/wasm-interp.h
Normal file
@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_INTERP_H
|
||||
#define _WASM_INTERP_H
|
||||
|
||||
#include "wasm.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct WASMFunctionInstance;
|
||||
|
||||
typedef struct WASMInterpFrame {
|
||||
/* The frame of the caller that are calling the current function. */
|
||||
struct WASMInterpFrame *prev_frame;
|
||||
|
||||
/* The current WASM function. */
|
||||
struct WASMFunctionInstance *function;
|
||||
|
||||
/* Instruction pointer of the bytecode array. */
|
||||
uint8 *ip;
|
||||
|
||||
/* Operand stack top pointer of the current frame. The bottom of
|
||||
the stack is the next cell after the last local variable. */
|
||||
uint32 *sp_bottom;
|
||||
uint32 *sp_boundary;
|
||||
uint32 *sp;
|
||||
|
||||
WASMBranchBlock *csp_bottom;
|
||||
WASMBranchBlock *csp_boundary;
|
||||
WASMBranchBlock *csp;
|
||||
|
||||
/* Frame data, the layout is:
|
||||
lp: param_cell_count + local_cell_count
|
||||
sp_bottom to sp_boundary: stack of data
|
||||
csp_bottom to csp_boundary: stack of block
|
||||
ref to frame end: data types of local vairables and stack data
|
||||
*/
|
||||
uint32 lp[1];
|
||||
} WASMInterpFrame;
|
||||
|
||||
/**
|
||||
* Calculate the size of interpreter area of frame of a function.
|
||||
*
|
||||
* @param all_cell_num number of all cells including local variables
|
||||
* and the working stack slots
|
||||
*
|
||||
* @return the size of interpreter area of the frame
|
||||
*/
|
||||
static inline unsigned
|
||||
wasm_interp_interp_frame_size(unsigned all_cell_num)
|
||||
{
|
||||
return align_uint(offsetof(WASMInterpFrame, lp) + all_cell_num * 5, 4);
|
||||
}
|
||||
|
||||
void
|
||||
wasm_interp_call_wasm(struct WASMFunctionInstance *function,
|
||||
uint32 argc, uint32 argv[]);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_INTERP_H */
|
||||
2874
core/iwasm/runtime/vmcore_wasm/wasm-loader.c
Normal file
2874
core/iwasm/runtime/vmcore_wasm/wasm-loader.c
Normal file
File diff suppressed because it is too large
Load Diff
92
core/iwasm/runtime/vmcore_wasm/wasm-loader.h
Normal file
92
core/iwasm/runtime/vmcore_wasm/wasm-loader.h
Normal file
@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
#ifndef _WASM_LOADER_H
|
||||
#define _WASM_LOADER_H
|
||||
|
||||
#include "wasm.h"
|
||||
#include "wasm_hashmap.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Load a WASM module from a specified byte buffer.
|
||||
*
|
||||
* @param buf the byte buffer which contains the WASM binary data
|
||||
* @param size the size of the buffer
|
||||
* @param error_buf output of the exception info
|
||||
* @param error_buf_size the size of the exception string
|
||||
*
|
||||
* @return return module loaded, NULL if failed
|
||||
*/
|
||||
WASMModule*
|
||||
wasm_loader_load(const uint8 *buf, uint32 size, char *error_buf, uint32 error_buf_size);
|
||||
|
||||
/**
|
||||
* Load a WASM module from a specified WASM section list.
|
||||
*
|
||||
* @param section_list the section list which contains each section data
|
||||
* @param error_buf output of the exception info
|
||||
* @param error_buf_size the size of the exception string
|
||||
*
|
||||
* @return return WASM module loaded, NULL if failed
|
||||
*/
|
||||
WASMModule*
|
||||
wasm_loader_load_from_sections(WASMSection *section_list,
|
||||
char *error_buf, uint32_t error_buf_size);
|
||||
|
||||
/**
|
||||
* Unload a WASM module.
|
||||
*
|
||||
* @param module the module to be unloaded
|
||||
*/
|
||||
void
|
||||
wasm_loader_unload(WASMModule *module);
|
||||
|
||||
/**
|
||||
* Find address of related else opcode and end opcode of opcode block/loop/if
|
||||
* according to the start address of opcode.
|
||||
*
|
||||
* @param branch_set the hashtable to store the else/end adress info of
|
||||
* block/loop/if opcode. The function will lookup the hashtable firstly,
|
||||
* if not found, it will then search the code from start_addr, and if success,
|
||||
* stores the result to the hashtable.
|
||||
* @param start_addr the next address of opcode block/loop/if
|
||||
* @param code_end_addr the end address of function code block
|
||||
* @param block_type the type of block, 0/1/2 denotes block/loop/if
|
||||
* @param p_else_addr returns the else addr if found
|
||||
* @param p_end_addr returns the end addr if found
|
||||
* @param error_buf returns the error log for this function
|
||||
* @param error_buf_size returns the error log string length
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_loader_find_block_addr(HashMap *map,
|
||||
const uint8 *start_addr,
|
||||
const uint8 *code_end_addr,
|
||||
uint8 block_type,
|
||||
uint8 **p_else_addr,
|
||||
uint8 **p_end_addr,
|
||||
char *error_buf,
|
||||
uint32 error_buf_size);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_LOADER_H */
|
||||
66
core/iwasm/runtime/vmcore_wasm/wasm-native.h
Normal file
66
core/iwasm/runtime/vmcore_wasm/wasm-native.h
Normal file
@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_NATIVE_H
|
||||
#define _WASM_NATIVE_H
|
||||
|
||||
#include "wasm.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Initialize the native module, e.g. sort the function defs
|
||||
* and the global defs.
|
||||
*
|
||||
* @return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_native_init();
|
||||
|
||||
/**
|
||||
* Lookup native function implementation of a given import function.
|
||||
*
|
||||
* @param module_name the module name of the import function
|
||||
* @param func_name the function name of the import function
|
||||
*
|
||||
* @return return the native function pointer if success, NULL otherwise
|
||||
*/
|
||||
void*
|
||||
wasm_native_func_lookup(const char *module_name, const char *func_name);
|
||||
|
||||
/**
|
||||
* Lookup global variable of a given import global
|
||||
*
|
||||
* @param module_name the module name of the import global
|
||||
* @param global_name the global name of the import global
|
||||
* @param global return the global data
|
||||
*
|
||||
* @param return true if success, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_native_global_lookup(const char *module_name, const char *global_name,
|
||||
WASMGlobalImport *global);
|
||||
|
||||
void* wasm_platform_native_func_lookup(const char *module_name,
|
||||
const char *func_name);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_NATIVE_H */
|
||||
472
core/iwasm/runtime/vmcore_wasm/wasm-opcode.h
Normal file
472
core/iwasm/runtime/vmcore_wasm/wasm-opcode.h
Normal file
@ -0,0 +1,472 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_OPCODE_H
|
||||
#define _WASM_OPCODE_H
|
||||
|
||||
#include "wasm.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef enum WASMOpcode {
|
||||
/* control instructions */
|
||||
WASM_OP_UNREACHABLE = 0x00, /* unreachable */
|
||||
WASM_OP_NOP = 0x01, /* nop */
|
||||
WASM_OP_BLOCK = 0x02, /* block */
|
||||
WASM_OP_LOOP = 0x03, /* loop */
|
||||
WASM_OP_IF = 0x04, /* if */
|
||||
WASM_OP_ELSE = 0x05, /* else */
|
||||
|
||||
WASM_OP_UNUSED_0x06 = 0x06,
|
||||
WASM_OP_UNUSED_0x07 = 0x07,
|
||||
WASM_OP_UNUSED_0x08 = 0x08,
|
||||
WASM_OP_UNUSED_0x09 = 0x09,
|
||||
WASM_OP_UNUSED_0x0a = 0x0a,
|
||||
|
||||
WASM_OP_END = 0x0b, /* end */
|
||||
WASM_OP_BR = 0x0c, /* br */
|
||||
WASM_OP_BR_IF = 0x0d, /* br if */
|
||||
WASM_OP_BR_TABLE = 0x0e, /* br table */
|
||||
WASM_OP_RETURN = 0x0f, /* return */
|
||||
WASM_OP_CALL = 0x10, /* call */
|
||||
WASM_OP_CALL_INDIRECT = 0x11, /* call_indirect */
|
||||
|
||||
WASM_OP_UNUSED_0x12 = 0x12,
|
||||
WASM_OP_UNUSED_0x13 = 0x13,
|
||||
WASM_OP_UNUSED_0x14 = 0x14,
|
||||
WASM_OP_UNUSED_0x15 = 0x15,
|
||||
WASM_OP_UNUSED_0x16 = 0x16,
|
||||
WASM_OP_UNUSED_0x17 = 0x17,
|
||||
WASM_OP_UNUSED_0x18 = 0x18,
|
||||
WASM_OP_UNUSED_0x19 = 0x19,
|
||||
|
||||
/* parametric instructions */
|
||||
WASM_OP_DROP = 0x1a, /* drop */
|
||||
WASM_OP_SELECT = 0x1b, /* select */
|
||||
|
||||
WASM_OP_UNUSED_0x1c = 0x1c,
|
||||
WASM_OP_UNUSED_0x1d = 0x1d,
|
||||
WASM_OP_UNUSED_0x1e = 0x1e,
|
||||
WASM_OP_UNUSED_0x1f = 0x1f,
|
||||
|
||||
/* variable instructions */
|
||||
WASM_OP_GET_LOCAL = 0x20, /* get_local */
|
||||
WASM_OP_SET_LOCAL = 0x21, /* set_local */
|
||||
WASM_OP_TEE_LOCAL = 0x22, /* tee_local */
|
||||
WASM_OP_GET_GLOBAL = 0x23, /* get_global */
|
||||
WASM_OP_SET_GLOBAL = 0x24, /* set_global */
|
||||
|
||||
WASM_OP_UNUSED_0x25 = 0x25,
|
||||
WASM_OP_UNUSED_0x26 = 0x26,
|
||||
WASM_OP_UNUSED_0x27 = 0x27,
|
||||
|
||||
/* memory instructions */
|
||||
WASM_OP_I32_LOAD = 0x28, /* i32.load */
|
||||
WASM_OP_I64_LOAD = 0x29, /* i64.load */
|
||||
WASM_OP_F32_LOAD = 0x2a, /* f32.load */
|
||||
WASM_OP_F64_LOAD = 0x2b, /* f64.load */
|
||||
WASM_OP_I32_LOAD8_S = 0x2c, /* i32.load8_s */
|
||||
WASM_OP_I32_LOAD8_U = 0x2d, /* i32.load8_u */
|
||||
WASM_OP_I32_LOAD16_S = 0x2e, /* i32.load16_s */
|
||||
WASM_OP_I32_LOAD16_U = 0x2f, /* i32.load16_u */
|
||||
WASM_OP_I64_LOAD8_S = 0x30, /* i64.load8_s */
|
||||
WASM_OP_I64_LOAD8_U = 0x31, /* i64.load8_u */
|
||||
WASM_OP_I64_LOAD16_S = 0x32, /* i64.load16_s */
|
||||
WASM_OP_I64_LOAD16_U = 0x33, /* i64.load16_u */
|
||||
WASM_OP_I64_LOAD32_S = 0x34, /* i32.load32_s */
|
||||
WASM_OP_I64_LOAD32_U = 0x35, /* i32.load32_u */
|
||||
WASM_OP_I32_STORE = 0x36, /* i32.store */
|
||||
WASM_OP_I64_STORE = 0x37, /* i64.store */
|
||||
WASM_OP_F32_STORE = 0x38, /* f32.store */
|
||||
WASM_OP_F64_STORE = 0x39, /* f64.store */
|
||||
WASM_OP_I32_STORE8 = 0x3a, /* i32.store8 */
|
||||
WASM_OP_I32_STORE16 = 0x3b, /* i32.store16 */
|
||||
WASM_OP_I64_STORE8 = 0x3c, /* i64.store8 */
|
||||
WASM_OP_I64_STORE16 = 0x3d, /* i64.sotre16 */
|
||||
WASM_OP_I64_STORE32 = 0x3e, /* i64.store32 */
|
||||
WASM_OP_MEMORY_SIZE = 0x3f, /* memory.size */
|
||||
WASM_OP_MEMORY_GROW = 0x40, /* memory.grow */
|
||||
|
||||
/* constant instructions */
|
||||
WASM_OP_I32_CONST = 0x41, /* i32.const */
|
||||
WASM_OP_I64_CONST = 0x42, /* i64.const */
|
||||
WASM_OP_F32_CONST = 0x43, /* f32.const */
|
||||
WASM_OP_F64_CONST = 0x44, /* f64.const */
|
||||
|
||||
/* comparison instructions */
|
||||
WASM_OP_I32_EQZ = 0x45, /* i32.eqz */
|
||||
WASM_OP_I32_EQ = 0x46, /* i32.eq */
|
||||
WASM_OP_I32_NE = 0x47, /* i32.ne */
|
||||
WASM_OP_I32_LT_S = 0x48, /* i32.lt_s */
|
||||
WASM_OP_I32_LT_U = 0x49, /* i32.lt_u */
|
||||
WASM_OP_I32_GT_S = 0x4a, /* i32.gt_s */
|
||||
WASM_OP_I32_GT_U = 0x4b, /* i32.gt_u */
|
||||
WASM_OP_I32_LE_S = 0x4c, /* i32.le_s */
|
||||
WASM_OP_I32_LE_U = 0x4d, /* i32.le_u */
|
||||
WASM_OP_I32_GE_S = 0x4e, /* i32.ge_s */
|
||||
WASM_OP_I32_GE_U = 0x4f, /* i32.ge_u */
|
||||
|
||||
WASM_OP_I64_EQZ = 0x50, /* i64.eqz */
|
||||
WASM_OP_I64_EQ = 0x51, /* i64.eq */
|
||||
WASM_OP_I64_NE = 0x52, /* i64.ne */
|
||||
WASM_OP_I64_LT_S = 0x53, /* i64.lt_s */
|
||||
WASM_OP_I64_LT_U = 0x54, /* i64.lt_u */
|
||||
WASM_OP_I64_GT_S = 0x55, /* i64.gt_s */
|
||||
WASM_OP_I64_GT_U = 0x56, /* i64.gt_u */
|
||||
WASM_OP_I64_LE_S = 0x57, /* i64.le_s */
|
||||
WASM_OP_I64_LE_U = 0x58, /* i64.le_u */
|
||||
WASM_OP_I64_GE_S = 0x59, /* i64.ge_s */
|
||||
WASM_OP_I64_GE_U = 0x5a, /* i64.ge_u */
|
||||
|
||||
WASM_OP_F32_EQ = 0x5b, /* f32.eq */
|
||||
WASM_OP_F32_NE = 0x5c, /* f32.ne */
|
||||
WASM_OP_F32_LT = 0x5d, /* f32.lt */
|
||||
WASM_OP_F32_GT = 0x5e, /* f32.gt */
|
||||
WASM_OP_F32_LE = 0x5f, /* f32.le */
|
||||
WASM_OP_F32_GE = 0x60, /* f32.ge */
|
||||
|
||||
WASM_OP_F64_EQ = 0x61, /* f64.eq */
|
||||
WASM_OP_F64_NE = 0x62, /* f64.ne */
|
||||
WASM_OP_F64_LT = 0x63, /* f64.lt */
|
||||
WASM_OP_F64_GT = 0x64, /* f64.gt */
|
||||
WASM_OP_F64_LE = 0x65, /* f64.le */
|
||||
WASM_OP_F64_GE = 0x66, /* f64.ge */
|
||||
|
||||
/* numeric operators */
|
||||
WASM_OP_I32_CLZ = 0x67, /* i32.clz */
|
||||
WASM_OP_I32_CTZ = 0x68, /* i32.ctz */
|
||||
WASM_OP_I32_POPCNT = 0x69, /* i32.popcnt */
|
||||
WASM_OP_I32_ADD = 0x6a, /* i32.add */
|
||||
WASM_OP_I32_SUB = 0x6b, /* i32.sub */
|
||||
WASM_OP_I32_MUL = 0x6c, /* i32.mul */
|
||||
WASM_OP_I32_DIV_S = 0x6d, /* i32.div_s */
|
||||
WASM_OP_I32_DIV_U = 0x6e, /* i32.div_u */
|
||||
WASM_OP_I32_REM_S = 0x6f, /* i32.rem_s */
|
||||
WASM_OP_I32_REM_U = 0x70, /* i32.rem_u */
|
||||
WASM_OP_I32_AND = 0x71, /* i32.and */
|
||||
WASM_OP_I32_OR = 0x72, /* i32.or */
|
||||
WASM_OP_I32_XOR = 0x73, /* i32.xor */
|
||||
WASM_OP_I32_SHL = 0x74, /* i32.shl */
|
||||
WASM_OP_I32_SHR_S = 0x75, /* i32.shr_s */
|
||||
WASM_OP_I32_SHR_U = 0x76, /* i32.shr_u */
|
||||
WASM_OP_I32_ROTL = 0x77, /* i32.rotl */
|
||||
WASM_OP_I32_ROTR = 0x78, /* i32.rotr */
|
||||
|
||||
WASM_OP_I64_CLZ = 0x79, /* i64.clz */
|
||||
WASM_OP_I64_CTZ = 0x7a, /* i64.ctz */
|
||||
WASM_OP_I64_POPCNT = 0x7b, /* i64.popcnt */
|
||||
WASM_OP_I64_ADD = 0x7c, /* i64.add */
|
||||
WASM_OP_I64_SUB = 0x7d, /* i64.sub */
|
||||
WASM_OP_I64_MUL = 0x7e, /* i64.mul */
|
||||
WASM_OP_I64_DIV_S = 0x7f, /* i64.div_s */
|
||||
WASM_OP_I64_DIV_U = 0x80, /* i64.div_u */
|
||||
WASM_OP_I64_REM_S = 0x81, /* i64.rem_s */
|
||||
WASM_OP_I64_REM_U = 0x82, /* i64.rem_u */
|
||||
WASM_OP_I64_AND = 0x83, /* i64.and */
|
||||
WASM_OP_I64_OR = 0x84, /* i64.or */
|
||||
WASM_OP_I64_XOR = 0x85, /* i64.xor */
|
||||
WASM_OP_I64_SHL = 0x86, /* i64.shl */
|
||||
WASM_OP_I64_SHR_S = 0x87, /* i64.shr_s */
|
||||
WASM_OP_I64_SHR_U = 0x88, /* i64.shr_u */
|
||||
WASM_OP_I64_ROTL = 0x89, /* i64.rotl */
|
||||
WASM_OP_I64_ROTR = 0x8a, /* i64.rotr */
|
||||
|
||||
WASM_OP_F32_ABS = 0x8b, /* f32.abs */
|
||||
WASM_OP_F32_NEG = 0x8c, /* f32.neg */
|
||||
WASM_OP_F32_CEIL = 0x8d, /* f32.ceil */
|
||||
WASM_OP_F32_FLOOR = 0x8e, /* f32.floor */
|
||||
WASM_OP_F32_TRUNC = 0x8f, /* f32.trunc */
|
||||
WASM_OP_F32_NEAREST = 0x90, /* f32.nearest */
|
||||
WASM_OP_F32_SQRT = 0x91, /* f32.sqrt */
|
||||
WASM_OP_F32_ADD = 0x92, /* f32.add */
|
||||
WASM_OP_F32_SUB = 0x93, /* f32.sub */
|
||||
WASM_OP_F32_MUL = 0x94, /* f32.mul */
|
||||
WASM_OP_F32_DIV = 0x95, /* f32.div */
|
||||
WASM_OP_F32_MIN = 0x96, /* f32.min */
|
||||
WASM_OP_F32_MAX = 0x97, /* f32.max */
|
||||
WASM_OP_F32_COPYSIGN = 0x98, /* f32.copysign */
|
||||
|
||||
WASM_OP_F64_ABS = 0x99, /* f64.abs */
|
||||
WASM_OP_F64_NEG = 0x9a, /* f64.neg */
|
||||
WASM_OP_F64_CEIL = 0x9b, /* f64.ceil */
|
||||
WASM_OP_F64_FLOOR = 0x9c, /* f64.floor */
|
||||
WASM_OP_F64_TRUNC = 0x9d, /* f64.trunc */
|
||||
WASM_OP_F64_NEAREST = 0x9e, /* f64.nearest */
|
||||
WASM_OP_F64_SQRT = 0x9f, /* f64.sqrt */
|
||||
WASM_OP_F64_ADD = 0xa0, /* f64.add */
|
||||
WASM_OP_F64_SUB = 0xa1, /* f64.sub */
|
||||
WASM_OP_F64_MUL = 0xa2, /* f64.mul */
|
||||
WASM_OP_F64_DIV = 0xa3, /* f64.div */
|
||||
WASM_OP_F64_MIN = 0xa4, /* f64.min */
|
||||
WASM_OP_F64_MAX = 0xa5, /* f64.max */
|
||||
WASM_OP_F64_COPYSIGN = 0xa6, /* f64.copysign */
|
||||
|
||||
/* conversions */
|
||||
WASM_OP_I32_WRAP_I64 = 0xa7, /* i32.wrap/i64 */
|
||||
WASM_OP_I32_TRUNC_S_F32 = 0xa8, /* i32.trunc_s/f32 */
|
||||
WASM_OP_I32_TRUNC_U_F32 = 0xa9, /* i32.trunc_u/f32 */
|
||||
WASM_OP_I32_TRUNC_S_F64 = 0xaa, /* i32.trunc_s/f64 */
|
||||
WASM_OP_I32_TRUNC_U_F64 = 0xab, /* i32.trunc_u/f64 */
|
||||
|
||||
WASM_OP_I64_EXTEND_S_I32 = 0xac, /* i64.extend_s/i32 */
|
||||
WASM_OP_I64_EXTEND_U_I32 = 0xad, /* i64.extend_u/i32 */
|
||||
WASM_OP_I64_TRUNC_S_F32 = 0xae, /* i64.trunc_s/f32 */
|
||||
WASM_OP_I64_TRUNC_U_F32 = 0xaf, /* i64.trunc_u/f32 */
|
||||
WASM_OP_I64_TRUNC_S_F64 = 0xb0, /* i64.trunc_s/f64 */
|
||||
WASM_OP_I64_TRUNC_U_F64 = 0xb1, /* i64.trunc_u/f64 */
|
||||
|
||||
WASM_OP_F32_CONVERT_S_I32 = 0xb2, /* f32.convert_s/i32 */
|
||||
WASM_OP_F32_CONVERT_U_I32 = 0xb3, /* f32.convert_u/i32 */
|
||||
WASM_OP_F32_CONVERT_S_I64 = 0xb4, /* f32.convert_s/i64 */
|
||||
WASM_OP_F32_CONVERT_U_I64 = 0xb5, /* f32.convert_u/i64 */
|
||||
WASM_OP_F32_DEMOTE_F64 = 0xb6, /* f32.demote/f64 */
|
||||
|
||||
WASM_OP_F64_CONVERT_S_I32 = 0xb7, /* f64.convert_s/i32 */
|
||||
WASM_OP_F64_CONVERT_U_I32 = 0xb8, /* f64.convert_u/i32 */
|
||||
WASM_OP_F64_CONVERT_S_I64 = 0xb9, /* f64.convert_s/i64 */
|
||||
WASM_OP_F64_CONVERT_U_I64 = 0xba, /* f64.convert_u/i64 */
|
||||
WASM_OP_F64_PROMOTE_F32 = 0xbb, /* f64.promote/f32 */
|
||||
|
||||
/* reinterpretations */
|
||||
WASM_OP_I32_REINTERPRET_F32 = 0xbc, /* i32.reinterpret/f32 */
|
||||
WASM_OP_I64_REINTERPRET_F64 = 0xbd, /* i64.reinterpret/f64 */
|
||||
WASM_OP_F32_REINTERPRET_I32 = 0xbe, /* f32.reinterpret/i32 */
|
||||
WASM_OP_F64_REINTERPRET_I64 = 0xbf, /* f64.reinterpret/i64 */
|
||||
|
||||
/* drop/select specified types*/
|
||||
WASM_OP_DROP_32 = 0xc0,
|
||||
WASM_OP_DROP_64 = 0xc1,
|
||||
WASM_OP_SELECT_32 = 0xc2,
|
||||
WASM_OP_SELECT_64 = 0xc3,
|
||||
|
||||
WASM_OP_IMPDEP1 = WASM_OP_SELECT_64 + 1,
|
||||
WASM_OP_IMPDEP2 = WASM_OP_IMPDEP1 + 1
|
||||
} WASMOpcode;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Macro used to generate computed goto tables for the C interpreter.
|
||||
*/
|
||||
#define WASM_INSTRUCTION_NUM 256
|
||||
|
||||
#define DEFINE_GOTO_TABLE(_name) \
|
||||
static const void *_name[WASM_INSTRUCTION_NUM] = { \
|
||||
HANDLE_OPCODE (WASM_OP_UNREACHABLE), /* 0x00 */ \
|
||||
HANDLE_OPCODE (WASM_OP_NOP), /* 0x01 */ \
|
||||
HANDLE_OPCODE (WASM_OP_BLOCK), /* 0x02 */ \
|
||||
HANDLE_OPCODE (WASM_OP_LOOP), /* 0x03 */ \
|
||||
HANDLE_OPCODE (WASM_OP_IF), /* 0x04 */ \
|
||||
HANDLE_OPCODE (WASM_OP_ELSE), /* 0x05 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x06), /* 0x06 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x07), /* 0x07 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x08), /* 0x08 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x09), /* 0x09 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x0a), /* 0x0a */ \
|
||||
HANDLE_OPCODE (WASM_OP_END), /* 0x0b */ \
|
||||
HANDLE_OPCODE (WASM_OP_BR), /* 0x0c */ \
|
||||
HANDLE_OPCODE (WASM_OP_BR_IF), /* 0x0d */ \
|
||||
HANDLE_OPCODE (WASM_OP_BR_TABLE), /* 0x0e */ \
|
||||
HANDLE_OPCODE (WASM_OP_RETURN), /* 0x0f */ \
|
||||
HANDLE_OPCODE (WASM_OP_CALL), /* 0x10 */ \
|
||||
HANDLE_OPCODE (WASM_OP_CALL_INDIRECT), /* 0x11 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x12), /* 0x12 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x13), /* 0x13 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x14), /* 0x14 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x15), /* 0x15 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x16), /* 0x16 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x17), /* 0x17 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x18), /* 0x18 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x19), /* 0x19 */ \
|
||||
HANDLE_OPCODE (WASM_OP_DROP), /* 0x1a */ \
|
||||
HANDLE_OPCODE (WASM_OP_SELECT), /* 0x1b */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x1c), /* 0x1c */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x1d), /* 0x1d */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x1e), /* 0x1e */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x1f), /* 0x1f */ \
|
||||
HANDLE_OPCODE (WASM_OP_GET_LOCAL), /* 0x20 */ \
|
||||
HANDLE_OPCODE (WASM_OP_SET_LOCAL), /* 0x21 */ \
|
||||
HANDLE_OPCODE (WASM_OP_TEE_LOCAL), /* 0x22 */ \
|
||||
HANDLE_OPCODE (WASM_OP_GET_GLOBAL), /* 0x23 */ \
|
||||
HANDLE_OPCODE (WASM_OP_SET_GLOBAL), /* 0x24 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x25), /* 0x25 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x26), /* 0x26 */ \
|
||||
HANDLE_OPCODE (WASM_OP_UNUSED_0x27), /* 0x27 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LOAD), /* 0x28 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD), /* 0x29 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_LOAD), /* 0x2a */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_LOAD), /* 0x2b */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LOAD8_S), /* 0x2c */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LOAD8_U), /* 0x2d */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LOAD16_S), /* 0x2e */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LOAD16_U), /* 0x2f */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD8_S), /* 0x30 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD8_U), /* 0x31 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD16_S), /* 0x32 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD16_U), /* 0x33 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD32_S), /* 0x34 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LOAD32_U), /* 0x35 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_STORE), /* 0x36 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_STORE), /* 0x37 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_STORE), /* 0x38 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_STORE), /* 0x39 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_STORE8), /* 0x3a */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_STORE16), /* 0x3b */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_STORE8), /* 0x3c */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_STORE16), /* 0x3d */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_STORE32), /* 0x3e */ \
|
||||
HANDLE_OPCODE (WASM_OP_MEMORY_SIZE), /* 0x3f */ \
|
||||
HANDLE_OPCODE (WASM_OP_MEMORY_GROW), /* 0x40 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_CONST), /* 0x41 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_CONST), /* 0x42 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CONST), /* 0x43 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CONST), /* 0x44 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_EQZ), /* 0x45 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_EQ), /* 0x46 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_NE), /* 0x47 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LT_S), /* 0x48 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LT_U), /* 0x49 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_GT_S), /* 0x4a */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_GT_U), /* 0x4b */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LE_S), /* 0x4c */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_LE_U), /* 0x4d */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_GE_S), /* 0x4e */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_GE_U), /* 0x4f */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_EQZ), /* 0x50 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_EQ), /* 0x51 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_NE), /* 0x52 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LT_S), /* 0x53 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LT_U), /* 0x54 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_GT_S), /* 0x55 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_GT_U), /* 0x56 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LE_S), /* 0x57 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_LE_U), /* 0x58 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_GE_S), /* 0x59 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_GE_U), /* 0x5a */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_EQ), /* 0x5b */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_NE), /* 0x5c */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_LT), /* 0x5d */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_GT), /* 0x5e */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_LE), /* 0x5f */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_GE), /* 0x60 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_EQ), /* 0x61 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_NE), /* 0x62 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_LT), /* 0x63 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_GT), /* 0x64 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_LE), /* 0x65 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_GE), /* 0x66 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_CLZ), /* 0x67 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_CTZ), /* 0x68 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_POPCNT), /* 0x69 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_ADD), /* 0x6a */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_SUB), /* 0x6b */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_MUL), /* 0x6c */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_DIV_S), /* 0x6d */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_DIV_U), /* 0x6e */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_REM_S), /* 0x6f */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_REM_U), /* 0x70 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_AND), /* 0x71 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_OR), /* 0x72 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_XOR), /* 0x73 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_SHL), /* 0x74 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_SHR_S), /* 0x75 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_SHR_U), /* 0x76 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_ROTL), /* 0x77 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_ROTR), /* 0x78 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_CLZ), /* 0x79 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_CTZ), /* 0x7a */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_POPCNT), /* 0x7b */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_ADD), /* 0x7c */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_SUB), /* 0x7d */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_MUL), /* 0x7e */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_DIV_S), /* 0x7f */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_DIV_U), /* 0x80 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_REM_S), /* 0x81 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_REM_U), /* 0x82 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_AND), /* 0x83 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_OR), /* 0x84 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_XOR), /* 0x85 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_SHL), /* 0x86 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_SHR_S), /* 0x87 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_SHR_U), /* 0x88 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_ROTL), /* 0x89 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_ROTR), /* 0x8a */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_ABS), /* 0x8b */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_NEG), /* 0x8c */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CEIL), /* 0x8d */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_FLOOR), /* 0x8e */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_TRUNC), /* 0x8f */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_NEAREST), /* 0x90 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_SQRT), /* 0x91 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_ADD), /* 0x92 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_SUB), /* 0x93 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_MUL), /* 0x94 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_DIV), /* 0x95 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_MIN), /* 0x96 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_MAX), /* 0x97 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_COPYSIGN), /* 0x98 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_ABS), /* 0x99 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_NEG), /* 0x9a */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CEIL), /* 0x9b */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_FLOOR), /* 0x9c */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_TRUNC), /* 0x9d */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_NEAREST), /* 0x9e */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_SQRT), /* 0x9f */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_ADD), /* 0xa0 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_SUB), /* 0xa1 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_MUL), /* 0xa2 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_DIV), /* 0xa3 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_MIN), /* 0xa4 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_MAX), /* 0xa5 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_COPYSIGN), /* 0xa6 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_WRAP_I64), /* 0xa7 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_TRUNC_S_F32), /* 0xa8 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_TRUNC_U_F32), /* 0xa9 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_TRUNC_S_F64), /* 0xaa */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_TRUNC_U_F64), /* 0xab */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_EXTEND_S_I32), /* 0xac */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_EXTEND_U_I32), /* 0xad */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_TRUNC_S_F32), /* 0xae */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_TRUNC_U_F32), /* 0xaf */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_TRUNC_S_F64), /* 0xb0 */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_TRUNC_U_F64), /* 0xb1 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CONVERT_S_I32), /* 0xb2 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CONVERT_U_I32), /* 0xb3 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CONVERT_S_I64), /* 0xb4 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_CONVERT_U_I64), /* 0xb5 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_DEMOTE_F64), /* 0xb6 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CONVERT_S_I32), /* 0xb7 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CONVERT_U_I32), /* 0xb8 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CONVERT_S_I64), /* 0xb9 */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_CONVERT_U_I64), /* 0xba */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_PROMOTE_F32), /* 0xbb */ \
|
||||
HANDLE_OPCODE (WASM_OP_I32_REINTERPRET_F32), /* 0xbc */ \
|
||||
HANDLE_OPCODE (WASM_OP_I64_REINTERPRET_F64), /* 0xbd */ \
|
||||
HANDLE_OPCODE (WASM_OP_F32_REINTERPRET_I32), /* 0xbe */ \
|
||||
HANDLE_OPCODE (WASM_OP_F64_REINTERPRET_I64), /* 0xbf */ \
|
||||
HANDLE_OPCODE (WASM_OP_DROP_32), /* 0xc0 */ \
|
||||
HANDLE_OPCODE (WASM_OP_DROP_64), /* 0xc1 */ \
|
||||
HANDLE_OPCODE (WASM_OP_SELECT_32), /* 0xc2 */ \
|
||||
HANDLE_OPCODE (WASM_OP_SELECT_64), /* 0xc3 */ \
|
||||
HANDLE_OPCODE (WASM_OP_IMPDEP1), /* 0xc4 */ \
|
||||
HANDLE_OPCODE (WASM_OP_IMPDEP2), /* 0xc5 */ \
|
||||
}
|
||||
|
||||
#endif /* end of _WASM_OPCODE_H */
|
||||
1220
core/iwasm/runtime/vmcore_wasm/wasm-runtime.c
Normal file
1220
core/iwasm/runtime/vmcore_wasm/wasm-runtime.c
Normal file
File diff suppressed because it is too large
Load Diff
328
core/iwasm/runtime/vmcore_wasm/wasm-runtime.h
Normal file
328
core/iwasm/runtime/vmcore_wasm/wasm-runtime.h
Normal file
@ -0,0 +1,328 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_RUNTIME_H
|
||||
#define _WASM_RUNTIME_H
|
||||
|
||||
#include "wasm.h"
|
||||
#include "wasm-thread.h"
|
||||
#include "wasm_hashmap.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
#define DEFAULT_WASM_STACK_SIZE (8 * 1024)
|
||||
#define DEFAULT_WASM_HEAP_SIZE (8 * 1024)
|
||||
#define MIN_WASM_HEAP_SIZE (1 * 1024)
|
||||
|
||||
typedef struct WASMMemoryInstance {
|
||||
/* Current page count */
|
||||
uint32 cur_page_count;
|
||||
/* Maximum page count */
|
||||
uint32 max_page_count;
|
||||
/* Data of import globals with address info, like _stdin/_stdout/_stderr,
|
||||
stdin/stdout/stderr is stored here, but the actual addr info, or offset
|
||||
to memory_data is stored in global_data section */
|
||||
uint8 *addr_data;
|
||||
/* Size of addr_data */
|
||||
uint32 addr_data_size;
|
||||
|
||||
/* Thunk data of argument strings */
|
||||
uint8 *thunk_argv_data;
|
||||
uint32 thunk_argv_data_size;
|
||||
/* Thunk argument count */
|
||||
uint32 thunk_argc;
|
||||
/* Thunk argument offsets */
|
||||
uint8 *thunk_argv_offsets;
|
||||
|
||||
/* Heap data */
|
||||
uint8 *heap_data;
|
||||
/* Heap size */
|
||||
uint32 heap_data_size;
|
||||
/* The heap created */
|
||||
void *heap_handle;
|
||||
|
||||
/* Memory data */
|
||||
uint8 *memory_data;
|
||||
/* Global data of global instances */
|
||||
uint8 *global_data;
|
||||
uint32 global_data_size;
|
||||
|
||||
/* End address of memory */
|
||||
uint8 *end_addr;
|
||||
|
||||
/* Base address, the layout is:
|
||||
addr_data + thunk_argv data + thunk arg offsets +
|
||||
heap data + memory data + global data
|
||||
memory data init size is: NumBytesPerPage * cur_page_count
|
||||
addr data size and global data size is calculated in module instantiating
|
||||
Note: when memory is re-allocated, the addr data, thunk argv data, thunk
|
||||
argv offsets and memory data must be copied to new memory also.
|
||||
*/
|
||||
uint8 base_addr[1];
|
||||
} WASMMemoryInstance;
|
||||
|
||||
typedef struct WASMTableInstance {
|
||||
/* The element type, TABLE_ELEM_TYPE_ANY_FUNC currently */
|
||||
uint8 elem_type;
|
||||
/* Current size */
|
||||
uint32 cur_size;
|
||||
/* Maximum size */
|
||||
uint32 max_size;
|
||||
/* Base address */
|
||||
uint8 base_addr[1];
|
||||
} WASMTableInstance;
|
||||
|
||||
typedef struct WASMGlobalInstance {
|
||||
/* value type, VALUE_TYPE_I32/I64/F32/F64 */
|
||||
uint8 type;
|
||||
/* mutable or constant */
|
||||
bool is_mutable;
|
||||
bool is_addr;
|
||||
/* data offset to base_addr of WASMMemoryInstance */
|
||||
uint32 data_offset;
|
||||
/* initial value */
|
||||
WASMValue initial_value;
|
||||
} WASMGlobalInstance;
|
||||
|
||||
typedef struct WASMFunctionInstance {
|
||||
/* whether it is import function or WASM function */
|
||||
bool is_import_func;
|
||||
/* cell num of parameters */
|
||||
uint16 param_cell_num;
|
||||
/* cell num of return type */
|
||||
uint16 ret_cell_num;
|
||||
/* cell num of local variables, 0 for import function */
|
||||
uint16 local_cell_num;
|
||||
uint16 *local_offsets;
|
||||
union {
|
||||
WASMFunctionImport *func_import;
|
||||
WASMFunction *func;
|
||||
} u;
|
||||
} WASMFunctionInstance;
|
||||
|
||||
typedef struct WASMExportFuncInstance {
|
||||
char *name;
|
||||
WASMFunctionInstance *function;
|
||||
} WASMExportFuncInstance;
|
||||
|
||||
/* Package Type */
|
||||
typedef enum {
|
||||
Wasm_Module_Bytecode = 0,
|
||||
Wasm_Module_AoT,
|
||||
Package_Type_Unknown = 0xFFFF
|
||||
} PackageType;
|
||||
|
||||
typedef struct WASMModuleInstance {
|
||||
/* Module instance type, for module instance loaded from
|
||||
WASM bytecode binary, this field is Wasm_Module_Bytecode;
|
||||
for module instance loaded from AOT package, this field is
|
||||
Wasm_Module_AoT, and this structure should be treated as
|
||||
WASMAOTContext structure. */
|
||||
uint32 module_type;
|
||||
|
||||
uint32 memory_count;
|
||||
uint32 table_count;
|
||||
uint32 global_count;
|
||||
uint32 function_count;
|
||||
uint32 export_func_count;
|
||||
|
||||
WASMMemoryInstance **memories;
|
||||
WASMTableInstance **tables;
|
||||
WASMGlobalInstance *globals;
|
||||
WASMFunctionInstance *functions;
|
||||
WASMExportFuncInstance *export_functions;
|
||||
|
||||
WASMMemoryInstance *default_memory;
|
||||
WASMTableInstance *default_table;
|
||||
|
||||
WASMFunctionInstance *start_function;
|
||||
|
||||
HashMap *branch_set;
|
||||
const WASMModule *module;
|
||||
|
||||
uint32 DYNAMICTOP_PTR_offset;
|
||||
uint32 temp_ret;
|
||||
uint32 llvm_stack;
|
||||
|
||||
/* Default WASM stack size of threads of this Module instance. */
|
||||
uint32 wasm_stack_size;
|
||||
|
||||
/* Default WASM stack */
|
||||
uint8 *wasm_stack;
|
||||
|
||||
/* The exception buffer of wasm interpreter for current thread. */
|
||||
char cur_exception[128];
|
||||
|
||||
/* The thread data of the attaching thread */
|
||||
void *thread_data;
|
||||
|
||||
/* Main Thread */
|
||||
WASMThread main_tlr;
|
||||
} WASMModuleInstance;
|
||||
|
||||
/* Execution environment, e.g. stack info */
|
||||
typedef struct WASMExecEnv {
|
||||
uint8_t *stack;
|
||||
uint32_t stack_size;
|
||||
} WASMExecEnv;
|
||||
|
||||
struct WASMInterpFrame;
|
||||
typedef struct WASMInterpFrame WASMRuntimeFrame;
|
||||
|
||||
/**
|
||||
* Return the current thread.
|
||||
*
|
||||
* @return the current thread
|
||||
*/
|
||||
static inline WASMThread*
|
||||
wasm_runtime_get_self()
|
||||
{
|
||||
return (WASMThread*)ws_tls_get();
|
||||
}
|
||||
|
||||
/**
|
||||
* Set self as the current thread.
|
||||
*
|
||||
* @param self the thread to be set as current thread
|
||||
*/
|
||||
static inline void
|
||||
wasm_runtime_set_tlr(WASMThread *self)
|
||||
{
|
||||
ws_tls_put(self);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the code block of a function.
|
||||
*
|
||||
* @param func the WASM function instance
|
||||
*
|
||||
* @return the code block of the function
|
||||
*/
|
||||
static inline uint8*
|
||||
wasm_runtime_get_func_code(WASMFunctionInstance *func)
|
||||
{
|
||||
return func->is_import_func ? NULL : func->u.func->code;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the code block end of a function.
|
||||
*
|
||||
* @param func the WASM function instance
|
||||
*
|
||||
* @return the code block end of the function
|
||||
*/
|
||||
static inline uint8*
|
||||
wasm_runtime_get_func_code_end(WASMFunctionInstance *func)
|
||||
{
|
||||
return func->is_import_func
|
||||
? NULL : func->u.func->code + func->u.func->code_size;
|
||||
}
|
||||
|
||||
/**
|
||||
* Call the given WASM function of a WASM module instance with arguments (bytecode and AoT).
|
||||
*
|
||||
* @param module_inst the WASM module instance which the function belongs to
|
||||
* @param exec_env the execution environment to call the function. If the module instance
|
||||
* is created by AoT mode, it is ignored and just set it to NULL. If the module instance
|
||||
* is created by bytecode mode and it is NULL, a temporary env object will be created
|
||||
* @param function the function to be called
|
||||
* @param argc the number of arguments
|
||||
* @param argv the arguments. If the function method has return value,
|
||||
* the first (or first two in case 64-bit return value) element of
|
||||
* argv stores the return value of the called WASM function after this
|
||||
* function returns.
|
||||
*
|
||||
* @return true if success, false otherwise and exception will be thrown,
|
||||
* the caller can call wasm_runtime_get_exception to get exception info.
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_call_wasm(WASMModuleInstance *module,
|
||||
WASMExecEnv *exec_env,
|
||||
WASMFunctionInstance *function,
|
||||
unsigned argc, uint32 argv[]);
|
||||
|
||||
/**
|
||||
* Set current exception string to global exception string.
|
||||
*
|
||||
* @param module the wasm module instance
|
||||
*
|
||||
* @param exception current exception string
|
||||
*/
|
||||
void
|
||||
wasm_runtime_set_exception(WASMModuleInstance *module,
|
||||
const char *exception);
|
||||
|
||||
/**
|
||||
* Get current exception string.
|
||||
*
|
||||
* @param module the wasm module instance
|
||||
*
|
||||
* @return return exception string if exception is thrown, NULL otherwise
|
||||
*/
|
||||
const char*
|
||||
wasm_runtime_get_exception(WASMModuleInstance *module);
|
||||
|
||||
/**
|
||||
* Enlarge wasm memory data space.
|
||||
*
|
||||
* @param module the wasm module instance
|
||||
* @param inc_page_count denote the page number to increase
|
||||
* @return return true if enlarge successfully, false otherwise
|
||||
*/
|
||||
bool
|
||||
wasm_runtime_enlarge_memory(WASMModuleInstance *module, int inc_page_count);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
WASMModuleInstance *
|
||||
wasm_runtime_get_current_module_inst();
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
int32_t
|
||||
wasm_runtime_module_malloc(WASMModuleInstance *module_inst, uint32_t size);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
void
|
||||
wasm_runtime_module_free(WASMModuleInstance *module_inst, int32_t ptr);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
bool
|
||||
wasm_runtime_validate_app_addr(WASMModuleInstance *module_inst,
|
||||
int32_t app_offset, uint32_t size);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
bool
|
||||
wasm_runtime_validate_native_addr(WASMModuleInstance *module_inst,
|
||||
void *native_ptr, uint32_t size);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
void *
|
||||
wasm_runtime_addr_app_to_native(WASMModuleInstance *module_inst,
|
||||
int32_t app_offset);
|
||||
|
||||
/* See wasm-export.h for description */
|
||||
int32_t
|
||||
wasm_runtime_addr_native_to_app(WASMModuleInstance *module_inst,
|
||||
void *native_ptr);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_RUNTIME_H */
|
||||
|
||||
146
core/iwasm/runtime/vmcore_wasm/wasm-thread.h
Normal file
146
core/iwasm/runtime/vmcore_wasm/wasm-thread.h
Normal file
@ -0,0 +1,146 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_RUNTIME_THREAD_H
|
||||
#define _WASM_RUNTIME_THREAD_H
|
||||
|
||||
#include "wasm_assert.h"
|
||||
#include "wasm_thread.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct WASMModuleInstance;
|
||||
struct WASMInterpFrame;
|
||||
|
||||
typedef struct WASMStack {
|
||||
/* The bottom of the stack, must be 8-bytes align. */
|
||||
uint8 *bottom;
|
||||
/* Top cell index which is free. */
|
||||
uint8 *top;
|
||||
/* The top boundary of the stack. */
|
||||
uint8 *top_boundary;
|
||||
} WASMStack;
|
||||
|
||||
typedef struct WASMThread {
|
||||
/* Previous thread's tlr of an instance. */
|
||||
struct WASMThread *prev;
|
||||
|
||||
/* Next thread's tlr of an instance. */
|
||||
struct WASMThread *next;
|
||||
|
||||
/* The WASM module instance of current thread */
|
||||
struct WASMModuleInstance *module_inst;
|
||||
|
||||
/* Current frame of current thread. */
|
||||
struct WASMInterpFrame *cur_frame;
|
||||
|
||||
/* The boundary of native stack. When interpreter detects that native
|
||||
frame may overrun this boundary, it will throw a stack overflow
|
||||
exception. */
|
||||
void *native_stack_boundary;
|
||||
|
||||
/* The WASM stack of current thread. */
|
||||
WASMStack wasm_stack;
|
||||
|
||||
/* The native thread handle of current thread. */
|
||||
korp_tid handle;
|
||||
|
||||
/* Current suspend count of this thread. */
|
||||
uint32 suspend_count;
|
||||
} WASMThread;
|
||||
|
||||
/**
|
||||
* Allocate a WASM frame from the WASM stack.
|
||||
*
|
||||
* @param tlr the current thread
|
||||
* @param size size of the WASM frame, it must be a multiple of 4
|
||||
*
|
||||
* @return the WASM frame if there is enough space in the stack area
|
||||
* with a protection area, NULL otherwise
|
||||
*/
|
||||
static inline void*
|
||||
wasm_thread_alloc_wasm_frame(WASMThread *tlr, unsigned size)
|
||||
{
|
||||
uint8 *addr = tlr->wasm_stack.top;
|
||||
|
||||
wasm_assert(!(size & 3));
|
||||
|
||||
/* The outs area size cannot be larger than the frame size, so
|
||||
multiplying by 2 is enough. */
|
||||
if (addr + size * 2 > tlr->wasm_stack.top_boundary) {
|
||||
/* WASM stack overflow. */
|
||||
/* When throwing SOE, the preserved space must be enough. */
|
||||
/*wasm_assert(!tlr->throwing_soe);*/
|
||||
return NULL;
|
||||
}
|
||||
|
||||
tlr->wasm_stack.top += size;
|
||||
|
||||
return addr;
|
||||
}
|
||||
|
||||
static inline void
|
||||
wasm_thread_free_wasm_frame(WASMThread *tlr, void *prev_top)
|
||||
{
|
||||
wasm_assert((uint8 *)prev_top >= tlr->wasm_stack.bottom);
|
||||
tlr->wasm_stack.top = (uint8 *)prev_top;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the current WASM stack top pointer.
|
||||
*
|
||||
* @param tlr the current thread
|
||||
*
|
||||
* @return the current WASM stack top pointer
|
||||
*/
|
||||
static inline void*
|
||||
wasm_thread_wasm_stack_top(WASMThread *tlr)
|
||||
{
|
||||
return tlr->wasm_stack.top;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the current frame pointer.
|
||||
*
|
||||
* @param tlr the current thread
|
||||
* @param frame the WASM frame to be set for the current thread
|
||||
*/
|
||||
static inline void
|
||||
wasm_thread_set_cur_frame(WASMThread *tlr, struct WASMInterpFrame *frame)
|
||||
{
|
||||
tlr->cur_frame = frame;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the current frame pointer.
|
||||
*
|
||||
* @param tlr the current thread
|
||||
*
|
||||
* @return the current frame pointer
|
||||
*/
|
||||
static inline struct WASMInterpFrame*
|
||||
wasm_thread_get_cur_frame(WASMThread *tlr)
|
||||
{
|
||||
return tlr->cur_frame;
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_RUNTIME_THREAD_H */
|
||||
392
core/iwasm/runtime/vmcore_wasm/wasm.h
Normal file
392
core/iwasm/runtime/vmcore_wasm/wasm.h
Normal file
@ -0,0 +1,392 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _WASM_H_
|
||||
#define _WASM_H_
|
||||
|
||||
#include "wasm_platform.h"
|
||||
#include "wasm_hashmap.h"
|
||||
#include "wasm_assert.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/** Value Type */
|
||||
#define VALUE_TYPE_I32 0x7F
|
||||
#define VALUE_TYPE_I64 0X7E
|
||||
#define VALUE_TYPE_F32 0x7D
|
||||
#define VALUE_TYPE_F64 0x7C
|
||||
#define VALUE_TYPE_VOID 0x00
|
||||
|
||||
/* Table Element Type */
|
||||
#define TABLE_ELEM_TYPE_ANY_FUNC 0x70
|
||||
|
||||
#define MaxMemoryPages 65536
|
||||
#define MaxTableElems UINT32_MAX
|
||||
#define NumBytesPerPage 65536
|
||||
#define NumBytesPerPageLog2 16
|
||||
#define MaxReturnValues 16
|
||||
|
||||
#define INIT_EXPR_TYPE_I32_CONST 0x41
|
||||
#define INIT_EXPR_TYPE_I64_CONST 0x42
|
||||
#define INIT_EXPR_TYPE_F32_CONST 0x43
|
||||
#define INIT_EXPR_TYPE_F64_CONST 0x44
|
||||
#define INIT_EXPR_TYPE_GET_GLOBAL 0x23
|
||||
#define INIT_EXPR_TYPE_ERROR 0xff
|
||||
|
||||
#define WASM_MAGIC_NUMBER 0x6d736100
|
||||
#define WASM_CURRENT_VERSION 1
|
||||
|
||||
#define SECTION_TYPE_USER 0
|
||||
#define SECTION_TYPE_TYPE 1
|
||||
#define SECTION_TYPE_IMPORT 2
|
||||
#define SECTION_TYPE_FUNC 3
|
||||
#define SECTION_TYPE_TABLE 4
|
||||
#define SECTION_TYPE_MEMORY 5
|
||||
#define SECTION_TYPE_GLOBAL 6
|
||||
#define SECTION_TYPE_EXPORT 7
|
||||
#define SECTION_TYPE_START 8
|
||||
#define SECTION_TYPE_ELEM 9
|
||||
#define SECTION_TYPE_CODE 10
|
||||
#define SECTION_TYPE_DATA 11
|
||||
|
||||
#define IMPORT_KIND_FUNC 0
|
||||
#define IMPORT_KIND_TABLE 1
|
||||
#define IMPORT_KIND_MEMORY 2
|
||||
#define IMPORT_KIND_GLOBAL 3
|
||||
|
||||
#define EXPORT_KIND_FUNC 0
|
||||
#define EXPORT_KIND_TABLE 1
|
||||
#define EXPORT_KIND_MEMORY 2
|
||||
#define EXPORT_KIND_GLOBAL 3
|
||||
|
||||
#define BLOCK_TYPE_BLOCK 0
|
||||
#define BLOCK_TYPE_LOOP 1
|
||||
#define BLOCK_TYPE_IF 2
|
||||
#define BLOCK_TYPE_FUNCTION 3
|
||||
|
||||
#define CALL_TYPE_WRAPPER 0
|
||||
#define CALL_TYPE_C_INTRINSIC 1
|
||||
|
||||
typedef union WASMValue {
|
||||
int32 i32;
|
||||
uint32 u32;
|
||||
int64 i64;
|
||||
uint64 u64;
|
||||
float32 f32;
|
||||
float64 f64;
|
||||
uintptr_t addr;
|
||||
} WASMValue;
|
||||
|
||||
typedef struct InitializerExpression {
|
||||
/* type of INIT_EXPR_TYPE_XXX */
|
||||
uint8 init_expr_type;
|
||||
union {
|
||||
int32 i32;
|
||||
int64 i64;
|
||||
float32 f32;
|
||||
float64 f64;
|
||||
uint32 global_index;
|
||||
} u;
|
||||
} InitializerExpression;
|
||||
|
||||
typedef struct WASMType {
|
||||
uint32 param_count;
|
||||
/* only one result is supported currently */
|
||||
uint32 result_count;
|
||||
/* types of params and results */
|
||||
uint8 types[1];
|
||||
} WASMType;
|
||||
|
||||
typedef struct WASMTable {
|
||||
uint8 elem_type;
|
||||
uint32 flags;
|
||||
uint32 init_size;
|
||||
/* specified if (flags & 1), else it is 0x10000 */
|
||||
uint32 max_size;
|
||||
} WASMTable;
|
||||
|
||||
typedef struct WASMMemory {
|
||||
uint32 flags;
|
||||
/* 64 kbytes one page by default */
|
||||
uint32 init_page_count;
|
||||
uint32 max_page_count;
|
||||
} WASMMemory;
|
||||
|
||||
typedef struct WASMTableImport {
|
||||
char *module_name;
|
||||
char *field_name;
|
||||
uint8 elem_type;
|
||||
uint32 flags;
|
||||
uint32 init_size;
|
||||
/* specified if (flags & 1), else it is 0x10000 */
|
||||
uint32 max_size;
|
||||
} WASMTableImport;
|
||||
|
||||
typedef struct WASMMemoryImport {
|
||||
char *module_name;
|
||||
char *field_name;
|
||||
uint32 flags;
|
||||
/* 64 kbytes one page by default */
|
||||
uint32 init_page_count;
|
||||
uint32 max_page_count;
|
||||
} WASMMemoryImport;
|
||||
|
||||
typedef struct WASMFunctionImport {
|
||||
char *module_name;
|
||||
char *field_name;
|
||||
/* function type */
|
||||
WASMType *func_type;
|
||||
/* c intrinsic function or wrapper function */
|
||||
uint32 call_type;
|
||||
/* function pointer after linked */
|
||||
void *func_ptr_linked;
|
||||
} WASMFunctionImport;
|
||||
|
||||
typedef struct WASMGlobalImport {
|
||||
char *module_name;
|
||||
char *field_name;
|
||||
uint8 type;
|
||||
bool is_mutable;
|
||||
bool is_addr;
|
||||
/* global data after linked */
|
||||
WASMValue global_data_linked;
|
||||
} WASMGlobalImport;
|
||||
|
||||
typedef struct WASMImport {
|
||||
uint8 kind;
|
||||
union {
|
||||
WASMFunctionImport function;
|
||||
WASMTableImport table;
|
||||
WASMMemoryImport memory;
|
||||
WASMGlobalImport global;
|
||||
struct {
|
||||
char *module_name;
|
||||
char *field_name;
|
||||
} names;
|
||||
} u;
|
||||
} WASMImport;
|
||||
|
||||
typedef struct WASMFunction {
|
||||
/* the type of function */
|
||||
WASMType *func_type;
|
||||
uint32 local_count;
|
||||
uint8 *local_types;
|
||||
uint32 max_stack_cell_num;
|
||||
uint32 max_block_num;
|
||||
uint32 code_size;
|
||||
uint8 *code;
|
||||
} WASMFunction;
|
||||
|
||||
typedef struct WASMGlobal {
|
||||
uint8 type;
|
||||
bool is_mutable;
|
||||
bool is_addr;
|
||||
InitializerExpression init_expr;
|
||||
} WASMGlobal;
|
||||
|
||||
typedef struct WASMExport {
|
||||
char *name;
|
||||
uint8 kind;
|
||||
uint32 index;
|
||||
} WASMExport;
|
||||
|
||||
typedef struct WASMTableSeg {
|
||||
uint32 table_index;
|
||||
InitializerExpression base_offset;
|
||||
uint32 function_count;
|
||||
uint32 *func_indexes;
|
||||
} WASMTableSeg;
|
||||
|
||||
typedef struct WASMDataSeg {
|
||||
uint32 memory_index;
|
||||
InitializerExpression base_offset;
|
||||
uint32 data_length;
|
||||
uint8 *data;
|
||||
} WASMDataSeg;
|
||||
|
||||
typedef struct WASMModule {
|
||||
uint32 type_count;
|
||||
uint32 import_count;
|
||||
uint32 function_count;
|
||||
uint32 table_count;
|
||||
uint32 memory_count;
|
||||
uint32 global_count;
|
||||
uint32 export_count;
|
||||
uint32 table_seg_count;
|
||||
uint32 data_seg_count;
|
||||
|
||||
uint32 import_function_count;
|
||||
uint32 import_table_count;
|
||||
uint32 import_memory_count;
|
||||
uint32 import_global_count;
|
||||
|
||||
WASMImport *import_functions;
|
||||
WASMImport *import_tables;
|
||||
WASMImport *import_memories;
|
||||
WASMImport *import_globals;
|
||||
|
||||
WASMType **types;
|
||||
WASMImport *imports;
|
||||
WASMFunction **functions;
|
||||
WASMTable *tables;
|
||||
WASMMemory *memories;
|
||||
WASMGlobal *globals;
|
||||
WASMExport *exports;
|
||||
WASMTableSeg *table_segments;
|
||||
WASMDataSeg **data_segments;
|
||||
uint32 start_function;
|
||||
|
||||
HashMap *const_str_set;
|
||||
HashMap *branch_set;
|
||||
} WASMModule;
|
||||
|
||||
typedef struct WASMBranchBlock {
|
||||
uint8 block_type;
|
||||
uint8 return_type;
|
||||
uint8 *start_addr;
|
||||
uint8 *else_addr;
|
||||
uint8 *end_addr;
|
||||
uint32 *frame_sp;
|
||||
uint8 *frame_ref;
|
||||
} WASMBranchBlock;
|
||||
|
||||
typedef struct WASMSection {
|
||||
struct WASMSection *next;
|
||||
/* section type */
|
||||
int section_type;
|
||||
/* section body, not include type and size */
|
||||
const uint8_t *section_body;
|
||||
/* section body size */
|
||||
uint32_t section_body_size;
|
||||
} WASMSection;
|
||||
|
||||
/* Execution environment, e.g. stack info */
|
||||
/**
|
||||
* Align an unsigned value on a alignment boundary.
|
||||
*
|
||||
* @param v the value to be aligned
|
||||
* @param b the alignment boundary (2, 4, 8, ...)
|
||||
*
|
||||
* @return the aligned value
|
||||
*/
|
||||
inline static unsigned
|
||||
align_uint (unsigned v, unsigned b)
|
||||
{
|
||||
unsigned m = b - 1;
|
||||
return (v + m) & ~m;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the hash value of c string.
|
||||
*/
|
||||
inline static uint32
|
||||
wasm_string_hash(const char *str)
|
||||
{
|
||||
unsigned h = strlen(str);
|
||||
const uint8 *p = (uint8*)str;
|
||||
const uint8 *end = p + h;
|
||||
|
||||
while (p != end)
|
||||
h = ((h << 5) - h) + *p++;
|
||||
return h;
|
||||
}
|
||||
|
||||
/**
|
||||
* Whether two c strings are equal.
|
||||
*/
|
||||
inline static bool
|
||||
wasm_string_equal(const char *s1, const char *s2)
|
||||
{
|
||||
return strcmp(s1, s2) == 0 ? true : false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the byte size of value type.
|
||||
*
|
||||
*/
|
||||
inline static uint32
|
||||
wasm_value_type_size(uint8 value_type)
|
||||
{
|
||||
switch (value_type) {
|
||||
case VALUE_TYPE_I32:
|
||||
case VALUE_TYPE_F32:
|
||||
return sizeof(int32);
|
||||
case VALUE_TYPE_I64:
|
||||
case VALUE_TYPE_F64:
|
||||
return sizeof(int64);
|
||||
default:
|
||||
wasm_assert(0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
inline static uint16
|
||||
wasm_value_type_cell_num(uint8 value_type)
|
||||
{
|
||||
switch (value_type) {
|
||||
case VALUE_TYPE_I32:
|
||||
case VALUE_TYPE_F32:
|
||||
return 1;
|
||||
case VALUE_TYPE_I64:
|
||||
case VALUE_TYPE_F64:
|
||||
return 2;
|
||||
default:
|
||||
wasm_assert(0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
inline static uint16
|
||||
wasm_get_cell_num(const uint8 *types, uint32 type_count)
|
||||
{
|
||||
uint16 cell_num = 0;
|
||||
uint32 i;
|
||||
for (i = 0; i < type_count; i++)
|
||||
cell_num += wasm_value_type_cell_num(types[i]);
|
||||
return cell_num;
|
||||
}
|
||||
|
||||
inline static uint16
|
||||
wasm_type_param_cell_num(const WASMType *type)
|
||||
{
|
||||
return wasm_get_cell_num(type->types, type->param_count);
|
||||
}
|
||||
|
||||
inline static uint16
|
||||
wasm_type_return_cell_num(const WASMType *type)
|
||||
{
|
||||
return wasm_get_cell_num(type->types + type->param_count,
|
||||
type->result_count);
|
||||
}
|
||||
|
||||
inline static bool
|
||||
wasm_type_equal(const WASMType *type1, const WASMType *type2)
|
||||
{
|
||||
return (type1->param_count == type2->param_count
|
||||
&& type1->result_count == type2->result_count
|
||||
&& memcmp(type1->types, type2->types,
|
||||
type1->param_count + type1->result_count) == 0)
|
||||
? true : false;
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* end of extern "C" */
|
||||
#endif
|
||||
|
||||
#endif /* end of _WASM_H_ */
|
||||
|
||||
Reference in New Issue
Block a user