Import reference-types feature (#612)
Implement spec reference-types proposal for interpreter, AOT and JIT, update documents and add sample. And upgrade AOT_CURRENT_VERSION to 3 as AOT file format and AOT module instance layout are changed. Signed-off-by: Wenyong Huang <wenyong.huang@intel.com>
This commit is contained in:
108
samples/ref-types/CMakeLists.txt
Normal file
108
samples/ref-types/CMakeLists.txt
Normal file
@ -0,0 +1,108 @@
|
||||
# Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
cmake_minimum_required (VERSION 2.8)
|
||||
|
||||
if (NOT WAMR_BUILD_PLATFORM STREQUAL "windows")
|
||||
project(ref-types)
|
||||
else()
|
||||
project (ref-types C ASM)
|
||||
enable_language (ASM_MASM)
|
||||
endif()
|
||||
|
||||
if(NOT CMAKE_BUILD_TYPE)
|
||||
set(CMAKE_BUILD_TYPE Debug)
|
||||
endif()
|
||||
|
||||
################ runtime settings ################
|
||||
string (TOLOWER ${CMAKE_HOST_SYSTEM_NAME} WAMR_BUILD_PLATFORM)
|
||||
if (APPLE)
|
||||
add_definitions(-DBH_PLATFORM_DARWIN)
|
||||
endif ()
|
||||
|
||||
# Resetdefault linker flags
|
||||
set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS "")
|
||||
set(CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS "")
|
||||
|
||||
# WAMR features switch
|
||||
set(WAMR_BUILD_TARGET "X86_64")
|
||||
|
||||
if(NOT DEFINED WAMR_BUILD_INTERP)
|
||||
set(WAMR_BUILD_INTERP 1)
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED WAMR_BUILD_AOT)
|
||||
set(WAMR_BUILD_AOT 0)
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED WAMR_BUILD_JOT)
|
||||
set(WAMR_BUILD_JIT 0)
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED WAMR_BUILD_FAST_INTERP)
|
||||
set(WAMR_BUILD_FAST_INTERP 1)
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED WAMR_BUILD_LIBC_BUILTIN)
|
||||
set(WAMR_BUILD_LIBC_BUILTIN 1)
|
||||
endif()
|
||||
|
||||
# Enable reference-types feature
|
||||
set(WAMR_BUILD_REF_TYPES 1)
|
||||
|
||||
if (NOT MSVC)
|
||||
# compiling and linking flags
|
||||
set (CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -pie -fPIE")
|
||||
if (NOT (CMAKE_C_COMPILER MATCHES ".*clang.*" OR CMAKE_C_COMPILER_ID MATCHES ".*Clang"))
|
||||
set (CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--gc-sections")
|
||||
endif ()
|
||||
set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wextra -Wformat -Wformat-security")
|
||||
if (WAMR_BUILD_TARGET MATCHES "X86_.*" OR WAMR_BUILD_TARGET STREQUAL "AMD_64")
|
||||
if (NOT (CMAKE_C_COMPILER MATCHES ".*clang.*" OR CMAKE_C_COMPILER_ID MATCHES ".*Clang"))
|
||||
set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -mindirect-branch-register")
|
||||
endif ()
|
||||
endif ()
|
||||
endif()
|
||||
# build out vmlib
|
||||
set(WAMR_ROOT_DIR ${CMAKE_CURRENT_LIST_DIR}/../..)
|
||||
set(WAMRC ${WAMR_ROOT_DIR}/wamr-compiler/build/wamrc)
|
||||
include (${WAMR_ROOT_DIR}/build-scripts/runtime_lib.cmake)
|
||||
|
||||
add_library(vmlib STATIC ${WAMR_RUNTIME_LIB_SOURCE})
|
||||
if (MSVC)
|
||||
target_compile_definitions(vmlib PRIVATE WASM_API_EXTERN=)
|
||||
endif()
|
||||
|
||||
################ application related ################
|
||||
## locate wat2wasm
|
||||
find_program(WAT2WASM
|
||||
wat2wasm
|
||||
PATHS /opt/wabt/bin
|
||||
REQUIRED
|
||||
)
|
||||
|
||||
if(NOT WAT2WASM)
|
||||
message(SEND_ERROR "can not find wat2wasm")
|
||||
endif()
|
||||
|
||||
include (${SHARED_DIR}/utils/uncommon/shared_uncommon.cmake)
|
||||
|
||||
add_executable(hello src/hello.c ${UNCOMMON_SHARED_SOURCE})
|
||||
|
||||
target_include_directories(hello PRIVATE ${UNCOMMON_SHARED_DIR})
|
||||
|
||||
target_link_libraries(hello vmlib -lpthread -lm)
|
||||
|
||||
if (MSVC)
|
||||
target_compile_definitions(hello PRIVATE WASM_API_EXTERN=)
|
||||
endif()
|
||||
|
||||
# wat to wasm
|
||||
file(GLOB WAT_FILE src/hello.wat)
|
||||
add_custom_target(hello_wasm ALL
|
||||
COMMAND ${WAT2WASM} ${WAT_FILE} -o ${PROJECT_BINARY_DIR}/hello.wasm
|
||||
DEPENDS ${WAT_FILE}
|
||||
BYPRODUCTS ${PROJECT_BINARY_DIR}/hello.wasm
|
||||
VERBATIM
|
||||
SOURCES ${WAT_FILE}
|
||||
)
|
||||
165
samples/ref-types/src/hello.c
Normal file
165
samples/ref-types/src/hello.c
Normal file
@ -0,0 +1,165 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
* SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
*/
|
||||
|
||||
#include "bh_platform.h"
|
||||
#include "bh_read_file.h"
|
||||
#include "wasm_export.h"
|
||||
|
||||
#define USE_GLOBAL_HEAP_BUF 0
|
||||
|
||||
#if USE_GLOBAL_HEAP_BUF != 0
|
||||
static char global_heap_buf[10 * 1024 * 1024] = { 0 };
|
||||
#endif
|
||||
|
||||
static int
|
||||
test_write_wrapper(wasm_exec_env_t exec_env,
|
||||
uint32 externref_idx_of_file,
|
||||
const char *str, int len)
|
||||
{
|
||||
FILE *file;
|
||||
char buf[16];
|
||||
|
||||
printf("## retrieve file handle from externref index\n");
|
||||
if (!wasm_externref_ref2obj(externref_idx_of_file, (void **)&file)) {
|
||||
printf("failed to get host object from externref index!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
snprintf(buf, sizeof(buf), "%%%ds", len);
|
||||
|
||||
printf("## write string to file: ");
|
||||
printf(buf, str);
|
||||
|
||||
return fprintf(file, buf, str);
|
||||
}
|
||||
|
||||
static NativeSymbol native_symbols[] = {
|
||||
{ "test_write", test_write_wrapper, "(i*~)i", NULL }
|
||||
};
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
char *wasm_file = "hello.wasm";
|
||||
uint8 *wasm_file_buf = NULL;
|
||||
uint32 wasm_file_size, externref_idx;
|
||||
uint32 stack_size = 16 * 1024, heap_size = 16 * 1024;
|
||||
wasm_module_t wasm_module = NULL;
|
||||
wasm_module_inst_t wasm_module_inst = NULL;
|
||||
wasm_function_inst_t func_inst = NULL;
|
||||
wasm_exec_env_t exec_env = NULL;
|
||||
RuntimeInitArgs init_args;
|
||||
char error_buf[128] = { 0 };
|
||||
const char *exce;
|
||||
unsigned argv1[8];
|
||||
#if WASM_ENABLE_LOG != 0
|
||||
int log_verbose_level = 2;
|
||||
#endif
|
||||
FILE *file;
|
||||
|
||||
memset(&init_args, 0, sizeof(RuntimeInitArgs));
|
||||
|
||||
#if USE_GLOBAL_HEAP_BUF != 0
|
||||
init_args.mem_alloc_type = Alloc_With_Pool;
|
||||
init_args.mem_alloc_option.pool.heap_buf = global_heap_buf;
|
||||
init_args.mem_alloc_option.pool.heap_size = sizeof(global_heap_buf);
|
||||
#else
|
||||
init_args.mem_alloc_type = Alloc_With_Allocator;
|
||||
init_args.mem_alloc_option.allocator.malloc_func = malloc;
|
||||
init_args.mem_alloc_option.allocator.realloc_func = realloc;
|
||||
init_args.mem_alloc_option.allocator.free_func = free;
|
||||
#endif
|
||||
|
||||
init_args.n_native_symbols = sizeof(native_symbols) / sizeof(NativeSymbol);
|
||||
init_args.native_module_name = "env";
|
||||
init_args.native_symbols = native_symbols;
|
||||
|
||||
/* initialize runtime environment */
|
||||
if (!wasm_runtime_full_init(&init_args)) {
|
||||
printf("Init runtime environment failed.\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if WASM_ENABLE_LOG != 0
|
||||
bh_log_set_verbose_level(log_verbose_level);
|
||||
#endif
|
||||
|
||||
/* load WASM byte buffer from WASM bin file */
|
||||
if (!(wasm_file_buf =
|
||||
(uint8 *)bh_read_file_to_buffer(wasm_file, &wasm_file_size)))
|
||||
goto fail1;
|
||||
|
||||
/* load WASM module */
|
||||
if (!(wasm_module = wasm_runtime_load(wasm_file_buf, wasm_file_size,
|
||||
error_buf, sizeof(error_buf)))) {
|
||||
printf("%s\n", error_buf);
|
||||
goto fail2;
|
||||
}
|
||||
|
||||
/* instantiate the module */
|
||||
if (!(wasm_module_inst =
|
||||
wasm_runtime_instantiate(wasm_module, stack_size, heap_size,
|
||||
error_buf, sizeof(error_buf)))) {
|
||||
printf("%s\n", error_buf);
|
||||
goto fail3;
|
||||
}
|
||||
|
||||
/* lookup function instance */
|
||||
if (!(func_inst = wasm_runtime_lookup_function(wasm_module_inst,
|
||||
"test", NULL))) {
|
||||
printf("%s\n", "lookup function test failed");
|
||||
goto fail4;
|
||||
}
|
||||
|
||||
if (!(exec_env =
|
||||
wasm_runtime_create_exec_env(wasm_module_inst, stack_size))) {
|
||||
printf("%s\n", "create exec env failed");
|
||||
goto fail4;
|
||||
}
|
||||
|
||||
printf("## open file test.txt\n");
|
||||
if (!(file = fopen("test.txt", "wb+"))) {
|
||||
printf("%s\n", "open file text.txt failed");
|
||||
goto fail5;
|
||||
}
|
||||
|
||||
printf("## map file handle to externref index\n");
|
||||
if (!wasm_externref_obj2ref(wasm_module_inst, file, &externref_idx)) {
|
||||
printf("%s\n", "map host object to externref index failed");
|
||||
goto fail6;
|
||||
}
|
||||
|
||||
printf("## call wasm function with externref index\n");
|
||||
argv1[0] = externref_idx;
|
||||
wasm_runtime_call_wasm(exec_env, func_inst, 1, argv1);
|
||||
|
||||
if ((exce = wasm_runtime_get_exception(wasm_module_inst))) {
|
||||
printf("Exception: %s\n", exce);
|
||||
}
|
||||
|
||||
fail6:
|
||||
fclose(file);
|
||||
|
||||
fail5:
|
||||
/* destroy exec env */
|
||||
wasm_runtime_destroy_exec_env(exec_env);
|
||||
|
||||
fail4:
|
||||
/* destroy the module instance */
|
||||
wasm_runtime_deinstantiate(wasm_module_inst);
|
||||
|
||||
fail3:
|
||||
/* unload the module */
|
||||
wasm_runtime_unload(wasm_module);
|
||||
|
||||
fail2:
|
||||
/* free the file buffer */
|
||||
wasm_runtime_free(wasm_file_buf);
|
||||
|
||||
fail1:
|
||||
/* destroy runtime environment */
|
||||
wasm_runtime_destroy();
|
||||
return 0;
|
||||
}
|
||||
22
samples/ref-types/src/hello.wat
Normal file
22
samples/ref-types/src/hello.wat
Normal file
@ -0,0 +1,22 @@
|
||||
;; Copyright (C) 2019 Intel Corporation. All rights reserved.
|
||||
;; SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
(module
|
||||
;; import test_write function which is implemented by host
|
||||
(import "env" "test_write"
|
||||
(func $test_write (param externref i32 i32) (result i32)))
|
||||
|
||||
;; memory with one page (64KiB).
|
||||
(memory (export "memory") 1)
|
||||
|
||||
(data (i32.const 0x8) "Hello, world!\n")
|
||||
|
||||
;; function that writes string to a given open file handle
|
||||
(func (export "test") (param externref)
|
||||
(local.get 0)
|
||||
(i32.const 0x8)
|
||||
(i32.const 14)
|
||||
(call $test_write)
|
||||
drop
|
||||
)
|
||||
)
|
||||
Reference in New Issue
Block a user