re-organized the readme (#111)
* Update README.md * re-organize the readme * more changes * roadmap and releases * Update README.md
268
doc/building.md
Normal file
@ -0,0 +1,268 @@
|
||||
|
||||
Build WAMR Core
|
||||
=========================
|
||||
Please follow the instructions below to build the WAMR core on different platforms.
|
||||
|
||||
Linux
|
||||
-------------------------
|
||||
First of all please install library dependencies of lib gcc.
|
||||
Use installation commands below for Ubuntu Linux:
|
||||
``` Bash
|
||||
sudo apt install lib32gcc-5-dev g++-multilib
|
||||
```
|
||||
Or in Fedora:
|
||||
``` Bash
|
||||
sudo dnf install glibc-devel.i686
|
||||
```
|
||||
|
||||
After installing dependencies, build the source code:
|
||||
``` Bash
|
||||
cd core/iwasm/products/linux/
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ..
|
||||
make
|
||||
```
|
||||
|
||||
Mac
|
||||
-------------------------
|
||||
Make sure to install Xcode from App Store firstly, and install cmake.
|
||||
|
||||
If you use Homebrew, install cmake from the command line:
|
||||
``` Bash
|
||||
brew install cmake
|
||||
```
|
||||
|
||||
Then build the source codes:
|
||||
```
|
||||
cd core/iwasm/products/darwin/
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ..
|
||||
make
|
||||
```
|
||||
|
||||
VxWorks
|
||||
-------------------------
|
||||
VxWorks 7 SR0620 release is validated.
|
||||
|
||||
First you need to build a VSB. Make sure *UTILS_UNIX* layer is added in the VSB.
|
||||
After the VSB is built, export the VxWorks toolchain path by:
|
||||
```
|
||||
export <vsb_dir_path>/host/vx-compiler/bin:$PATH
|
||||
```
|
||||
Now switch to iwasm source tree to build the source code:
|
||||
```
|
||||
cd core/iwasm/products/vxworks/
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ..
|
||||
make
|
||||
```
|
||||
Create a VIP based on the VSB. Make sure the following components are added:
|
||||
* INCLUDE_POSIX_PTHREADS
|
||||
* INCLUDE_POSIX_PTHREAD_SCHEDULER
|
||||
* INCLUDE_SHARED_DATA
|
||||
* INCLUDE_SHL
|
||||
|
||||
Copy the generated iwasm executable, the test WASM binary as well as the needed
|
||||
shared libraries (libc.so.1, libllvm.so.1 or libgnu.so.1 depending on the VSB,
|
||||
libunix.so.1) to a supported file system (eg: romfs).
|
||||
|
||||
Zephyr
|
||||
-------------------------
|
||||
You need to download the Zephyr source code first and embed WAMR into it.
|
||||
``` Bash
|
||||
git clone https://github.com/zephyrproject-rtos/zephyr.git
|
||||
cd zephyr/samples/
|
||||
cp -a <iwasm_dir>/products/zephyr/simple .
|
||||
cd simple
|
||||
ln -s <iwam_dir> iwasm
|
||||
ln -s <shared_lib_dir> shared-lib
|
||||
mkdir build && cd build
|
||||
source ../../../zephyr-env.sh
|
||||
cmake -GNinja -DBOARD=qemu_x86 ..
|
||||
ninja
|
||||
```
|
||||
AliOS-Things
|
||||
-------------------------
|
||||
1. a developerkit board id needed for testing
|
||||
2. download the AliOS-Things code
|
||||
``` Bash
|
||||
git clone https://github.com/alibaba/AliOS-Things.git
|
||||
```
|
||||
3. copy <iwasm_root_dir>/products/alios-things directory to AliOS-Things/middleware, and rename it as iwasm
|
||||
``` Bash
|
||||
cp -a <iwasm_root_dir>/products/alios-things middleware/iwasm
|
||||
```
|
||||
4. create a link to <iwasm_root_dir> in middleware/iwasm/ and rename it to iwasm
|
||||
``` Bash
|
||||
ln -s <iwasm_root_dir> middleware/iwasm/iwasm
|
||||
```
|
||||
5. create a link to <shared-lib_root_dir> in middleware/iwasm/ and rename it to shared-lib
|
||||
``` Bash
|
||||
ln -s <shared-lib_root_dir> middle/iwasm/shared-lib
|
||||
```
|
||||
6. modify file app/example/helloworld/helloworld.c, patch as:
|
||||
``` C
|
||||
#include <stdbool.h>
|
||||
#include <aos/kernel.h>
|
||||
extern bool iwasm_init();
|
||||
int application_start(int argc, char *argv[])
|
||||
{
|
||||
int count = 0;
|
||||
iwasm_init();
|
||||
...
|
||||
}
|
||||
```
|
||||
7. modify file app/example/helloworld/aos.mk
|
||||
``` C
|
||||
$(NAME)_COMPONENTS := osal_aos iwasm
|
||||
```
|
||||
8. build source code
|
||||
``` Bash
|
||||
aos make helloworld@developerkit -c config
|
||||
aos make
|
||||
```
|
||||
9. download the binary to developerkit board, check the output from serial port
|
||||
|
||||
Docker
|
||||
-------------------------
|
||||
[Docker](https://www.docker.com/) will download all the dependencies and build WAMR Core on your behalf.
|
||||
|
||||
Make sure you have Docker installed on your machine: [macOS](https://docs.docker.com/docker-for-mac/install/), [Windows](https://docs.docker.com/docker-for-windows/install/) or [Linux](https://docs.docker.com/install/linux/docker-ce/ubuntu/).
|
||||
|
||||
Build the Docker image:
|
||||
|
||||
``` Bash
|
||||
docker build --rm -f "Dockerfile" -t wamr:latest .
|
||||
```
|
||||
Run the image in interactive mode:
|
||||
``` Bash
|
||||
docker run --rm -it wamr:latest
|
||||
```
|
||||
You'll now enter the container at `/root`.
|
||||
|
||||
|
||||
Build WASM app
|
||||
=========================
|
||||
You can write a simple ```test.c``` as the first sample.
|
||||
|
||||
```C
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
char *buf;
|
||||
|
||||
printf("Hello world!\n");
|
||||
|
||||
buf = malloc(1024);
|
||||
if (!buf) {
|
||||
printf("malloc buf failed\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
printf("buf ptr: %p\n", buf);
|
||||
|
||||
sprintf(buf, "%s", "1234\n");
|
||||
printf("buf: %s", buf);
|
||||
|
||||
free(buf);
|
||||
return 0;
|
||||
}
|
||||
```
|
||||
|
||||
There are three methods to build a WASM binary. They are Emscripten, the clang compiler and Docker.
|
||||
|
||||
## Use Emscripten tool
|
||||
|
||||
A method to build a WASM binary is to use Emscripten tool ```emcc```.
|
||||
Assuming you are using Linux, you may install emcc from Emscripten EMSDK following the steps below:
|
||||
|
||||
```
|
||||
git clone https://github.com/emscripten-core/emsdk.git
|
||||
emsdk install latest
|
||||
emsdk activate latest
|
||||
```
|
||||
source ```./emsdk_env.sh```.
|
||||
The Emscripten website provides other installation methods beyond Linux.
|
||||
|
||||
Use the emcc command below to build the WASM C source code into the WASM binary.
|
||||
``` Bash
|
||||
emcc -g -O3 *.c -s WASM=1 -s SIDE_MODULE=1 -s ASSERTIONS=1 -s STACK_OVERFLOW_CHECK=2 \
|
||||
-s TOTAL_MEMORY=65536 -s TOTAL_STACK=4096 -o test.wasm
|
||||
```
|
||||
You will get ```test.wasm``` which is the WASM app binary.
|
||||
|
||||
## Use clang compiler
|
||||
|
||||
Another method to build a WASM binary is to use clang compiler```clang-8```.
|
||||
|
||||
Add source to your system source list from llvm website, for ubuntu16.04, add following lines to /etc/apt/sources.list:
|
||||
|
||||
```Bash
|
||||
deb http://apt.llvm.org/xenial/ llvm-toolchain-xenial main
|
||||
deb-src http://apt.llvm.org/xenial/ llvm-toolchain-xenial main # 7
|
||||
deb http://apt.llvm.org/xenial/ llvm-toolchain-xenial-7 main
|
||||
deb-src http://apt.llvm.org/xenial/ llvm-toolchain-xenial-7 main # 8
|
||||
deb http://apt.llvm.org/xenial/ llvm-toolchain-xenial-8 main
|
||||
deb-src http://apt.llvm.org/xenial/ llvm-toolchain-xenial-8 main
|
||||
```
|
||||
|
||||
Download and install clang-8 tool-chain using following commands:
|
||||
|
||||
```Bash
|
||||
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
|
||||
sudo apt-get update
|
||||
sudo apt-get install llvm-8 lld-8 clang-8
|
||||
```
|
||||
|
||||
Create a soft link under /usr/bin:
|
||||
|
||||
```Bash
|
||||
cd /usr/bin
|
||||
sudo ln -s wasm-ld-8 wasm-ld
|
||||
```
|
||||
|
||||
Use the clang-8 command below to build the WASM C source code into the WASM binary.
|
||||
|
||||
```Bash
|
||||
clang-8 --target=wasm32 -O3 -Wl,--initial-memory=131072,--allow-undefined,--export=main,
|
||||
--no-threads,--strip-all,--no-entry -nostdlib -o test.wasm test.c
|
||||
```
|
||||
|
||||
You will get ```test.wasm``` which is the WASM app binary.
|
||||
|
||||
## Using Docker
|
||||
|
||||
The last method availble is using [Docker](https://www.docker.com/). We assume you've already configured Docker (see Platform section above) and have a running interactive shell. Currently the Dockerfile only supports compiling apps with clang, with Emscripten planned for the future.
|
||||
|
||||
Use the clang-8 command below to build the WASM C source code into the WASM binary.
|
||||
|
||||
```Bash
|
||||
clang-8 --target=wasm32 -O3 -Wl,--initial-memory=131072,--allow-undefined,--export=main,
|
||||
--no-threads,--strip-all,--no-entry -nostdlib -o test.wasm test.c
|
||||
```
|
||||
|
||||
You will get ```test.wasm``` which is the WASM app binary.
|
||||
|
||||
Run WASM app
|
||||
========================
|
||||
|
||||
Assume you are using Linux, the command to run the test.wasm is:
|
||||
``` Bash
|
||||
cd iwasm/products/linux/build
|
||||
./iwasm test.wasm
|
||||
```
|
||||
You will get the following output:
|
||||
```
|
||||
Hello world!
|
||||
buf ptr: 0x400002b0
|
||||
buf: 1234
|
||||
```
|
||||
If you would like to run the test app on Zephyr, we have embedded a test sample into its OS image. You will need to execute:
|
||||
```
|
||||
ninja run
|
||||
```
|
||||
40
doc/embed_wamr.md
Normal file
@ -0,0 +1,40 @@
|
||||
Embed WAMR into software production
|
||||
=====================================
|
||||
|
||||

|
||||
|
||||
|
||||
A typical WAMR API usage is shown below (some return value checks are ignored):
|
||||
``` C
|
||||
static char global_heap_buf[512 * 1024];
|
||||
|
||||
char *buffer;
|
||||
wasm_module_t module;
|
||||
wasm_module_inst_t inst;
|
||||
wasm_function_inst_t func;
|
||||
wasm_exec_env_t env;
|
||||
uint32 argv[2];
|
||||
|
||||
bh_memory_init_with_pool(global_heap_buf, sizeof(global_heap_buf));
|
||||
wasm_runtime_init();
|
||||
|
||||
buffer = read_wasm_binary_to_buffer(…);
|
||||
module = wasm_runtime_load(buffer, size, err, err_size);
|
||||
inst = wasm_runtime_instantiate(module, 0, 0, err, err_size);
|
||||
func = wasm_runtime_lookup_function(inst, "fib", "(i32)i32");
|
||||
env = wasm_runtime_create_exec_env(stack_size);
|
||||
|
||||
argv[0] = 8;
|
||||
if (!wasm_runtime_call_wasm(inst, env, func, 1, argv_buf) ) {
|
||||
wasm_runtime_clear_exception(inst);
|
||||
}
|
||||
/* the return value is stored in argv[0] */
|
||||
printf("fib function return: %d\n", argv[0]);
|
||||
|
||||
wasm_runtime_destory_exec_env(env);
|
||||
wasm_runtime_deinstantiate(inst);
|
||||
wasm_runtime_unload(module);
|
||||
wasm_runtime_destroy();
|
||||
bh_memory_destroy();
|
||||
```
|
||||
|
||||
|
Before Width: | Height: | Size: 52 KiB |
|
Before Width: | Height: | Size: 77 KiB |
BIN
doc/pics/vgl.PNG
|
Before Width: | Height: | Size: 48 KiB |
|
Before Width: | Height: | Size: 81 KiB |
BIN
doc/pics/vgl_demo.png
Normal file
|
After Width: | Height: | Size: 130 KiB |
BIN
doc/pics/vgl_demo2.png
Normal file
|
After Width: | Height: | Size: 146 KiB |
BIN
doc/pics/vgl_demo_linux.png
Normal file
|
After Width: | Height: | Size: 5.7 KiB |
BIN
doc/pics/wamr-arch.JPG
Normal file
|
After Width: | Height: | Size: 129 KiB |
53
doc/release_ack.md
Normal file
@ -0,0 +1,53 @@
|
||||
Major feature releases and contributors
|
||||
=========================================
|
||||
|
||||
|
||||
**May 07, 2019: WAMR first GitHub release**
|
||||
|
||||
- Contributors: Wenyong Huang, Weining Lu, Lei Shi, Li Tian, Jizhao Zhang, Yi Zhang, Daoming Qiu, Xin Wang (Intel)
|
||||
|
||||
**May 17, 2019: Application manager, WASM APP API, samples and test tools**
|
||||
|
||||
- Contributors: Wenyong Huang, Weining Lu, Lei Shi, Li Tian, Jizhao Zhang, Yi Zhang, Daoming Qiu, Xin Wang (Intel)
|
||||
|
||||
**May 23, 2019: Support AliOS Things**
|
||||
|
||||
- Contributor: JinZhong Zhu (Alibaba)
|
||||
|
||||
|
||||
**May 24, 2019: Support memory usage profiler**
|
||||
|
||||
- Contributors Wenyong Huang (Intel)
|
||||
|
||||
**Jun 11, 2019: Add WASM APP API: connection **
|
||||
|
||||
- Contributor: Weining Lu (Intel)
|
||||
|
||||
**Jun 10, 2019: Support VxWorks **
|
||||
|
||||
- Contributor: Yiting Wang (WindRiver)
|
||||
|
||||
**Aug 1, 2019: Add WGL graphic user interface API **
|
||||
|
||||
- Contributor: Weining Lu
|
||||
|
||||
**Aug 14, 2019: Add Docker support **
|
||||
|
||||
- Contributor: beriberikix
|
||||
|
||||
|
||||
**Aug 14, 2019: WASM IoT app store demo **
|
||||
|
||||
- Contributor: Luhanzhi Li, Jun Xu (Intel)
|
||||
|
||||
|
||||
**Aug 28, 2019: SGX support **
|
||||
|
||||
- Contributor: Mic Bowman (Intel)
|
||||
|
||||
|
||||
**Sep 6, 2019: Mac platform support **
|
||||
|
||||
- Contributor: Jonathan Dong (Alibaba)
|
||||
|
||||
|
||||
16
doc/roadmap.md
Normal file
@ -0,0 +1,16 @@
|
||||
|
||||
# WebAssembly Micro Runtime Roadmap
|
||||
|
||||
|
||||
## Ahead of time compilation
|
||||
Status: under development. The first release is targetted to the end of 2019.
|
||||
|
||||
## WASI support
|
||||
Evaluated solution.
|
||||
|
||||
## Data serialization
|
||||
Evauating using cbor as the default data serialization
|
||||
|
||||
## Threading
|
||||
Not started yet
|
||||
|
||||
310
doc/wamr_api.md
Normal file
@ -0,0 +1,310 @@
|
||||
|
||||
WASM application library
|
||||
========================
|
||||
|
||||
WAMR APP API includes built-in Libc API's, Base library and Extension library reference.
|
||||
|
||||
|
||||
**Libc API's**<br/>
|
||||
This is a minimal set of Libc API's for memory allocation, string manipulation and printing. The header file is located at ```lib/app-libs/libc/lib_base.h```. The current supported API set is listed here:
|
||||
``` C
|
||||
void *malloc(size_t size);
|
||||
void *calloc(size_t n, size_t size);
|
||||
void free(void *ptr);
|
||||
int memcmp(const void *s1, const void *s2, size_t n);
|
||||
void *memcpy(void *dest, const void *src, size_t n);
|
||||
void *memmove(void *dest, const void *src, size_t n);
|
||||
void *memset(void *s, int c, size_t n);
|
||||
int putchar(int c);
|
||||
int snprintf(char *str, size_t size, const char *format, ...);
|
||||
int sprintf(char *str, const char *format, ...);
|
||||
char *strchr(const char *s, int c);
|
||||
int strcmp(const char *s1, const char *s2);
|
||||
char *strcpy(char *dest, const char *src);
|
||||
size_t strlen(const char *s);
|
||||
int strncmp(const char * str1, const char * str2, size_t n);
|
||||
char *strncpy(char *dest, const char *src, unsigned long n);
|
||||
```
|
||||
|
||||
**Base library**<br/>
|
||||
Basic support for communication, timers, etc is available. You can refer to the header file ```lib/app-libs/base/wasm_app.h``` which contains the definitions for request and response API's, event pub/sub API's and timer API's. Please note that these API's require the native implementations.
|
||||
The API set is listed below:
|
||||
``` C
|
||||
typedef void(*request_handler_f)(request_t *) ;
|
||||
typedef void(*response_handler_f)(response_t *, void *) ;
|
||||
|
||||
// Request API's
|
||||
bool api_register_resource_handler(const char *url, request_handler_f);
|
||||
void api_send_request(request_t * request, response_handler_f response_handler, void * user_data);
|
||||
void api_response_send(response_t *response);
|
||||
|
||||
// Event API's
|
||||
bool api_publish_event(const char *url, int fmt, void *payload, int payload_len);
|
||||
bool api_subscribe_event(const char * url, request_handler_f handler);
|
||||
|
||||
struct user_timer;
|
||||
typedef struct user_timer * user_timer_t;
|
||||
|
||||
// Timer API's
|
||||
user_timer_t api_timer_create(int interval, bool is_period, bool auto_start, void(*on_user_timer_update)(user_timer_t
|
||||
));
|
||||
void api_timer_cancel(user_timer_t timer);
|
||||
void api_timer_restart(user_timer_t timer, int interval);
|
||||
```
|
||||
|
||||
**Library extension reference**<br/>
|
||||
Currently we provide several kinds of extension library for reference including sensor, connection and GUI.
|
||||
|
||||
Sensor API: In the header file ```lib/app-libs/extension/sensor/sensor.h```, the API set is defined as below:
|
||||
``` C
|
||||
sensor_t sensor_open(const char* name, int index,
|
||||
void(*on_sensor_event)(sensor_t, attr_container_t *, void *),
|
||||
void *user_data);
|
||||
bool sensor_config(sensor_t sensor, int interval, int bit_cfg, int delay);
|
||||
bool sensor_config_with_attr_container(sensor_t sensor, attr_container_t *cfg);
|
||||
bool sensor_close(sensor_t sensor);
|
||||
```
|
||||
Connection API: In the header file `lib/app-libs/extension/connection/connection.h.`, the API set is defined as below:
|
||||
``` C
|
||||
/* Connection event type */
|
||||
typedef enum {
|
||||
/* Data is received */
|
||||
CONN_EVENT_TYPE_DATA = 1,
|
||||
/* Connection is disconnected */
|
||||
CONN_EVENT_TYPE_DISCONNECT
|
||||
} conn_event_type_t;
|
||||
|
||||
typedef void (*on_connection_event_f)(connection_t *conn,
|
||||
conn_event_type_t type,
|
||||
const char *data,
|
||||
uint32 len,
|
||||
void *user_data);
|
||||
connection_t *api_open_connection(const char *name,
|
||||
attr_container_t *args,
|
||||
on_connection_event_f on_event,
|
||||
void *user_data);
|
||||
void api_close_connection(connection_t *conn);
|
||||
int api_send_on_connection(connection_t *conn, const char *data, uint32 len);
|
||||
bool api_config_connection(connection_t *conn, attr_container_t *cfg);
|
||||
```
|
||||
GUI API: The API's is list in header file ```lib/app-libs/extension/gui/wgl.h``` which is implemented based open soure 2D graphic library [LittlevGL](https://docs.littlevgl.com/en/html/index.html). Currently supported widgets include button, label, list and check box and more wigdet would be provided in future.
|
||||
|
||||
The mechanism of exporting native API to WASM application
|
||||
=======================================================
|
||||
|
||||
The basic working flow for WASM application calling into the native API is shown in the following diagram:
|
||||
|
||||

|
||||
|
||||
|
||||
WAMR provides the macro `EXPORT_WASM_API` to enable users to export a native API to a WASM application. WAMR has implemented a base API for the timer and messaging by using `EXPORT_WASM_API`. This can be a point of reference for extending your own library.
|
||||
``` C
|
||||
static NativeSymbol extended_native_symbol_defs[] = {
|
||||
EXPORT_WASM_API(wasm_register_resource),
|
||||
EXPORT_WASM_API(wasm_response_send),
|
||||
EXPORT_WASM_API(wasm_post_request),
|
||||
EXPORT_WASM_API(wasm_sub_event),
|
||||
EXPORT_WASM_API(wasm_create_timer),
|
||||
EXPORT_WASM_API(wasm_timer_set_interval),
|
||||
EXPORT_WASM_API(wasm_timer_cancel),
|
||||
EXPORT_WASM_API(wasm_timer_restart)
|
||||
};
|
||||
```
|
||||
|
||||
 **Security attention:** A WebAssembly application should only have access to its own memory space. As a result, the integrator should carefully design the native function to ensure that the memory accesses are safe. The native API to be exported to the WASM application must:
|
||||
- Only use 32 bits number for parameters
|
||||
- Should not pass data to the structure pointer (do data serialization instead)
|
||||
- Should do the pointer address conversion in the native API
|
||||
- Should not pass function pointer as callback
|
||||
|
||||
Below is a sample of a library extension. All code invoked across WASM and native world must be serialized and de-serialized, and the native world must do a boundary check for every incoming address from the WASM world.
|
||||
|
||||
|
||||
<img src="./pics/safe.PNG" width="90%">
|
||||
|
||||
|
||||
Steps for exporting native API
|
||||
==========================
|
||||
|
||||
WAMR implemented a framework for developers to export API's. Below is the procedure to expose the platform API's in three steps:
|
||||
|
||||
**Step 1. Create a header file**<br/>
|
||||
Declare the API's for your WASM application source project to include.
|
||||
|
||||
**Step 2. Create a source file**<br/>
|
||||
Export the platform API's, for example in ``` products/linux/ext_lib_export.c ```
|
||||
``` C
|
||||
#include "lib_export.h"
|
||||
|
||||
static NativeSymbol extended_native_symbol_defs[] =
|
||||
{
|
||||
};
|
||||
|
||||
#include "ext_lib_export.h"
|
||||
```
|
||||
|
||||
**Step 3. Register new API's**<br/>
|
||||
Use the macro `EXPORT_WASM_API` and `EXPORT_WASM_API2` to add exported API's into the array of ```extended_native_symbol_defs```.
|
||||
The pre-defined MACRO `EXPORT_WASM_API` should be used to declare a function export:
|
||||
``` c
|
||||
#define EXPORT_WASM_API(symbol) {#symbol, symbol}
|
||||
```
|
||||
|
||||
Below code example shows how to extend the library to support `customized()`:
|
||||
|
||||
```
|
||||
//lib_export_impl.c
|
||||
void customized()
|
||||
{
|
||||
// your code
|
||||
}
|
||||
|
||||
|
||||
// lib_export_dec.h
|
||||
#ifndef _LIB_EXPORT_DEC_H_
|
||||
#define _LIB_EXPORT_DEC_H_
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void customized();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
// ext_lib_export.c
|
||||
#include "lib_export.h"
|
||||
#include "lib_export_dec.h"
|
||||
|
||||
static NativeSymbol extended_native_symbol_defs[] =
|
||||
{
|
||||
EXPORT_WASM_API(customized)
|
||||
};
|
||||
|
||||
#include "ext_lib_export.h"
|
||||
```
|
||||
|
||||
Use extended library
|
||||
------------------------
|
||||
In the application source project, it will include the WAMR built-in API's header file and platform extension header files. Assuming the board vendor extends the library which added an API called customized(), the WASM application would be like this:
|
||||
``` C
|
||||
#include <stdio.h>
|
||||
#include "lib_export_dec.h" // provided by the platform vendor
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int I;
|
||||
char *buf = “abcd”;
|
||||
customized(); // customized API provided by the platform vendor
|
||||
return i;
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
Communication programming models
|
||||
=========================
|
||||
WAMR supports two typical communication programming models, the microservice model and the pub/sub model.
|
||||
|
||||
|
||||
Microservice model
|
||||
-------------------------
|
||||
The microservice model is also known as request and response model. One WASM application acts as the server which provides a specific service. Other WASM applications or host/cloud applications request that service and get the response.
|
||||
<img src="./pics/request.PNG" width="60%" height="60%">
|
||||
|
||||
Below is the reference implementation of the server application. It provides room temperature measurement service.
|
||||
|
||||
``` C
|
||||
void on_init()
|
||||
{
|
||||
api_register_resource_handler("/room_temp", room_temp_handler);
|
||||
}
|
||||
|
||||
void on_destroy()
|
||||
{
|
||||
}
|
||||
|
||||
void room_temp_handler(request_t *request)
|
||||
{
|
||||
response_t response[1];
|
||||
attr_container_t *payload;
|
||||
payload = attr_container_create("room_temp payload");
|
||||
if (payload == NULL)
|
||||
return;
|
||||
|
||||
attr_container_set_string(&payload, "temp unit", "centigrade");
|
||||
attr_container_set_int(&payload, "value", 26);
|
||||
|
||||
make_response_for_request(request, response);
|
||||
set_response(response,
|
||||
CONTENT_2_05,
|
||||
FMT_ATTR_CONTAINER,
|
||||
payload,
|
||||
attr_container_get_serialize_length(payload));
|
||||
|
||||
api_response_send(response);
|
||||
attr_container_destroy(payload);
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
Pub/sub model
|
||||
-------------------------
|
||||
One WASM application acts as the event publisher. It publishes events to notify WASM applications or host/cloud applications which subscribe to the events.
|
||||
|
||||
<img src="./pics/sub.PNG" width="60%" height="60%">
|
||||
|
||||
Below is the reference implementation of the pub application. It utilizes a timer to repeatedly publish an overheat alert event to the subscriber applications. Then the subscriber applications receive the events immediately.
|
||||
|
||||
``` C
|
||||
/* Timer callback */
|
||||
void timer_update(user_timer_t timer
|
||||
{
|
||||
attr_container_t *event;
|
||||
|
||||
event = attr_container_create("event");
|
||||
attr_container_set_string(&event,
|
||||
"warning",
|
||||
"temperature is over high");
|
||||
|
||||
api_publish_event("alert/overheat",
|
||||
FMT_ATTR_CONTAINER,
|
||||
event,
|
||||
attr_container_get_serialize_length(event));
|
||||
|
||||
attr_container_destroy(event);
|
||||
}
|
||||
|
||||
void on_init()
|
||||
{
|
||||
user_timer_t timer;
|
||||
timer = api_timer_create(1000, true, true, timer_update);
|
||||
}
|
||||
|
||||
void on_destroy()
|
||||
{
|
||||
}
|
||||
```
|
||||
|
||||
Below is the reference implementation of the sub application.
|
||||
``` C
|
||||
void overheat_handler(request_t *event)
|
||||
{
|
||||
printf("Event: %s\n", event->url);
|
||||
|
||||
if (event->payload != NULL && event->fmt == FMT_ATTR_CONTAINER)
|
||||
attr_container_dump((attr_container_t *) event->payload);
|
||||
}
|
||||
|
||||
void on_init(
|
||||
{
|
||||
api_subscribe_event ("alert/overheat", overheat_handler);
|
||||
}
|
||||
|
||||
void on_destroy()
|
||||
{
|
||||
}
|
||||
```
|
||||
**Note:** You can also subscribe this event from host side by using host tool. Please refer `samples/simple` project for deail usage.
|
||||