summaryrefslogtreecommitdiffstats
path: root/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-03-09 13:19:22 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-03-09 13:19:22 +0000
commitc21c3b0befeb46a51b6bf3758ffa30813bea0ff0 (patch)
tree9754ff1ca740f6346cf8483ec915d4054bc5da2d /fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework
parentAdding upstream version 1.43.2. (diff)
downloadnetdata-c21c3b0befeb46a51b6bf3758ffa30813bea0ff0.tar.xz
netdata-c21c3b0befeb46a51b6bf3758ffa30813bea0ff0.zip
Adding upstream version 1.44.3.upstream/1.44.3
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework')
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/README.md120
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/README.md11
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/attr_container.c986
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/attr_container.h596
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/shared_utils.h155
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/wgl_shared_utils.h101
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.cmake15
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.h13
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/restful_utils.c493
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_ext_lib_export.c38
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_framework.cmake93
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.c89
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.h65
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/req_resp_api.h31
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/request.c365
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer.c100
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer_api.h36
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/request.h171
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/timer_wasm_app.h71
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.cmake13
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.h20
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib.inl14
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib_export.c24
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/req_resp_native_api.h29
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/request_response.c84
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/runtime_lib.h22
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_native_api.h40
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_wrapper.c220
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/wasm_lib.cmake13
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection.c118
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection_api.h31
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wa-inc/connection.h94
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wasm_app.cmake11
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection.inl9
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_lib.h75
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_native_api.h36
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_wrapper.c61
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.c54
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.h28
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.c103
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.h28
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.c58
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.h28
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.c609
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.cmake13
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/wasm_lib.cmake18
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_lib_impl.c25
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_mgr.cmake13
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor.c122
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor_api.h31
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wa-inc/sensor.h94
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wasm_app.cmake11
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.c434
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.h69
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.inl9
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_mgr_ref.c148
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_native_api.h33
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/wasm_lib.cmake14
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wa-inc/app_xxx.h8
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wasm_app.cmake16
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/app_xxx.inl6
-rw-r--r--fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/wasm_lib.cmake17
62 files changed, 6452 insertions, 0 deletions
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/README.md b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/README.md
new file mode 100644
index 000000000..d1476fd8b
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/README.md
@@ -0,0 +1,120 @@
+# Application framework
+
+By using the WAMR VM core, we are flexible to build different application frameworks for the specific domains, although it would take quite some effort.
+
+The WAMR has offered a comprehensive framework for programming WASM applications for device and IoT usages. The framework supports running multiple applications, that are based on the event driven programming model. Here are the supporting API sets by the [WAMR application framework library](../doc/wamr_api.md) :
+
+- Timer, Inter-app communication (request/response and pub/sub), Sensor, Connectivity and data transmission, 2D graphic UI
+
+Browse the folder [core/app-framework](./app-framework) for how to extend the application framework.
+
+
+## Directory structure
+This folder "app-native-shared" is for the source files shared by both WASM APP and native runtime
+
+- The c files in this directory are compiled into both the WASM APP and runtime.
+- The header files for distributing to SDK are placed in the "bi-inc" folder.
+
+This folder "template" contains a pre-defined directory structure for a framework component. The developers can copy the template folder to create new components to the application framework.
+
+Every other subfolder is framework component. Each component contains two library parts: **app and native**.
+
+- The "base" component provide timer API and inter-app communication support. It must be enabled if other components are selected.
+- Under the "app" folder of a component, the subfolder "wa_inc" holds all header files that should be included by the WASM applications
+
+## Application framework basic model
+
+The app framework is built on top of two fundamental operations:
+
+- [Native calls into WASM function](../../doc/embed_wamr.md)
+
+- [WASM app calls into native API](../../doc/export_native_api.md)
+
+Asynchronized programming model is supported for WASM applications
+
+- Every WASM app has its own sandbox and thread
+
+- Queue and messaging
+
+<img src="../../doc/pics/app_framework.PNG" style="zoom:67%;" />
+
+
+
+## Customized building of app framework
+
+A component can be compilation configurable to the runtime. The wamr SDK tool "build_sdk.sh" supports menu config to select app components for building a customized runtime.
+
+A number of CMAKE variables are defined to control build of framework and components. You can create a cmake file for defining these variables and include it in the CMakeList.txt for your software, or pass it in "-x" argument when run the [build_sdk.sh](../../wamr-sdk/build_sdk.sh) for building the runtime SDK.
+
+```cmake
+set (WAMR_BUILD_APP_FRAMEWORK 1)
+set (WAMR_BUILD_APP_LIST WAMR_APP_BUILD_BASE)
+```
+
+Variables:
+
+- **WAMR_BUILD_APP_FRAMEWORK**: enable the application framework
+- **WAMR_BUILD_APP_LIST**: the selected components to be built into the final runtime
+
+
+
+The configuration file can be generated through the wamr-sdk menu config:
+
+```bash
+cd wamr-sdk
+./build_sdk -n [profile] -i
+```
+
+
+
+## Create new components
+
+Generally you should follow following steps to create a new component:
+
+- Copy the “template” for creating a new folder
+
+- Implement the app part
+
+ - If your component exports native function to WASM, ensure your created a header file under app for declaring the function prototype.
+ - If you component provides header files for the WASM applications to include, ensure it is placed under subfolder "wa_inc".
+
+- Implement the native part
+
+ - If your native function is exported to WASM, you need to create an inl file for the registration. It can be any file name, assuming the file name is "my_component.inl" here:
+
+ ```c
+ //use right signature for your functions
+ EXPORT_WASM_API_WITH_SIG(wasm_my_component_api_1, "(i*~)i"),
+ EXPORT_WASM_API_WITH_SIG(wasm_my_component_api_2, "(i)i"),
+ ```
+
+ - Ensure "wasm_lib.cmake" is provided as it will be included by the WAMR SDK building script
+
+ - Add a definition in "wasm_lib.cmake" for your component, e.g.
+
+ ```cmake
+ add_definitions (-DAPP_FRAMEWORK_MY_COMPONENT)
+ ```
+
+- Modify the file [app_ext_lib_export.c](./app_ext_lib_export.c) to register native APIs exported for the new introduced component. Skip it if not exporting native functions.
+
+ ```
+ #include "lib_export.h"
+
+ ...
+ #ifdef APP_FRAMEWORK_MY_COMPONENT // this definition is created in wasm_lib.cmake
+ #include "my_component_native_api.h"
+ #endif
+
+ static NativeSymbol extended_native_symbol_defs[] = {
+ ...
+ #ifdef APP_FRAMEWORK_MY_COMPONENT
+ #include "my_component.inl"
+ #endif
+ };
+ ```
+
+
+## Sensor component working flow
+![](../../doc/pics/sensor_callflow.PNG)
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/README.md b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/README.md
new file mode 100644
index 000000000..b166e0b3a
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/README.md
@@ -0,0 +1,11 @@
+ Notes:
+=======
+This folder is for the source files shared by both WASM APP and native runtime
+
+- The c files in this directory are compiled into both the WASM APP and runtime.
+- The header files for distributing to SDK are placed in the "bi-inc" folder.
+
+
+
+
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/attr_container.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/attr_container.c
new file mode 100644
index 000000000..e1e9f4e35
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/attr_container.c
@@ -0,0 +1,986 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "bi-inc/attr_container.h"
+
+typedef union jvalue {
+ bool z;
+ int8_t i8;
+ uint8_t u8;
+ int16_t i16;
+ uint16_t u16;
+ int32_t i32;
+ uint32_t u32;
+ int64_t i64;
+ uint64_t u64;
+ float f;
+ double d;
+} jvalue;
+
+static inline int16_t
+get_int16(const char *buf)
+{
+ int16_t ret;
+ bh_memcpy_s(&ret, sizeof(int16_t), buf, sizeof(int16_t));
+ return ret;
+}
+
+static inline uint16_t
+get_uint16(const char *buf)
+{
+ uint16_t ret;
+ bh_memcpy_s(&ret, sizeof(uint16_t), buf, sizeof(uint16_t));
+ return ret;
+}
+
+static inline int32_t
+get_int32(const char *buf)
+{
+ int32_t ret;
+ bh_memcpy_s(&ret, sizeof(int32_t), buf, sizeof(int32_t));
+ return ret;
+}
+
+static inline uint32_t
+get_uint32(const char *buf)
+{
+ uint32_t ret;
+ bh_memcpy_s(&ret, sizeof(uint32_t), buf, sizeof(uint32_t));
+ return ret;
+}
+
+static inline int64_t
+get_int64(const char *buf)
+{
+ int64_t ret;
+ bh_memcpy_s(&ret, sizeof(int64_t), buf, sizeof(int64_t));
+ return ret;
+}
+
+static inline uint64_t
+get_uint64(const char *buf)
+{
+ uint64_t ret;
+ bh_memcpy_s(&ret, sizeof(uint64_t), buf, sizeof(uint64_t));
+ return ret;
+}
+
+static inline void
+set_int16(char *buf, int16_t v)
+{
+ bh_memcpy_s(buf, sizeof(int16_t), &v, sizeof(int16_t));
+}
+
+static inline void
+set_uint16(char *buf, uint16_t v)
+{
+ bh_memcpy_s(buf, sizeof(uint16_t), &v, sizeof(uint16_t));
+}
+
+static inline void
+set_int32(char *buf, int32_t v)
+{
+ bh_memcpy_s(buf, sizeof(int32_t), &v, sizeof(int32_t));
+}
+
+static inline void
+set_uint32(char *buf, uint32_t v)
+{
+ bh_memcpy_s(buf, sizeof(uint32_t), &v, sizeof(uint32_t));
+}
+
+static inline void
+set_int64(char *buf, int64_t v)
+{
+ bh_memcpy_s(buf, sizeof(int64_t), &v, sizeof(int64_t));
+}
+
+static inline void
+set_uint64(char *buf, uint64_t v)
+{
+ bh_memcpy_s(buf, sizeof(uint64_t), &v, sizeof(uint64_t));
+}
+
+char *
+attr_container_get_attr_begin(const attr_container_t *attr_cont,
+ uint32_t *p_total_length, uint16_t *p_attr_num)
+{
+ char *p = (char *)attr_cont->buf;
+ uint16_t str_len, attr_num;
+ uint32_t total_length;
+
+ /* skip total length */
+ total_length = get_uint32(p);
+ p += sizeof(uint32_t);
+ if (!total_length)
+ return NULL;
+
+ /* tag length */
+ str_len = get_uint16(p);
+ p += sizeof(uint16_t);
+ if (!str_len)
+ return NULL;
+
+ /* tag content */
+ p += str_len;
+ if ((uint32_t)(p - attr_cont->buf) >= total_length)
+ return NULL;
+
+ /* attribute num */
+ attr_num = get_uint16(p);
+ p += sizeof(uint16_t);
+ if ((uint32_t)(p - attr_cont->buf) >= total_length)
+ return NULL;
+
+ if (p_total_length)
+ *p_total_length = total_length;
+
+ if (p_attr_num)
+ *p_attr_num = attr_num;
+
+ /* first attribute */
+ return p;
+}
+
+static char *
+attr_container_get_attr_next(const char *curr_attr)
+{
+ char *p = (char *)curr_attr;
+ uint8_t type;
+
+ /* key length and key */
+ p += sizeof(uint16_t) + get_uint16(p);
+ type = *p++;
+
+ /* Byte type to Boolean type */
+ if (type >= ATTR_TYPE_BYTE && type <= ATTR_TYPE_BOOLEAN) {
+ p += 1 << (type & 3);
+ return p;
+ }
+ /* String type */
+ else if (type == ATTR_TYPE_STRING) {
+ p += sizeof(uint16_t) + get_uint16(p);
+ return p;
+ }
+ /* ByteArray type */
+ else if (type == ATTR_TYPE_BYTEARRAY) {
+ p += sizeof(uint32_t) + get_uint32(p);
+ return p;
+ }
+
+ return NULL;
+}
+
+static const char *
+attr_container_find_attr(const attr_container_t *attr_cont, const char *key)
+{
+ uint32_t total_length;
+ uint16_t str_len, attr_num, i;
+ const char *p = attr_cont->buf;
+
+ if (!key)
+ return NULL;
+
+ if (!(p = attr_container_get_attr_begin(attr_cont, &total_length,
+ &attr_num)))
+ return NULL;
+
+ for (i = 0; i < attr_num; i++) {
+ /* key length */
+ if (!(str_len = get_uint16(p)))
+ return NULL;
+
+ if (str_len == strlen(key) + 1
+ && memcmp(p + sizeof(uint16_t), key, str_len) == 0) {
+ if ((uint32_t)(p + sizeof(uint16_t) + str_len - attr_cont->buf)
+ >= total_length)
+ return NULL;
+ return p;
+ }
+
+ if (!(p = attr_container_get_attr_next(p)))
+ return NULL;
+ }
+
+ return NULL;
+}
+
+char *
+attr_container_get_attr_end(const attr_container_t *attr_cont)
+{
+ uint32_t total_length;
+ uint16_t attr_num, i;
+ char *p;
+
+ if (!(p = attr_container_get_attr_begin(attr_cont, &total_length,
+ &attr_num)))
+ return NULL;
+
+ for (i = 0; i < attr_num; i++)
+ if (!(p = attr_container_get_attr_next(p)))
+ return NULL;
+
+ return p;
+}
+
+static char *
+attr_container_get_msg_end(attr_container_t *attr_cont)
+{
+ char *p = attr_cont->buf;
+ return p + get_uint32(p);
+}
+
+uint16_t
+attr_container_get_attr_num(const attr_container_t *attr_cont)
+{
+ uint16_t str_len;
+ /* skip total length */
+ const char *p = attr_cont->buf + sizeof(uint32_t);
+
+ str_len = get_uint16(p);
+ /* skip tag length and tag */
+ p += sizeof(uint16_t) + str_len;
+
+ /* attribute num */
+ return get_uint16(p);
+}
+
+static void
+attr_container_inc_attr_num(attr_container_t *attr_cont)
+{
+ uint16_t str_len, attr_num;
+ /* skip total length */
+ char *p = attr_cont->buf + sizeof(uint32_t);
+
+ str_len = get_uint16(p);
+ /* skip tag length and tag */
+ p += sizeof(uint16_t) + str_len;
+
+ /* attribute num */
+ attr_num = get_uint16(p) + 1;
+ set_uint16(p, attr_num);
+}
+
+attr_container_t *
+attr_container_create(const char *tag)
+{
+ attr_container_t *attr_cont;
+ int length, tag_length;
+ char *p;
+
+ tag_length = tag ? strlen(tag) + 1 : 1;
+ length = offsetof(attr_container_t, buf) +
+ /* total length + tag length + tag + reserved 100 bytes */
+ sizeof(uint32_t) + sizeof(uint16_t) + tag_length + 100;
+
+ if (!(attr_cont = attr_container_malloc(length))) {
+ attr_container_printf(
+ "Create attr_container failed: allocate memory failed.\r\n");
+ return NULL;
+ }
+
+ memset(attr_cont, 0, length);
+ p = attr_cont->buf;
+
+ /* total length */
+ set_uint32(p, length - offsetof(attr_container_t, buf));
+ p += 4;
+
+ /* tag length, tag */
+ set_uint16(p, tag_length);
+ p += 2;
+ if (tag)
+ bh_memcpy_s(p, tag_length, tag, tag_length);
+
+ return attr_cont;
+}
+
+void
+attr_container_destroy(const attr_container_t *attr_cont)
+{
+ if (attr_cont)
+ attr_container_free((char *)attr_cont);
+}
+
+static bool
+check_set_attr(attr_container_t **p_attr_cont, const char *key)
+{
+ uint32_t flags;
+
+ if (!p_attr_cont || !*p_attr_cont || !key || strlen(key) == 0) {
+ attr_container_printf(
+ "Set attribute failed: invalid input arguments.\r\n");
+ return false;
+ }
+
+ flags = get_uint32((char *)*p_attr_cont);
+ if (flags & ATTR_CONT_READONLY_SHIFT) {
+ attr_container_printf(
+ "Set attribute failed: attribute container is readonly.\r\n");
+ return false;
+ }
+
+ return true;
+}
+
+bool
+attr_container_set_attr(attr_container_t **p_attr_cont, const char *key,
+ int type, const void *value, int value_length)
+{
+ attr_container_t *attr_cont, *attr_cont1;
+ uint16_t str_len;
+ uint32_t total_length, attr_len;
+ char *p, *p1, *attr_end, *msg_end, *attr_buf;
+
+ if (!check_set_attr(p_attr_cont, key)) {
+ return false;
+ }
+
+ attr_cont = *p_attr_cont;
+ p = attr_cont->buf;
+ total_length = get_uint32(p);
+
+ if (!(attr_end = attr_container_get_attr_end(attr_cont))) {
+ attr_container_printf("Set attr failed: get attr end failed.\r\n");
+ return false;
+ }
+
+ msg_end = attr_container_get_msg_end(attr_cont);
+
+ /* key len + key + '\0' + type */
+ attr_len = sizeof(uint16_t) + strlen(key) + 1 + 1;
+ if (type >= ATTR_TYPE_BYTE && type <= ATTR_TYPE_BOOLEAN)
+ attr_len += 1 << (type & 3);
+ else if (type == ATTR_TYPE_STRING)
+ attr_len += sizeof(uint16_t) + value_length;
+ else if (type == ATTR_TYPE_BYTEARRAY)
+ attr_len += sizeof(uint32_t) + value_length;
+
+ if (!(p = attr_buf = attr_container_malloc(attr_len))) {
+ attr_container_printf("Set attr failed: allocate memory failed.\r\n");
+ return false;
+ }
+
+ /* Set the attr buf */
+ str_len = (uint16_t)(strlen(key) + 1);
+ set_uint16(p, str_len);
+ p += sizeof(uint16_t);
+ bh_memcpy_s(p, str_len, key, str_len);
+ p += str_len;
+
+ *p++ = type;
+ if (type >= ATTR_TYPE_BYTE && type <= ATTR_TYPE_BOOLEAN)
+ bh_memcpy_s(p, 1 << (type & 3), value, 1 << (type & 3));
+ else if (type == ATTR_TYPE_STRING) {
+ set_uint16(p, value_length);
+ p += sizeof(uint16_t);
+ bh_memcpy_s(p, value_length, value, value_length);
+ }
+ else if (type == ATTR_TYPE_BYTEARRAY) {
+ set_uint32(p, value_length);
+ p += sizeof(uint32_t);
+ bh_memcpy_s(p, value_length, value, value_length);
+ }
+
+ if ((p = (char *)attr_container_find_attr(attr_cont, key))) {
+ /* key found */
+ p1 = attr_container_get_attr_next(p);
+
+ if (p1 - p == attr_len) {
+ bh_memcpy_s(p, attr_len, attr_buf, attr_len);
+ attr_container_free(attr_buf);
+ return true;
+ }
+
+ if ((uint32_t)(p1 - p + msg_end - attr_end) >= attr_len) {
+ memmove(p, p1, attr_end - p1);
+ bh_memcpy_s(p + (attr_end - p1), attr_len, attr_buf, attr_len);
+ attr_container_free(attr_buf);
+ return true;
+ }
+
+ total_length += attr_len + 100;
+ if (!(attr_cont1 = attr_container_malloc(offsetof(attr_container_t, buf)
+ + total_length))) {
+ attr_container_printf(
+ "Set attr failed: allocate memory failed.\r\n");
+ attr_container_free(attr_buf);
+ return false;
+ }
+
+ bh_memcpy_s(attr_cont1, p - (char *)attr_cont, attr_cont,
+ p - (char *)attr_cont);
+ bh_memcpy_s((char *)attr_cont1 + (unsigned)(p - (char *)attr_cont),
+ attr_end - p1, p1, attr_end - p1);
+ bh_memcpy_s((char *)attr_cont1 + (unsigned)(p - (char *)attr_cont)
+ + (unsigned)(attr_end - p1),
+ attr_len, attr_buf, attr_len);
+ p = attr_cont1->buf;
+ set_uint32(p, total_length);
+ *p_attr_cont = attr_cont1;
+ /* Free original buffer */
+ attr_container_free(attr_cont);
+ attr_container_free(attr_buf);
+ return true;
+ }
+ else {
+ /* key not found */
+ if ((uint32_t)(msg_end - attr_end) >= attr_len) {
+ bh_memcpy_s(attr_end, msg_end - attr_end, attr_buf, attr_len);
+ attr_container_inc_attr_num(attr_cont);
+ attr_container_free(attr_buf);
+ return true;
+ }
+
+ total_length += attr_len + 100;
+ if (!(attr_cont1 = attr_container_malloc(offsetof(attr_container_t, buf)
+ + total_length))) {
+ attr_container_printf(
+ "Set attr failed: allocate memory failed.\r\n");
+ attr_container_free(attr_buf);
+ return false;
+ }
+
+ bh_memcpy_s(attr_cont1, attr_end - (char *)attr_cont, attr_cont,
+ attr_end - (char *)attr_cont);
+ bh_memcpy_s((char *)attr_cont1
+ + (unsigned)(attr_end - (char *)attr_cont),
+ attr_len, attr_buf, attr_len);
+ attr_container_inc_attr_num(attr_cont1);
+ p = attr_cont1->buf;
+ set_uint32(p, total_length);
+ *p_attr_cont = attr_cont1;
+ /* Free original buffer */
+ attr_container_free(attr_cont);
+ attr_container_free(attr_buf);
+ return true;
+ }
+
+ return false;
+}
+
+bool
+attr_container_set_short(attr_container_t **p_attr_cont, const char *key,
+ short value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_SHORT, &value,
+ 2);
+}
+
+bool
+attr_container_set_int16(attr_container_t **p_attr_cont, const char *key,
+ int16_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_INT16, &value,
+ 2);
+}
+
+bool
+attr_container_set_int(attr_container_t **p_attr_cont, const char *key,
+ int value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_INT, &value, 4);
+}
+
+bool
+attr_container_set_int32(attr_container_t **p_attr_cont, const char *key,
+ int32_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_INT32, &value,
+ 4);
+}
+
+bool
+attr_container_set_uint32(attr_container_t **p_attr_cont, const char *key,
+ uint32_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_UINT32, &value,
+ 4);
+}
+
+bool
+attr_container_set_int64(attr_container_t **p_attr_cont, const char *key,
+ int64_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_INT64, &value,
+ 8);
+}
+
+bool
+attr_container_set_uint64(attr_container_t **p_attr_cont, const char *key,
+ uint64_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_UINT64, &value,
+ 8);
+}
+
+bool
+attr_container_set_byte(attr_container_t **p_attr_cont, const char *key,
+ int8_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_BYTE, &value, 1);
+}
+
+bool
+attr_container_set_int8(attr_container_t **p_attr_cont, const char *key,
+ int8_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_INT8, &value, 1);
+}
+
+bool
+attr_container_set_uint8(attr_container_t **p_attr_cont, const char *key,
+ uint8_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_UINT8, &value,
+ 1);
+}
+
+bool
+attr_container_set_uint16(attr_container_t **p_attr_cont, const char *key,
+ uint16_t value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_UINT16, &value,
+ 2);
+}
+
+bool
+attr_container_set_float(attr_container_t **p_attr_cont, const char *key,
+ float value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_FLOAT, &value,
+ 4);
+}
+
+bool
+attr_container_set_double(attr_container_t **p_attr_cont, const char *key,
+ double value)
+{
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_DOUBLE, &value,
+ 8);
+}
+
+bool
+attr_container_set_bool(attr_container_t **p_attr_cont, const char *key,
+ bool value)
+{
+ int8_t value1 = value ? 1 : 0;
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_BOOLEAN, &value1,
+ 1);
+}
+
+bool
+attr_container_set_string(attr_container_t **p_attr_cont, const char *key,
+ const char *value)
+{
+ if (!value) {
+ attr_container_printf("Set attr failed: invald input arguments.\r\n");
+ return false;
+ }
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_STRING, value,
+ strlen(value) + 1);
+}
+
+bool
+attr_container_set_bytearray(attr_container_t **p_attr_cont, const char *key,
+ const int8_t *value, unsigned length)
+{
+ if (!value) {
+ attr_container_printf("Set attr failed: invald input arguments.\r\n");
+ return false;
+ }
+ return attr_container_set_attr(p_attr_cont, key, ATTR_TYPE_BYTEARRAY, value,
+ length);
+}
+
+static const char *
+attr_container_get_attr(const attr_container_t *attr_cont, const char *key)
+{
+ const char *attr_addr;
+
+ if (!attr_cont || !key) {
+ attr_container_printf(
+ "Get attribute failed: invalid input arguments.\r\n");
+ return NULL;
+ }
+
+ if (!(attr_addr = attr_container_find_attr(attr_cont, key))) {
+ attr_container_printf("Get attribute failed: lookup key failed.\r\n");
+ return NULL;
+ }
+
+ /* key len + key + '\0' */
+ return attr_addr + 2 + strlen(key) + 1;
+}
+
+#define TEMPLATE_ATTR_BUF_TO_VALUE(attr, key, var_name) \
+ do { \
+ jvalue val; \
+ const char *addr = attr_container_get_attr(attr, key); \
+ uint8_t type; \
+ if (!addr) \
+ return 0; \
+ val.i64 = 0; \
+ type = *(uint8_t *)addr++; \
+ switch (type) { \
+ case ATTR_TYPE_BYTE: /* = ATTR_TYPE_INT8 */ \
+ case ATTR_TYPE_SHORT: /* = ATTR_TYPE_INT16 */ \
+ case ATTR_TYPE_INT: /* = ATTR_TYPE_INT32 */ \
+ case ATTR_TYPE_INT64: \
+ case ATTR_TYPE_UINT8: \
+ case ATTR_TYPE_UINT16: \
+ case ATTR_TYPE_UINT32: \
+ case ATTR_TYPE_UINT64: \
+ case ATTR_TYPE_FLOAT: \
+ case ATTR_TYPE_DOUBLE: \
+ case ATTR_TYPE_BOOLEAN: \
+ bh_memcpy_s(&val, sizeof(val.var_name), addr, \
+ 1 << (type & 3)); \
+ break; \
+ case ATTR_TYPE_STRING: \
+ { \
+ unsigned len = get_uint16(addr); \
+ addr += 2; \
+ if (len > sizeof(val.var_name)) \
+ len = sizeof(val.var_name); \
+ bh_memcpy_s(&val.var_name, sizeof(val.var_name), addr, len); \
+ break; \
+ } \
+ case ATTR_TYPE_BYTEARRAY: \
+ { \
+ unsigned len = get_uint32(addr); \
+ addr += 4; \
+ if (len > sizeof(val.var_name)) \
+ len = sizeof(val.var_name); \
+ bh_memcpy_s(&val.var_name, sizeof(val.var_name), addr, len); \
+ break; \
+ } \
+ default: \
+ bh_assert(0); \
+ break; \
+ } \
+ return val.var_name; \
+ } while (0)
+
+short
+attr_container_get_as_short(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, i16);
+}
+
+int16_t
+attr_container_get_as_int16(const attr_container_t *attr_cont, const char *key)
+{
+ return (int16_t)attr_container_get_as_short(attr_cont, key);
+}
+
+int
+attr_container_get_as_int(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, i32);
+}
+
+int32_t
+attr_container_get_as_int32(const attr_container_t *attr_cont, const char *key)
+{
+ return (int32_t)attr_container_get_as_int(attr_cont, key);
+}
+
+uint32_t
+attr_container_get_as_uint32(const attr_container_t *attr_cont, const char *key)
+{
+ return (uint32_t)attr_container_get_as_int(attr_cont, key);
+}
+
+int64_t
+attr_container_get_as_int64(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, i64);
+}
+
+uint64_t
+attr_container_get_as_uint64(const attr_container_t *attr_cont, const char *key)
+{
+ return (uint64_t)attr_container_get_as_int64(attr_cont, key);
+}
+
+int8_t
+attr_container_get_as_byte(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, i8);
+}
+
+int8_t
+attr_container_get_as_int8(const attr_container_t *attr_cont, const char *key)
+{
+ return attr_container_get_as_byte(attr_cont, key);
+}
+
+uint8_t
+attr_container_get_as_uint8(const attr_container_t *attr_cont, const char *key)
+{
+ return (uint8_t)attr_container_get_as_byte(attr_cont, key);
+}
+
+uint16_t
+attr_container_get_as_uint16(const attr_container_t *attr_cont, const char *key)
+{
+ return (uint16_t)attr_container_get_as_short(attr_cont, key);
+}
+
+float
+attr_container_get_as_float(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, f);
+}
+
+double
+attr_container_get_as_double(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, d);
+}
+
+bool
+attr_container_get_as_bool(const attr_container_t *attr_cont, const char *key)
+{
+ TEMPLATE_ATTR_BUF_TO_VALUE(attr_cont, key, z);
+}
+
+const int8_t *
+attr_container_get_as_bytearray(const attr_container_t *attr_cont,
+ const char *key, unsigned *array_length)
+{
+ const char *addr = attr_container_get_attr(attr_cont, key);
+ uint8_t type;
+ uint32_t length;
+
+ if (!addr)
+ return NULL;
+
+ if (!array_length) {
+ attr_container_printf("Get attribute failed: invalid input arguments.");
+ return NULL;
+ }
+
+ type = *(uint8_t *)addr++;
+ switch (type) {
+ case ATTR_TYPE_BYTE: /* = ATTR_TYPE_INT8 */
+ case ATTR_TYPE_SHORT: /* = ATTR_TYPE_INT16 */
+ case ATTR_TYPE_INT: /* = ATTR_TYPE_INT32 */
+ case ATTR_TYPE_INT64:
+ case ATTR_TYPE_UINT8:
+ case ATTR_TYPE_UINT16:
+ case ATTR_TYPE_UINT32:
+ case ATTR_TYPE_UINT64:
+ case ATTR_TYPE_FLOAT:
+ case ATTR_TYPE_DOUBLE:
+ case ATTR_TYPE_BOOLEAN:
+ length = 1 << (type & 3);
+ break;
+ case ATTR_TYPE_STRING:
+ length = get_uint16(addr);
+ addr += 2;
+ break;
+ case ATTR_TYPE_BYTEARRAY:
+ length = get_uint32(addr);
+ addr += 4;
+ break;
+ default:
+ return NULL;
+ }
+
+ *array_length = length;
+ return (const int8_t *)addr;
+}
+
+char *
+attr_container_get_as_string(const attr_container_t *attr_cont, const char *key)
+{
+ unsigned array_length;
+ return (char *)attr_container_get_as_bytearray(attr_cont, key,
+ &array_length);
+}
+
+const char *
+attr_container_get_tag(const attr_container_t *attr_cont)
+{
+ return attr_cont ? attr_cont->buf + sizeof(uint32_t) + sizeof(uint16_t)
+ : NULL;
+}
+
+bool
+attr_container_contain_key(const attr_container_t *attr_cont, const char *key)
+{
+ if (!attr_cont || !key || !strlen(key)) {
+ attr_container_printf(
+ "Check contain key failed: invalid input arguments.\r\n");
+ return false;
+ }
+ return attr_container_find_attr(attr_cont, key) ? true : false;
+}
+
+unsigned int
+attr_container_get_serialize_length(const attr_container_t *attr_cont)
+{
+ const char *p;
+
+ if (!attr_cont) {
+ attr_container_printf("Get container serialize length failed: invalid "
+ "input arguments.\r\n");
+ return 0;
+ }
+
+ p = attr_cont->buf;
+ return sizeof(uint16_t) + get_uint32(p);
+}
+
+bool
+attr_container_serialize(char *buf, const attr_container_t *attr_cont)
+{
+ const char *p;
+ uint16_t flags;
+ uint32_t length;
+
+ if (!buf || !attr_cont) {
+ attr_container_printf(
+ "Container serialize failed: invalid input arguments.\r\n");
+ return false;
+ }
+
+ p = attr_cont->buf;
+ length = sizeof(uint16_t) + get_uint32(p);
+ bh_memcpy_s(buf, length, attr_cont, length);
+ /* Set readonly */
+ flags = get_uint16((const char *)attr_cont);
+ set_uint16(buf, flags | (1 << ATTR_CONT_READONLY_SHIFT));
+
+ return true;
+}
+
+bool
+attr_container_is_constant(const attr_container_t *attr_cont)
+{
+ uint16_t flags;
+
+ if (!attr_cont) {
+ attr_container_printf(
+ "Container check const: invalid input arguments.\r\n");
+ return false;
+ }
+
+ flags = get_uint16((const char *)attr_cont);
+ return (flags & (1 << ATTR_CONT_READONLY_SHIFT)) ? true : false;
+}
+
+void
+attr_container_dump(const attr_container_t *attr_cont)
+{
+ uint32_t total_length;
+ uint16_t attr_num, i, type;
+ const char *p, *tag, *key;
+ jvalue value;
+
+ if (!attr_cont)
+ return;
+
+ tag = attr_container_get_tag(attr_cont);
+ if (!tag)
+ return;
+
+ attr_container_printf("Attribute container dump:\n");
+ attr_container_printf("Tag: %s\n", tag);
+
+ p = attr_container_get_attr_begin(attr_cont, &total_length, &attr_num);
+ if (!p)
+ return;
+
+ attr_container_printf("Attribute list:\n");
+ for (i = 0; i < attr_num; i++) {
+ key = p + 2;
+ /* Skip key len and key */
+ p += 2 + get_uint16(p);
+ type = *p++;
+ attr_container_printf(" key: %s", key);
+
+ switch (type) {
+ case ATTR_TYPE_BYTE: /* = ATTR_TYPE_INT8 */
+ bh_memcpy_s(&value.i8, 1, p, 1);
+ attr_container_printf(", type: byte, value: 0x%x\n",
+ value.i8 & 0xFF);
+ p++;
+ break;
+ case ATTR_TYPE_SHORT: /* = ATTR_TYPE_INT16 */
+ bh_memcpy_s(&value.i16, sizeof(int16_t), p, sizeof(int16_t));
+ attr_container_printf(", type: short, value: 0x%x\n",
+ value.i16 & 0xFFFF);
+ p += 2;
+ break;
+ case ATTR_TYPE_INT: /* = ATTR_TYPE_INT32 */
+ bh_memcpy_s(&value.i32, sizeof(int32_t), p, sizeof(int32_t));
+ attr_container_printf(", type: int, value: 0x%x\n", value.i32);
+ p += 4;
+ break;
+ case ATTR_TYPE_INT64:
+ bh_memcpy_s(&value.i64, sizeof(int64_t), p, sizeof(int64_t));
+ attr_container_printf(", type: int64, value: 0x%llx\n",
+ (long long unsigned int)(value.i64));
+ p += 8;
+ break;
+ case ATTR_TYPE_UINT8:
+ bh_memcpy_s(&value.u8, 1, p, 1);
+ attr_container_printf(", type: uint8, value: 0x%x\n", value.u8);
+ p++;
+ break;
+ case ATTR_TYPE_UINT16:
+ bh_memcpy_s(&value.u16, sizeof(uint16_t), p, sizeof(uint16_t));
+ attr_container_printf(", type: uint16, value: 0x%x\n",
+ value.u16);
+ p += 2;
+ break;
+ case ATTR_TYPE_UINT32:
+ bh_memcpy_s(&value.u32, sizeof(uint32_t), p, sizeof(uint32_t));
+ attr_container_printf(", type: uint32, value: 0x%x\n",
+ value.u32);
+ p += 4;
+ break;
+ case ATTR_TYPE_UINT64:
+ bh_memcpy_s(&value.u64, sizeof(uint64_t), p, sizeof(uint64_t));
+ attr_container_printf(", type: int64, value: 0x%llx\n",
+ (long long unsigned int)(value.u64));
+ p += 8;
+ break;
+ case ATTR_TYPE_FLOAT:
+ bh_memcpy_s(&value.f, sizeof(float), p, sizeof(float));
+ attr_container_printf(", type: float, value: %f\n", value.f);
+ p += 4;
+ break;
+ case ATTR_TYPE_DOUBLE:
+ bh_memcpy_s(&value.d, sizeof(double), p, sizeof(double));
+ attr_container_printf(", type: double, value: %f\n", value.d);
+ p += 8;
+ break;
+ case ATTR_TYPE_BOOLEAN:
+ bh_memcpy_s(&value.z, 1, p, 1);
+ attr_container_printf(", type: bool, value: 0x%x\n", value.z);
+ p++;
+ break;
+ case ATTR_TYPE_STRING:
+ attr_container_printf(", type: string, value: %s\n",
+ p + sizeof(uint16_t));
+ p += sizeof(uint16_t) + get_uint16(p);
+ break;
+ case ATTR_TYPE_BYTEARRAY:
+ attr_container_printf(", type: byte array, length: %d\n",
+ get_uint32(p));
+ p += sizeof(uint32_t) + get_uint32(p);
+ break;
+ default:
+ bh_assert(0);
+ break;
+ }
+ }
+
+ attr_container_printf("\n");
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/attr_container.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/attr_container.h
new file mode 100644
index 000000000..f5d8759b8
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/attr_container.h
@@ -0,0 +1,596 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _ATTR_CONTAINER_H_
+#define _ATTR_CONTAINER_H_
+
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <stddef.h>
+#include <stdbool.h>
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* Attribute type */
+enum {
+ ATTR_TYPE_BEGIN = 0,
+ ATTR_TYPE_BYTE = ATTR_TYPE_BEGIN,
+ ATTR_TYPE_INT8 = ATTR_TYPE_BYTE,
+ ATTR_TYPE_SHORT,
+ ATTR_TYPE_INT16 = ATTR_TYPE_SHORT,
+ ATTR_TYPE_INT,
+ ATTR_TYPE_INT32 = ATTR_TYPE_INT,
+ ATTR_TYPE_INT64,
+ ATTR_TYPE_UINT8,
+ ATTR_TYPE_UINT16,
+ ATTR_TYPE_UINT32,
+ ATTR_TYPE_UINT64,
+ /**
+ * Why ATTR_TYPE_FLOAT = 10?
+ * We determine the number of bytes that should be copied through 1<<(type &
+ * 3). ATTR_TYPE_BYTE = 0, so the number of bytes is 1 << 0 = 1.
+ * ATTR_TYPE_UINT64 = 7, so the number of bytes is 1 << 3 = 8.
+ * Since the float type takes up 4 bytes, ATTR_TYPE_FLOAT should be 10.
+ * Calculation: (1 << (10&3)) = (1 << 2) = 4
+ */
+ ATTR_TYPE_FLOAT = 10,
+ ATTR_TYPE_DOUBLE,
+ ATTR_TYPE_BOOLEAN,
+ ATTR_TYPE_STRING,
+ ATTR_TYPE_BYTEARRAY,
+ ATTR_TYPE_END = ATTR_TYPE_BYTEARRAY
+};
+
+#define ATTR_CONT_READONLY_SHIFT 2
+
+typedef struct attr_container {
+ /* container flag:
+ * bit0, bit1 denote the implemenation algorithm, 00: buffer, 01: link list
+ * bit2 denotes the readonly flag: 1 is readonly and attr cannot be set
+ */
+ char flags[2];
+ /**
+ * Buffer format
+ * for buffer implementation:
+ * buf length (4 bytes)
+ * tag length (2 bytes)
+ * tag
+ * attr num (2bytes)
+ * attr[0..n-1]:
+ * attr key length (2 bytes)
+ * attr type (1byte)
+ * attr value (length depends on attr type)
+ */
+ char buf[1];
+} attr_container_t;
+
+/**
+ * Create attribute container
+ *
+ * @param tag tag of current attribute container
+ *
+ * @return the created attribute container, NULL if failed
+ */
+attr_container_t *
+attr_container_create(const char *tag);
+
+/**
+ * Destroy attribute container
+ *
+ * @param attr_cont the attribute container to destroy
+ */
+void
+attr_container_destroy(const attr_container_t *attr_cont);
+
+/**
+ * Set short attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_short(attr_container_t **p_attr_cont, const char *key,
+ short value);
+
+/**
+ * Set int16 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_int16(attr_container_t **p_attr_cont, const char *key,
+ int16_t value);
+
+/**
+ * Set int attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_int(attr_container_t **p_attr_cont, const char *key,
+ int value);
+
+/**
+ * Set int32 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_int32(attr_container_t **p_attr_cont, const char *key,
+ int32_t value);
+
+/**
+ * Set uint32 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_uint32(attr_container_t **p_attr_cont, const char *key,
+ uint32_t value);
+
+/**
+ * Set int64 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_int64(attr_container_t **p_attr_cont, const char *key,
+ int64_t value);
+
+/**
+ * Set uint64 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_uint64(attr_container_t **p_attr_cont, const char *key,
+ uint64_t value);
+
+/**
+ * Set byte attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_byte(attr_container_t **p_attr_cont, const char *key,
+ int8_t value);
+
+/**
+ * Set int8 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_int8(attr_container_t **p_attr_cont, const char *key,
+ int8_t value);
+
+/**
+ * Set uint8 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_uint8(attr_container_t **p_attr_cont, const char *key,
+ uint8_t value);
+
+/**
+ * Set uint16 attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_uint16(attr_container_t **p_attr_cont, const char *key,
+ uint16_t value);
+
+/**
+ * Set float attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_float(attr_container_t **p_attr_cont, const char *key,
+ float value);
+
+/**
+ * Set double attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_double(attr_container_t **p_attr_cont, const char *key,
+ double value);
+
+/**
+ * Set bool attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_bool(attr_container_t **p_attr_cont, const char *key,
+ bool value);
+
+/**
+ * Set string attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the attribute value
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_string(attr_container_t **p_attr_cont, const char *key,
+ const char *value);
+
+/**
+ * Set bytearray attribute in attribute container
+ *
+ * @param p_attr_cont pointer to attribute container to set attribute, and
+ * return the new attribute container if it is re-created
+ * @param key the attribute key
+ * @param value the bytearray buffer
+ * @param length the bytearray length
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_set_bytearray(attr_container_t **p_attr_cont, const char *key,
+ const int8_t *value, unsigned length);
+
+/**
+ * Get tag of current attribute container
+ *
+ * @param attr_cont the attribute container
+ *
+ * @return tag of current attribute container
+ */
+const char *
+attr_container_get_tag(const attr_container_t *attr_cont);
+
+/**
+ * Get attribute number of current attribute container
+ *
+ * @param attr_cont the attribute container
+ *
+ * @return attribute number of current attribute container
+ */
+uint16_t
+attr_container_get_attr_num(const attr_container_t *attr_cont);
+
+/**
+ * Whether the attribute container contains an attribute key.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return true if key is contained in message, false otherwise
+ */
+bool
+attr_container_contain_key(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as short value,
+ * return 0 if attribute isn't found in message.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the short value of the attribute, 0 if key isn't found
+ */
+short
+attr_container_get_as_short(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as int16 value,
+ * return 0 if attribute isn't found in message.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the short value of the attribute, 0 if key isn't found
+ */
+int16_t
+attr_container_get_as_int16(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as int value,
+ * return 0 if attribute isn't found in message.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the int value of the attribute, 0 if key isn't found
+ */
+int
+attr_container_get_as_int(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as int32 value,
+ * return 0 if attribute isn't found in message.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the int value of the attribute, 0 if key isn't found
+ */
+int32_t
+attr_container_get_as_int32(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as uint32 value,
+ * return 0 if attribute isn't found in message.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the unsigned int value of the attribute, 0 if key isn't found
+ */
+uint32_t
+attr_container_get_as_uint32(const attr_container_t *attr_cont,
+ const char *key);
+
+/**
+ * Get attribute from attribute container and return it as int64 value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the long value of the attribute, 0 if key isn't found
+ */
+int64_t
+attr_container_get_as_int64(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as uint64 value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the unsigned long value of the attribute, 0 if key isn't found
+ */
+uint64_t
+attr_container_get_as_uint64(const attr_container_t *attr_cont,
+ const char *key);
+
+/**
+ * Get attribute from attribute container and return it as byte value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the byte value of the attribute, 0 if key isn't found
+ */
+int8_t
+attr_container_get_as_byte(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as int8 value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the byte value of the attribute, 0 if key isn't found
+ */
+int8_t
+attr_container_get_as_int8(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as uint8 value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the uint8 value of the attribute, 0 if key isn't found
+ */
+uint8_t
+attr_container_get_as_uint8(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as uint16 value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the char value of the attribute, 0 if key isn't found
+ */
+uint16_t
+attr_container_get_as_uint16(const attr_container_t *attr_cont,
+ const char *key);
+
+/**
+ * Get attribute from attribute container and return it as float value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the float value of the attribute, 0 if key isn't found
+ */
+float
+attr_container_get_as_float(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as double value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the double value of the attribute, 0 if key isn't found
+ */
+double
+attr_container_get_as_double(const attr_container_t *attr_cont,
+ const char *key);
+
+/**
+ * Get attribute from attribute container and return it as bool value,
+ * return false if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the bool value of the attribute, 0 if key isn't found
+ */
+bool
+attr_container_get_as_bool(const attr_container_t *attr_cont, const char *key);
+
+/**
+ * Get attribute from attribute container and return it as string value,
+ * return NULL if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the string value of the attribute, NULL if key isn't found
+ */
+char *
+attr_container_get_as_string(const attr_container_t *attr_cont,
+ const char *key);
+
+/**
+ * Get attribute from attribute container and return it as bytearray value,
+ * return 0 if attribute isn't found in attribute container.
+ *
+ * @param attr_cont the attribute container
+ * @param key the attribute key
+ *
+ * @return the bytearray value of the attribute, NULL if key isn't found
+ */
+const int8_t *
+attr_container_get_as_bytearray(const attr_container_t *attr_cont,
+ const char *key, unsigned *array_length);
+
+/**
+ * Get the buffer size of attribute container
+ *
+ * @param attr_cont the attribute container
+ *
+ * @return the buffer size of attribute container
+ */
+unsigned
+attr_container_get_serialize_length(const attr_container_t *attr_cont);
+
+/**
+ * Serialize attribute container to a buffer
+ *
+ * @param buf the buffer to receive the serialized data
+ * @param attr_cont the attribute container to be serialized
+ *
+ * @return true if success, false otherwise
+ */
+bool
+attr_container_serialize(char *buf, const attr_container_t *attr_cont);
+
+/**
+ * Whether the attribute container is const, or set attribute isn't supported
+ *
+ * @param attr_cont the attribute container
+ *
+ * @return true if const, false otherwise
+ */
+bool
+attr_container_is_constant(const attr_container_t *attr_cont);
+
+void
+attr_container_dump(const attr_container_t *attr_cont);
+
+#ifndef attr_container_malloc
+#define attr_container_malloc WA_MALLOC
+#endif
+
+#ifndef attr_container_free
+#define attr_container_free WA_FREE
+#endif
+
+#ifndef attr_container_printf
+#define attr_container_printf printf
+#endif
+
+#ifdef __cplusplus
+} /* end of extern "C" */
+#endif
+
+#endif /* end of _ATTR_CONTAINER_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/shared_utils.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/shared_utils.h
new file mode 100644
index 000000000..8155ea1f7
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/shared_utils.h
@@ -0,0 +1,155 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _SHARED_UTILS_H_
+#define _SHARED_UTILS_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#define FMT_ATTR_CONTAINER 99
+#define FMT_APP_RAW_BINARY 98
+
+/* the request structure */
+typedef struct request {
+ // message id
+ uint32 mid;
+
+ // url of the request
+ char *url;
+
+ // action of the request, can be PUT/GET/POST/DELETE
+ int action;
+
+ // payload format, currently only support attr_container_t type
+ int fmt;
+
+ // payload of the request, currently only support attr_container_t type
+ void *payload;
+
+ // length in bytes of the payload
+ int payload_len;
+
+ // sender of the request
+ unsigned long sender;
+} request_t;
+
+/* the response structure */
+typedef struct response {
+ // message id
+ uint32 mid;
+
+ // status of the response
+ int status;
+
+ // payload format
+ int fmt;
+
+ // payload of the response,
+ void *payload;
+
+ // length in bytes of the payload
+ int payload_len;
+
+ // receiver of the response
+ unsigned long reciever;
+} response_t;
+
+int
+check_url_start(const char *url, int url_len, const char *leading_str);
+
+bool
+match_url(char *pattern, char *matched);
+
+char *
+find_key_value(char *buffer, int buffer_len, char *key, char *value,
+ int value_len, char delimiter);
+
+request_t *
+clone_request(request_t *request);
+
+void
+request_cleaner(request_t *request);
+
+response_t *
+clone_response(response_t *response);
+
+void
+response_cleaner(response_t *response);
+
+/**
+ * @brief Set fields of response.
+ *
+ * @param response pointer of the response to be set
+ * @param status status of response
+ * @param fmt format of the response payload
+ * @param payload payload of the response
+ * @param payload_len length in bytes of the response payload
+ *
+ * @return pointer to the response
+ *
+ * @warning the response pointer MUST NOT be NULL
+ */
+response_t *
+set_response(response_t *response, int status, int fmt, const char *payload,
+ int payload_len);
+
+/**
+ * @brief Make a response for a request.
+ *
+ * @param request pointer of the request
+ * @param response pointer of the response to be made
+ *
+ * @return pointer to the response
+ *
+ * @warning the request and response pointers MUST NOT be NULL
+ */
+response_t *
+make_response_for_request(request_t *request, response_t *response);
+
+/**
+ * @brief Initialize a request.
+ *
+ * @param request pointer of the request to be initialized
+ * @param url url of the request
+ * @param action action of the request
+ * @param fmt format of the request payload
+ * @param payload payload of the request
+ * @param payload_len length in bytes of the request payload
+ *
+ * @return pointer to the request
+ *
+ * @warning the request pointer MUST NOT be NULL
+ */
+request_t *
+init_request(request_t *request, char *url, int action, int fmt, void *payload,
+ int payload_len);
+
+char *
+pack_request(request_t *request, int *size);
+
+request_t *
+unpack_request(char *packet, int size, request_t *request);
+
+char *
+pack_response(response_t *response, int *size);
+
+response_t *
+unpack_response(char *packet, int size, response_t *response);
+
+void
+free_req_resp_packet(char *packet);
+
+char *
+wa_strdup(const char *str);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _SHARED_UTILS_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/wgl_shared_utils.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/wgl_shared_utils.h
new file mode 100644
index 000000000..86d864e41
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/bi-inc/wgl_shared_utils.h
@@ -0,0 +1,101 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef WAMR_GRAPHIC_LIBRARY_SHARED_UTILS_H
+#define WAMR_GRAPHIC_LIBRARY_SHARED_UTILS_H
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdbool.h>
+
+/* Object native function IDs */
+enum {
+ OBJ_FUNC_ID_DEL,
+ OBJ_FUNC_ID_DEL_ASYNC,
+ OBJ_FUNC_ID_CLEAN,
+ OBJ_FUNC_ID_SET_EVT_CB,
+ OBJ_FUNC_ID_ALIGN,
+
+ /* Number of functions */
+ _OBJ_FUNC_ID_NUM,
+};
+
+/* Button native function IDs */
+enum {
+ BTN_FUNC_ID_CREATE,
+ BTN_FUNC_ID_SET_TOGGLE,
+ BTN_FUNC_ID_SET_STATE,
+ BTN_FUNC_ID_TOGGLE,
+ BTN_FUNC_ID_SET_INK_IN_TIME,
+ BTN_FUNC_ID_SET_INK_WAIT_TIME,
+ BTN_FUNC_ID_SET_INK_OUT_TIME,
+ BTN_FUNC_ID_GET_STATE,
+ BTN_FUNC_ID_GET_TOGGLE,
+ BTN_FUNC_ID_GET_INK_IN_TIME,
+ BTN_FUNC_ID_GET_INK_WAIT_TIME,
+ BTN_FUNC_ID_GET_INK_OUT_TIME,
+ /* Number of functions */
+ _BTN_FUNC_ID_NUM,
+};
+
+/* Check box native function IDs */
+enum {
+ CB_FUNC_ID_CREATE,
+ CB_FUNC_ID_SET_TEXT,
+ CB_FUNC_ID_SET_STATIC_TEXT,
+ CB_FUNC_ID_GET_TEXT,
+ CB_FUNC_ID_GET_TEXT_LENGTH,
+
+ /* Number of functions */
+ _CB_FUNC_ID_NUM,
+};
+
+/* List native function IDs */
+enum {
+ LIST_FUNC_ID_CREATE,
+ LIST_FUNC_ID_ADD_BTN,
+
+ /* Number of functions */
+ _LIST_FUNC_ID_NUM,
+};
+
+/* Label native function IDs */
+enum {
+ LABEL_FUNC_ID_CREATE,
+ LABEL_FUNC_ID_SET_TEXT,
+ LABEL_FUNC_ID_SET_ARRAY_TEXT,
+ LABEL_FUNC_ID_SET_STATIC_TEXT,
+ LABEL_FUNC_ID_SET_LONG_MODE,
+ LABEL_FUNC_ID_SET_ALIGN,
+ LABEL_FUNC_ID_SET_RECOLOR,
+ LABEL_FUNC_ID_SET_BODY_DRAW,
+ LABEL_FUNC_ID_SET_ANIM_SPEED,
+ LABEL_FUNC_ID_SET_TEXT_SEL_START,
+ LABEL_FUNC_ID_SET_TEXT_SEL_END,
+ LABEL_FUNC_ID_GET_TEXT,
+ LABEL_FUNC_ID_GET_TEXT_LENGTH,
+ LABEL_FUNC_ID_GET_LONG_MODE,
+ LABEL_FUNC_ID_GET_ALIGN,
+ LABEL_FUNC_ID_GET_RECOLOR,
+ LABEL_FUNC_ID_GET_BODY_DRAW,
+ LABEL_FUNC_ID_GET_ANIM_SPEED,
+ LABEL_FUNC_ID_GET_LETTER_POS,
+ LABEL_FUNC_ID_GET_TEXT_SEL_START,
+ LABEL_FUNC_ID_GET_TEXT_SEL_END,
+ LABEL_FUNC_ID_INS_TEXT,
+ LABEL_FUNC_ID_CUT_TEXT,
+ /* Number of functions */
+ _LABEL_FUNC_ID_NUM,
+};
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* WAMR_GRAPHIC_LIBRARY_SHARED_UTILS_H */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.cmake
new file mode 100644
index 000000000..48ebe0a33
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.cmake
@@ -0,0 +1,15 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (NATIVE_INTERFACE_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${NATIVE_INTERFACE_DIR})
+
+
+file (GLOB_RECURSE source_all ${NATIVE_INTERFACE_DIR}/*.c)
+
+set (NATIVE_INTERFACE_SOURCE ${source_all})
+
+set (WASM_APP_BI_INC_DIR "${NATIVE_INTERFACE_DIR}/bi-inc")
+LIST (APPEND RUNTIME_LIB_HEADER_LIST "${NATIVE_INTERFACE_DIR}/native_interface.h")
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.h
new file mode 100644
index 000000000..ce9f24780
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/native_interface.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _NATIVE_INTERFACE_H_
+#define _NATIVE_INTERFACE_H_
+
+/* Note: the bh_plaform.h is the only head file separately
+ implemented by both [app] and [native] worlds */
+#include "bh_platform.h"
+
+#endif /* end of _NATIVE_INTERFACE_H */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/restful_utils.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/restful_utils.c
new file mode 100644
index 000000000..03e86a699
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app-native-shared/restful_utils.c
@@ -0,0 +1,493 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <stdbool.h>
+#include <stdio.h>
+
+#include "bi-inc/shared_utils.h"
+
+/* Serialization of request and response message
+ *
+ * Choices:
+ * We considered a few options:
+ * 1. coap
+ * 2. flatbuffer
+ * 3. cbor
+ * 4. attr-containers of our own
+ * 5. customized serialization for request/response
+ *
+ * Now we choose the #5 mainly because we need to quickly get the URL for
+ * dispatching and sometimes we want to change the URL in the original packet.
+ * the request format: fixed part: version: (1 byte), code (1 byte), fmt(2
+ * byte), mid (4 bytes), sender_id(4 bytes), url_len(2 bytes),
+ * payload_len(4bytes) dynamic part: url (bytes in url_len), payload
+ *
+ * response format:
+ * fixed part: (1 byte), code (1 byte), fmt(2 byte), mid (4 bytes), sender_id(4
+ * bytes), payload_len(4bytes) dynamic part: payload
+ */
+#define REQUES_PACKET_VER 1
+#define REQUEST_PACKET_FIX_PART_LEN 18
+#define REQUEST_PACKET_URL_OFFSET REQUEST_PACKET_FIX_PART_LEN
+#define REQUEST_PACKET_URL_LEN \
+ *((uint16 *)((char *)buffer + 12)) /* to ensure little endian */
+#define REQUEST_PACKET_PAYLOAD_LEN \
+ *((uint32 *)((char *)buffer + 14)) /* to ensure little endian */
+#define REQUEST_PACKET_URL(buffer) ((char *)buffer + REQUEST_PACKET_URL_OFFSET)
+#define REQUEST_PACKET_PAYLOAD(buffer) \
+ ((char *)buffer + REQUEST_PACKET_URL_OFFSET \
+ + REQUEST_PACKET_URL_LEN(buffer))
+
+#define RESPONSE_PACKET_FIX_PART_LEN 16
+
+char *
+pack_request(request_t *request, int *size)
+{
+ int url_len = strlen(request->url) + 1;
+ int len = REQUEST_PACKET_FIX_PART_LEN + url_len + request->payload_len;
+ uint16 u16;
+ uint32 u32;
+ char *packet;
+
+ if ((packet = (char *)WA_MALLOC(len)) == NULL)
+ return NULL;
+
+ /* TODO: ensure little endian for words and dwords */
+ *packet = REQUES_PACKET_VER;
+ *((uint8 *)(packet + 1)) = request->action;
+
+ u16 = htons(request->fmt);
+ memcpy(packet + 2, &u16, 2);
+
+ u32 = htonl(request->mid);
+ memcpy(packet + 4, &u32, 4);
+
+ u32 = htonl(request->sender);
+ memcpy(packet + 8, &u32, 4);
+
+ u16 = htons(url_len);
+ memcpy(packet + 12, &u16, 2);
+
+ u32 = htonl(request->payload_len);
+ memcpy(packet + 14, &u32, 4);
+
+ strcpy(packet + REQUEST_PACKET_URL_OFFSET, request->url);
+ memcpy(packet + REQUEST_PACKET_URL_OFFSET + url_len, request->payload,
+ request->payload_len);
+
+ *size = len;
+ return packet;
+}
+
+void
+free_req_resp_packet(char *packet)
+{
+ WA_FREE(packet);
+}
+
+request_t *
+unpack_request(char *packet, int size, request_t *request)
+{
+ uint16 url_len, u16;
+ uint32 payload_len, u32;
+
+ if (*packet != REQUES_PACKET_VER) {
+ return NULL;
+ }
+ if (size < REQUEST_PACKET_FIX_PART_LEN) {
+ return NULL;
+ }
+
+ memcpy(&u16, packet + 12, 2);
+ url_len = ntohs(u16);
+
+ memcpy(&u32, packet + 14, 4);
+ payload_len = ntohl(u32);
+
+ if (size != (REQUEST_PACKET_FIX_PART_LEN + url_len + payload_len)) {
+ return NULL;
+ }
+
+ if (*(packet + REQUEST_PACKET_FIX_PART_LEN + url_len - 1) != 0) {
+ return NULL;
+ }
+
+ request->action = *((uint8 *)(packet + 1));
+
+ memcpy(&u16, packet + 2, 2);
+ request->fmt = ntohs(u16);
+
+ memcpy(&u32, packet + 4, 4);
+ request->mid = ntohl(u32);
+
+ memcpy(&u32, packet + 8, 4);
+ request->sender = ntohl(u32);
+
+ request->payload_len = payload_len;
+ request->url = REQUEST_PACKET_URL(packet);
+
+ if (payload_len > 0)
+ request->payload = packet + REQUEST_PACKET_URL_OFFSET + url_len;
+ else
+ request->payload = NULL;
+
+ return request;
+}
+
+char *
+pack_response(response_t *response, int *size)
+{
+ int len = RESPONSE_PACKET_FIX_PART_LEN + response->payload_len;
+ uint16 u16;
+ uint32 u32;
+ char *packet;
+
+ if ((packet = (char *)WA_MALLOC(len)) == NULL)
+ return NULL;
+
+ /* TODO: ensure little endian for words and dwords */
+ *packet = REQUES_PACKET_VER;
+ *((uint8 *)(packet + 1)) = response->status;
+
+ u16 = htons(response->fmt);
+ memcpy(packet + 2, &u16, 2);
+
+ u32 = htonl(response->mid);
+ memcpy(packet + 4, &u32, 4);
+
+ u32 = htonl(response->reciever);
+ memcpy(packet + 8, &u32, 4);
+
+ u32 = htonl(response->payload_len);
+ memcpy(packet + 12, &u32, 4);
+
+ memcpy(packet + RESPONSE_PACKET_FIX_PART_LEN, response->payload,
+ response->payload_len);
+
+ *size = len;
+ return packet;
+}
+
+response_t *
+unpack_response(char *packet, int size, response_t *response)
+{
+ uint16 u16;
+ uint32 payload_len, u32;
+
+ if (*packet != REQUES_PACKET_VER)
+ return NULL;
+
+ if (size < RESPONSE_PACKET_FIX_PART_LEN)
+ return NULL;
+
+ memcpy(&u32, packet + 12, 4);
+ payload_len = ntohl(u32);
+ if (size != (RESPONSE_PACKET_FIX_PART_LEN + payload_len))
+ return NULL;
+
+ response->status = *((uint8 *)(packet + 1));
+
+ memcpy(&u16, packet + 2, 2);
+ response->fmt = ntohs(u16);
+
+ memcpy(&u32, packet + 4, 4);
+ response->mid = ntohl(u32);
+
+ memcpy(&u32, packet + 8, 4);
+ response->reciever = ntohl(u32);
+
+ response->payload_len = payload_len;
+ if (payload_len > 0)
+ response->payload = packet + RESPONSE_PACKET_FIX_PART_LEN;
+ else
+ response->payload = NULL;
+
+ return response;
+}
+
+request_t *
+clone_request(request_t *request)
+{
+ /* deep clone */
+ request_t *req = (request_t *)WA_MALLOC(sizeof(request_t));
+ if (req == NULL)
+ return NULL;
+
+ memset(req, 0, sizeof(*req));
+ req->action = request->action;
+ req->fmt = request->fmt;
+ req->url = wa_strdup(request->url);
+ req->sender = request->sender;
+ req->mid = request->mid;
+
+ if (req->url == NULL)
+ goto fail;
+
+ req->payload_len = request->payload_len;
+
+ if (request->payload_len) {
+ req->payload = (char *)WA_MALLOC(request->payload_len);
+ if (!req->payload)
+ goto fail;
+ memcpy(req->payload, request->payload, request->payload_len);
+ }
+ else {
+ /* when payload_len is 0, the payload may be used for
+ carrying some handle or integer */
+ req->payload = request->payload;
+ }
+
+ return req;
+
+fail:
+ request_cleaner(req);
+ return NULL;
+}
+
+void
+request_cleaner(request_t *request)
+{
+ if (request->url != NULL)
+ WA_FREE(request->url);
+ if (request->payload != NULL && request->payload_len > 0)
+ WA_FREE(request->payload);
+
+ WA_FREE(request);
+}
+
+void
+response_cleaner(response_t *response)
+{
+ if (response->payload != NULL && response->payload_len > 0)
+ WA_FREE(response->payload);
+
+ WA_FREE(response);
+}
+
+response_t *
+clone_response(response_t *response)
+{
+ response_t *clone = (response_t *)WA_MALLOC(sizeof(response_t));
+
+ if (clone == NULL)
+ return NULL;
+
+ memset(clone, 0, sizeof(*clone));
+ clone->fmt = response->fmt;
+ clone->mid = response->mid;
+ clone->status = response->status;
+ clone->reciever = response->reciever;
+ clone->payload_len = response->payload_len;
+ if (clone->payload_len) {
+ clone->payload = (char *)WA_MALLOC(response->payload_len);
+ if (!clone->payload)
+ goto fail;
+ memcpy(clone->payload, response->payload, response->payload_len);
+ }
+ else {
+ /* when payload_len is 0, the payload may be used for
+ carrying some handle or integer */
+ clone->payload = response->payload;
+ }
+ return clone;
+
+fail:
+ response_cleaner(clone);
+ return NULL;
+}
+
+response_t *
+set_response(response_t *response, int status, int fmt, const char *payload,
+ int payload_len)
+{
+ response->payload = (void *)payload;
+ response->payload_len = payload_len;
+ response->status = status;
+ response->fmt = fmt;
+ return response;
+}
+
+response_t *
+make_response_for_request(request_t *request, response_t *response)
+{
+ response->mid = request->mid;
+ response->reciever = request->sender;
+
+ return response;
+}
+
+static unsigned int mid = 0;
+
+request_t *
+init_request(request_t *request, char *url, int action, int fmt, void *payload,
+ int payload_len)
+{
+ request->url = url;
+ request->action = action;
+ request->fmt = fmt;
+ request->payload = payload;
+ request->payload_len = payload_len;
+ request->mid = ++mid;
+
+ return request;
+}
+
+/*
+ check if the "url" is starting with "leading_str"
+ return: 0 - not match; >0 - the offset of matched url, include any "/" at the
+ end notes:
+ 1. it ensures the leading_str "/abc" can pass "/abc/cde" and "/abc/, but fail
+ "/ab" and "/abcd". leading_str "/abc/" can pass "/abc"
+ 2. it omit the '/' at the first char
+ 3. it ensure the leading_str "/abc" can pass "/abc?cde
+ */
+
+int
+check_url_start(const char *url, int url_len, const char *leading_str)
+{
+ int offset = 0;
+ if (*leading_str == '/')
+ leading_str++;
+ if (url_len > 0 && *url == '/') {
+ url_len--;
+ url++;
+ offset++;
+ }
+
+ int len = strlen(leading_str);
+ if (len == 0)
+ return 0;
+
+ /* ensure leading_str not end with "/" */
+ if (leading_str[len - 1] == '/') {
+ len--;
+ if (len == 0)
+ return 0;
+ }
+
+ /* equal length */
+ if (url_len == len) {
+ if (memcmp(url, leading_str, url_len) == 0) {
+ return (offset + len);
+ }
+ else {
+ return 0;
+ }
+ }
+
+ if (url_len < len)
+ return 0;
+ else if (memcmp(url, leading_str, len) != 0)
+ return 0;
+ else if (url[len] != '/' && url[len] != '?')
+ return 0;
+ else
+ return (offset + len + 1);
+}
+
+// * @pattern:
+// * sample 1: /abcd, match /abcd only
+// * sample 2: /abcd/ match match "/abcd" and "/abcd/*"
+// * sample 3: /abcd*, match any url started with "/abcd"
+// * sample 4: /abcd/*, exclude "/abcd"
+
+bool
+match_url(char *pattern, char *matched)
+{
+ if (*pattern == '/')
+ pattern++;
+ if (*matched == '/')
+ matched++;
+
+ int matched_len = strlen(matched);
+ if (matched_len == 0)
+ return false;
+
+ if (matched[matched_len - 1] == '/') {
+ matched_len--;
+ if (matched_len == 0)
+ return false;
+ }
+
+ int len = strlen(pattern);
+ if (len == 0)
+ return false;
+
+ if (pattern[len - 1] == '/') {
+ len--;
+ if (strncmp(pattern, matched, len) != 0)
+ return false;
+
+ if (len == matched_len)
+ return true;
+
+ if (matched_len > len && matched[len] == '/')
+ return true;
+
+ return false;
+ }
+ else if (pattern[len - 1] == '*') {
+ if (pattern[len - 2] == '/') {
+ if (strncmp(pattern, matched, len - 1) == 0)
+ return true;
+ else
+ return false;
+ }
+ else {
+ return (strncmp(pattern, matched, len - 1) == 0);
+ }
+ }
+ else {
+ return (strcmp(pattern, matched) == 0);
+ }
+}
+
+/*
+ * get the value of the key from following format buffer:
+ * key1=value1;key2=value2;key3=value3
+ */
+char *
+find_key_value(char *buffer, int buffer_len, char *key, char *value,
+ int value_len, char delimiter)
+{
+ char *p = buffer;
+ int remaining = buffer_len;
+ int key_len = strlen(key);
+
+ while (*p != 0 && remaining > 0) {
+ while (*p == ' ' || *p == delimiter) {
+ p++;
+ remaining--;
+ }
+
+ if (remaining <= key_len)
+ return NULL;
+
+ /* find the key */
+ if (0 == strncmp(p, key, key_len) && p[key_len] == '=') {
+ p += (key_len + 1);
+ remaining -= (key_len + 1);
+ char *v = value;
+ memset(value, 0, value_len);
+ value_len--; /* ensure last char is 0 */
+ while (*p != delimiter && remaining > 0 && value_len > 0) {
+ *v++ = *p++;
+ remaining--;
+ value_len--;
+ }
+ return value;
+ }
+
+ /* goto next key */
+ while (*p != delimiter && remaining > 0) {
+ p++;
+ remaining--;
+ }
+ }
+
+ return NULL;
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_ext_lib_export.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_ext_lib_export.c
new file mode 100644
index 000000000..532491b43
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_ext_lib_export.c
@@ -0,0 +1,38 @@
+#include "lib_export.h"
+
+#ifdef APP_FRAMEWORK_SENSOR
+#include "sensor_native_api.h"
+#endif
+
+#ifdef APP_FRAMEWORK_CONNECTION
+#include "connection_native_api.h"
+#endif
+
+#ifdef APP_FRAMEWORK_WGL
+#include "gui_native_api.h"
+#endif
+
+/* More header file here */
+
+static NativeSymbol extended_native_symbol_defs[] = {
+#ifdef APP_FRAMEWORK_SENSOR
+#include "runtime_sensor.inl"
+#endif
+
+#ifdef APP_FRAMEWORK_CONNECTION
+#include "connection.inl"
+#endif
+
+#ifdef APP_FRAMEWORK_WGL
+#include "wamr_gui.inl"
+#endif
+
+ /* More inl file here */
+};
+
+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);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_framework.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_framework.cmake
new file mode 100644
index 000000000..b8a63d856
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/app_framework.cmake
@@ -0,0 +1,93 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+
+add_definitions (-DWASM_ENABLE_APP_FRAMEWORK=1)
+
+set (APP_FRAMEWORK_ROOT_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+if ( NOT DEFINED APP_FRAMEWORK_INCLUDE_TYPE )
+ LIST (APPEND WASM_APP_LIB_SOURCE_ALL ${CMAKE_CURRENT_LIST_DIR}/app_ext_lib_export.c)
+endif()
+
+# app-native-shared and base are required
+include (${APP_FRAMEWORK_ROOT_DIR}/app-native-shared/native_interface.cmake)
+LIST (APPEND WASM_APP_SOURCE_ALL ${NATIVE_INTERFACE_SOURCE})
+
+MACRO(SUBDIRLIST result curdir)
+ FILE(GLOB children RELATIVE ${curdir} ${curdir}/*)
+ SET(dirlist "")
+ FOREACH(child ${children})
+ IF(IS_DIRECTORY ${curdir}/${child})
+ LIST(APPEND dirlist ${child})
+ ENDIF()
+ ENDFOREACH()
+ SET(${result} ${dirlist})
+ENDMACRO()
+
+function (add_module_native arg)
+ message ("Add native module ${ARGV0}")
+ include (${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/native/wasm_lib.cmake)
+
+ file (GLOB header
+ ${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/native/*.h
+ ${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/native/*.inl
+ )
+
+ LIST (APPEND WASM_APP_LIBS_DIR ${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/native)
+ set (WASM_APP_LIBS_DIR ${WASM_APP_LIBS_DIR} PARENT_SCOPE)
+
+ LIST (APPEND RUNTIME_LIB_HEADER_LIST ${header})
+ set (RUNTIME_LIB_HEADER_LIST ${RUNTIME_LIB_HEADER_LIST} PARENT_SCOPE)
+
+ LIST (APPEND WASM_APP_LIB_SOURCE_ALL ${WASM_APP_LIB_CURRENT_SOURCE})
+ set (WASM_APP_LIB_SOURCE_ALL ${WASM_APP_LIB_SOURCE_ALL} PARENT_SCOPE)
+endfunction ()
+
+function (add_module_app arg)
+ message ("Add app module ${ARGV0}")
+ include (${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/app/wasm_app.cmake)
+
+ LIST (APPEND WASM_APP_WA_INC_DIR_LIST "${APP_FRAMEWORK_ROOT_DIR}/${ARGV0}/app/wa-inc")
+ set (WASM_APP_WA_INC_DIR_LIST ${WASM_APP_WA_INC_DIR_LIST} PARENT_SCOPE)
+
+ LIST (APPEND WASM_APP_NAME ${ARGV0})
+ set (WASM_APP_NAME ${WASM_APP_NAME} PARENT_SCOPE)
+
+ LIST (APPEND WASM_APP_SOURCE_ALL ${WASM_APP_CURRENT_SOURCE})
+ set (WASM_APP_SOURCE_ALL ${WASM_APP_SOURCE_ALL} PARENT_SCOPE)
+endfunction ()
+
+if ("${WAMR_BUILD_APP_LIST}" STREQUAL "WAMR_APP_BUILD_ALL")
+ # add all modules under this folder
+ SUBDIRLIST(SUBDIRS ${APP_FRAMEWORK_ROOT_DIR})
+
+ FOREACH(subdir ${SUBDIRS})
+ if ("${subdir}" STREQUAL "app-native-shared")
+ continue()
+ endif ()
+ if ("${subdir}" STREQUAL "template")
+ continue()
+ endif ()
+
+ if ( NOT DEFINED APP_FRAMEWORK_INCLUDE_TYPE )
+ add_module_native (${subdir})
+ else ()
+ add_module_app (${subdir})
+ endif ()
+ ENDFOREACH()
+
+else ()
+ # add each module in the list
+ FOREACH (dir IN LISTS WAMR_BUILD_APP_LIST)
+ string(REPLACE "WAMR_APP_BUILD_" "" dir ${dir})
+ string(TOLOWER ${dir} dir)
+
+ if ( NOT DEFINED APP_FRAMEWORK_INCLUDE_TYPE )
+ add_module_native (${dir})
+ else ()
+ add_module_app (${dir})
+ endif ()
+ ENDFOREACH (dir)
+
+endif()
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.c
new file mode 100644
index 000000000..1848d0792
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.c
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "bh_platform.h"
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+/*
+ *
+ *
+ */
+
+static bool
+is_little_endian()
+{
+ long i = 0x01020304;
+ unsigned char *c = (unsigned char *)&i;
+ return (*c == 0x04) ? true : false;
+}
+
+static void
+swap32(uint8 *pData)
+{
+ uint8 value = *pData;
+ *pData = *(pData + 3);
+ *(pData + 3) = value;
+
+ value = *(pData + 1);
+ *(pData + 1) = *(pData + 2);
+ *(pData + 2) = value;
+}
+
+static void
+swap16(uint8 *pData)
+{
+ uint8 value = *pData;
+ *(pData) = *(pData + 1);
+ *(pData + 1) = value;
+}
+
+uint32
+htonl(uint32 value)
+{
+ uint32 ret;
+ if (is_little_endian()) {
+ ret = value;
+ swap32((uint8 *)&ret);
+ return ret;
+ }
+
+ return value;
+}
+
+uint32
+ntohl(uint32 value)
+{
+ return htonl(value);
+}
+
+uint16
+htons(uint16 value)
+{
+ uint16 ret;
+ if (is_little_endian()) {
+ ret = value;
+ swap16((uint8 *)&ret);
+ return ret;
+ }
+
+ return value;
+}
+
+uint16
+ntohs(uint16 value)
+{
+ return htons(value);
+}
+
+char *
+wa_strdup(const char *s)
+{
+ char *s1 = NULL;
+ if (s && (s1 = WA_MALLOC(strlen(s) + 1)))
+ memcpy(s1, s, strlen(s) + 1);
+ return s1;
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.h
new file mode 100644
index 000000000..8e10dcb64
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/bh_platform.h
@@ -0,0 +1,65 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef DEPS_IWASM_APP_LIBS_BASE_BH_PLATFORM_H_
+#define DEPS_IWASM_APP_LIBS_BASE_BH_PLATFORM_H_
+
+#include <stdbool.h>
+
+typedef unsigned char uint8;
+typedef char int8;
+typedef unsigned short uint16;
+typedef short int16;
+typedef unsigned int uint32;
+typedef int int32;
+
+#ifndef NULL
+#define NULL ((void *)0)
+#endif
+
+#ifndef __cplusplus
+#define true 1
+#define false 0
+#define inline __inline
+#endif
+
+// all wasm-app<->native shared source files should use WA_MALLOC/WA_FREE.
+// they will be mapped to different implementations in each side
+#ifndef WA_MALLOC
+#define WA_MALLOC malloc
+#endif
+
+#ifndef WA_FREE
+#define WA_FREE free
+#endif
+
+uint32
+htonl(uint32 value);
+uint32
+ntohl(uint32 value);
+uint16
+htons(uint16 value);
+uint16
+ntohs(uint16 value);
+
+// We are not worried for the WASM world since the sandbox will catch it.
+#define bh_memcpy_s(dst, dst_len, src, src_len) memcpy(dst, src, src_len)
+
+#ifdef NDEBUG
+#define bh_assert(v) (void)0
+#else
+#define bh_assert(v) \
+ do { \
+ if (!(v)) { \
+ int _count; \
+ printf("ASSERTION FAILED: %s, at %s, line %d", #v, __FILE__, \
+ __LINE__); \
+ _count = printf("\n"); \
+ printf("%d\n", _count / (_count - 1)); \
+ } \
+ } while (0)
+#endif
+
+#endif /* DEPS_IWASM_APP_LIBS_BASE_BH_PLATFORM_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/req_resp_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/req_resp_api.h
new file mode 100644
index 000000000..575c35732
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/req_resp_api.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _REQ_RESP_API_H_
+#define _REQ_RESP_API_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+bool
+wasm_response_send(const char *buf, int size);
+
+void
+wasm_register_resource(const char *url);
+
+void
+wasm_post_request(const char *buf, int size);
+
+void
+wasm_sub_event(const char *url);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _REQ_RESP_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/request.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/request.c
new file mode 100644
index 000000000..3ba44fbc7
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/request.c
@@ -0,0 +1,365 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "bi-inc/attr_container.h"
+#include "wa-inc/request.h"
+#include "wa-inc/timer_wasm_app.h"
+#include "bi-inc/shared_utils.h"
+#include "wasm_app.h"
+#include "req_resp_api.h"
+#include "timer_api.h"
+
+#define TRANSACTION_TIMEOUT_MS 5000
+
+typedef enum { Reg_Event, Reg_Request } reg_type_t;
+
+typedef struct _res_register {
+ struct _res_register *next;
+ const char *url;
+ reg_type_t reg_type;
+ void (*request_handler)(request_t *);
+} res_register_t;
+
+typedef struct transaction {
+ struct transaction *next;
+ int mid;
+ unsigned int time; /* start time */
+ response_handler_f handler;
+ void *user_data;
+} transaction_t;
+
+static res_register_t *g_resources = NULL;
+
+static transaction_t *g_transactions = NULL;
+
+static user_timer_t g_trans_timer = NULL;
+
+static transaction_t *
+transaction_find(int mid)
+{
+ transaction_t *t = g_transactions;
+
+ while (t) {
+ if (t->mid == mid)
+ return t;
+ t = t->next;
+ }
+
+ return NULL;
+}
+
+/*
+ * new transaction is added to the tail of the list, so the list
+ * is sorted by expiry time naturally.
+ */
+static void
+transaction_add(transaction_t *trans)
+{
+ transaction_t *t;
+
+ if (g_transactions == NULL) {
+ g_transactions = trans;
+ return;
+ }
+
+ t = g_transactions;
+ while (t) {
+ if (t->next == NULL) {
+ t->next = trans;
+ return;
+ }
+ }
+}
+
+static void
+transaction_remove(transaction_t *trans)
+{
+ transaction_t *prev = NULL, *current = g_transactions;
+
+ while (current) {
+ if (current == trans) {
+ if (prev == NULL) {
+ g_transactions = current->next;
+ free(current);
+ return;
+ }
+ prev->next = current->next;
+ free(current);
+ return;
+ }
+ prev = current;
+ current = current->next;
+ }
+}
+
+static bool
+is_event_type(request_t *req)
+{
+ return req->action == COAP_EVENT;
+}
+
+static bool
+register_url_handler(const char *url, request_handler_f request_handler,
+ reg_type_t reg_type)
+{
+ res_register_t *r = g_resources;
+
+ while (r) {
+ if (reg_type == r->reg_type && strcmp(r->url, url) == 0) {
+ r->request_handler = request_handler;
+ return true;
+ }
+ r = r->next;
+ }
+
+ r = (res_register_t *)malloc(sizeof(res_register_t));
+ if (r == NULL)
+ return false;
+
+ memset(r, 0, sizeof(*r));
+
+ r->url = strdup(url);
+ if (!r->url) {
+ free(r);
+ return false;
+ }
+
+ r->request_handler = request_handler;
+ r->reg_type = reg_type;
+ r->next = g_resources;
+ g_resources = r;
+
+ // tell app mgr to route this url to me
+ if (reg_type == Reg_Request)
+ wasm_register_resource(url);
+ else
+ wasm_sub_event(url);
+
+ return true;
+}
+
+bool
+api_register_resource_handler(const char *url,
+ request_handler_f request_handler)
+{
+ return register_url_handler(url, request_handler, Reg_Request);
+}
+
+static void
+transaction_timeout_handler(user_timer_t timer)
+{
+ transaction_t *cur, *expired = NULL;
+ unsigned int elpased_ms, now = wasm_get_sys_tick_ms();
+
+ /*
+ * Since he transaction list is sorted by expiry time naturally,
+ * we can easily get all expired transactions.
+ * */
+ cur = g_transactions;
+ while (cur) {
+ if (now < cur->time)
+ elpased_ms = now + (0xFFFFFFFF - cur->time) + 1;
+ else
+ elpased_ms = now - cur->time;
+
+ if (elpased_ms >= TRANSACTION_TIMEOUT_MS) {
+ g_transactions = cur->next;
+ cur->next = expired;
+ expired = cur;
+ cur = g_transactions;
+ }
+ else {
+ break;
+ }
+ }
+
+ /* call each transaction's handler with response set to NULL */
+ cur = expired;
+ while (cur) {
+ transaction_t *tmp = cur;
+ cur->handler(NULL, cur->user_data);
+ cur = cur->next;
+ free(tmp);
+ }
+
+ /*
+ * If the transaction list is not empty, restart the timer according
+ * to the first transaction. Otherwise, stop the timer.
+ */
+ if (g_transactions != NULL) {
+ unsigned int elpased_ms, ms_to_expiry, now = wasm_get_sys_tick_ms();
+ if (now < g_transactions->time) {
+ elpased_ms = now + (0xFFFFFFFF - g_transactions->time) + 1;
+ }
+ else {
+ elpased_ms = now - g_transactions->time;
+ }
+ ms_to_expiry = TRANSACTION_TIMEOUT_MS - elpased_ms;
+ api_timer_restart(g_trans_timer, ms_to_expiry);
+ }
+ else {
+ api_timer_cancel(g_trans_timer);
+ g_trans_timer = NULL;
+ }
+}
+
+void
+api_send_request(request_t *request, response_handler_f response_handler,
+ void *user_data)
+{
+ int size;
+ char *buffer;
+ transaction_t *trans;
+
+ if ((trans = (transaction_t *)malloc(sizeof(transaction_t))) == NULL) {
+ printf(
+ "send request: allocate memory for request transaction failed!\n");
+ return;
+ }
+
+ memset(trans, 0, sizeof(transaction_t));
+ trans->handler = response_handler;
+ trans->mid = request->mid;
+ trans->time = wasm_get_sys_tick_ms();
+ trans->user_data = user_data;
+
+ if ((buffer = pack_request(request, &size)) == NULL) {
+ printf("send request: pack request failed!\n");
+ free(trans);
+ return;
+ }
+
+ transaction_add(trans);
+
+ /* if the trans is the 1st one, start the timer */
+ if (trans == g_transactions) {
+ /* assert(g_trans_timer == NULL); */
+ if (g_trans_timer == NULL) {
+ g_trans_timer = api_timer_create(TRANSACTION_TIMEOUT_MS, false,
+ true, transaction_timeout_handler);
+ }
+ }
+
+ wasm_post_request(buffer, size);
+
+ free_req_resp_packet(buffer);
+}
+
+/*
+ *
+ * APIs for the native layers to callback for request/response arrived to this
+ * app
+ *
+ */
+
+void
+on_response(char *buffer, int size)
+{
+ response_t response[1];
+ transaction_t *trans;
+
+ if (NULL == unpack_response(buffer, size, response)) {
+ printf("unpack response failed\n");
+ return;
+ }
+
+ if ((trans = transaction_find(response->mid)) == NULL) {
+ printf("cannot find the transaction\n");
+ return;
+ }
+
+ /*
+ * When the 1st transaction get response:
+ * 1. If the 2nd trans exist, restart the timer according to its expiry
+ * time;
+ * 2. Otherwise, stop the timer since there is no more transactions;
+ */
+ if (trans == g_transactions) {
+ if (trans->next != NULL) {
+ unsigned int elpased_ms, ms_to_expiry, now = wasm_get_sys_tick_ms();
+ if (now < trans->next->time) {
+ elpased_ms = now + (0xFFFFFFFF - trans->next->time) + 1;
+ }
+ else {
+ elpased_ms = now - trans->next->time;
+ }
+ ms_to_expiry = TRANSACTION_TIMEOUT_MS - elpased_ms;
+ api_timer_restart(g_trans_timer, ms_to_expiry);
+ }
+ else {
+ api_timer_cancel(g_trans_timer);
+ g_trans_timer = NULL;
+ }
+ }
+
+ trans->handler(response, trans->user_data);
+ transaction_remove(trans);
+}
+
+void
+on_request(char *buffer, int size)
+{
+ request_t request[1];
+ bool is_event;
+ res_register_t *r = g_resources;
+
+ if (NULL == unpack_request(buffer, size, request)) {
+ printf("unpack request failed\n");
+ return;
+ }
+
+ is_event = is_event_type(request);
+
+ while (r) {
+ if ((is_event && r->reg_type == Reg_Event)
+ || (!is_event && r->reg_type == Reg_Request)) {
+ if (check_url_start(request->url, strlen(request->url), r->url)
+ > 0) {
+ r->request_handler(request);
+ return;
+ }
+ }
+
+ r = r->next;
+ }
+
+ printf("on_request: exit. no service handler\n");
+}
+
+void
+api_response_send(response_t *response)
+{
+ int size;
+ char *buffer = pack_response(response, &size);
+ if (buffer == NULL)
+ return;
+
+ wasm_response_send(buffer, size);
+ free_req_resp_packet(buffer);
+}
+
+/// event api
+
+bool
+api_publish_event(const char *url, int fmt, void *payload, int payload_len)
+{
+ int size;
+ request_t request[1];
+ init_request(request, (char *)url, COAP_EVENT, fmt, payload, payload_len);
+ char *buffer = pack_request(request, &size);
+ if (buffer == NULL)
+ return false;
+ wasm_post_request(buffer, size);
+
+ free_req_resp_packet(buffer);
+
+ return true;
+}
+
+bool
+api_subscribe_event(const char *url, request_handler_f handler)
+{
+ return register_url_handler(url, handler, Reg_Event);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer.c
new file mode 100644
index 000000000..692626ca3
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer.c
@@ -0,0 +1,100 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "wa-inc/timer_wasm_app.h"
+#include "timer_api.h"
+
+#if 1
+#include <stdio.h>
+#else
+#define printf (...)
+#endif
+
+struct user_timer {
+ struct user_timer *next;
+ int timer_id;
+ void (*user_timer_callback)(user_timer_t);
+};
+
+struct user_timer *g_timers = NULL;
+
+user_timer_t
+api_timer_create(int interval, bool is_period, bool auto_start,
+ on_user_timer_update_f on_timer_update)
+{
+
+ int timer_id = wasm_create_timer(interval, is_period, auto_start);
+
+ // TODO
+ struct user_timer *timer =
+ (struct user_timer *)malloc(sizeof(struct user_timer));
+ if (timer == NULL) {
+ // TODO: remove the timer_id
+ printf("### api_timer_create malloc faild!!! \n");
+ return NULL;
+ }
+
+ memset(timer, 0, sizeof(*timer));
+ timer->timer_id = timer_id;
+ timer->user_timer_callback = on_timer_update;
+
+ if (g_timers == NULL)
+ g_timers = timer;
+ else {
+ timer->next = g_timers;
+ g_timers = timer;
+ }
+
+ return timer;
+}
+
+void
+api_timer_cancel(user_timer_t timer)
+{
+ user_timer_t t = g_timers, prev = NULL;
+
+ wasm_timer_cancel(timer->timer_id);
+
+ while (t) {
+ if (t == timer) {
+ if (prev == NULL) {
+ g_timers = t->next;
+ free(t);
+ }
+ else {
+ prev->next = t->next;
+ free(t);
+ }
+ return;
+ }
+ else {
+ prev = t;
+ t = t->next;
+ }
+ }
+}
+
+void
+api_timer_restart(user_timer_t timer, int interval)
+{
+ wasm_timer_restart(timer->timer_id, interval);
+}
+
+void
+on_timer_callback(int timer_id)
+{
+ struct user_timer *t = g_timers;
+
+ while (t) {
+ if (t->timer_id == timer_id) {
+ t->user_timer_callback(t);
+ break;
+ }
+ t = t->next;
+ }
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer_api.h
new file mode 100644
index 000000000..1fc7555ef
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/timer_api.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _TIMER_API_H_
+#define _TIMER_API_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef unsigned int timer_id_t;
+
+timer_id_t
+wasm_create_timer(int interval, bool is_period, bool auto_start);
+
+void
+wasm_timer_destroy(timer_id_t timer_id);
+
+void
+wasm_timer_cancel(timer_id_t timer_id);
+
+void
+wasm_timer_restart(timer_id_t timer_id, int interval);
+
+uint32
+wasm_get_sys_tick_ms(void);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _TIMER_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/request.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/request.h
new file mode 100644
index 000000000..25830f0a4
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/request.h
@@ -0,0 +1,171 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _AEE_REQUEST_H_
+#define _AEE_REQUEST_H_
+
+#include "bi-inc/shared_utils.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* CoAP request method codes */
+typedef enum {
+ COAP_GET = 1,
+ COAP_POST,
+ COAP_PUT,
+ COAP_DELETE,
+ COAP_EVENT = (COAP_DELETE + 2)
+} coap_method_t;
+
+/* CoAP response codes */
+typedef enum {
+ NO_ERROR = 0,
+
+ CREATED_2_01 = 65, /* CREATED */
+ DELETED_2_02 = 66, /* DELETED */
+ VALID_2_03 = 67, /* NOT_MODIFIED */
+ CHANGED_2_04 = 68, /* CHANGED */
+ CONTENT_2_05 = 69, /* OK */
+ CONTINUE_2_31 = 95, /* CONTINUE */
+
+ BAD_REQUEST_4_00 = 128, /* BAD_REQUEST */
+ UNAUTHORIZED_4_01 = 129, /* UNAUTHORIZED */
+ BAD_OPTION_4_02 = 130, /* BAD_OPTION */
+ FORBIDDEN_4_03 = 131, /* FORBIDDEN */
+ NOT_FOUND_4_04 = 132, /* NOT_FOUND */
+ METHOD_NOT_ALLOWED_4_05 = 133, /* METHOD_NOT_ALLOWED */
+ NOT_ACCEPTABLE_4_06 = 134, /* NOT_ACCEPTABLE */
+ PRECONDITION_FAILED_4_12 = 140, /* BAD_REQUEST */
+ REQUEST_ENTITY_TOO_LARGE_4_13 = 141, /* REQUEST_ENTITY_TOO_LARGE */
+ UNSUPPORTED_MEDIA_TYPE_4_15 = 143, /* UNSUPPORTED_MEDIA_TYPE */
+
+ INTERNAL_SERVER_ERROR_5_00 = 160, /* INTERNAL_SERVER_ERROR */
+ NOT_IMPLEMENTED_5_01 = 161, /* NOT_IMPLEMENTED */
+ BAD_GATEWAY_5_02 = 162, /* BAD_GATEWAY */
+ SERVICE_UNAVAILABLE_5_03 = 163, /* SERVICE_UNAVAILABLE */
+ GATEWAY_TIMEOUT_5_04 = 164, /* GATEWAY_TIMEOUT */
+ PROXYING_NOT_SUPPORTED_5_05 = 165, /* PROXYING_NOT_SUPPORTED */
+
+ /* Erbium errors */
+ MEMORY_ALLOCATION_ERROR = 192,
+ PACKET_SERIALIZATION_ERROR,
+
+ /* Erbium hooks */
+ MANUAL_RESPONSE,
+ PING_RESPONSE
+} coap_status_t;
+
+/**
+ * @typedef request_handler_f
+ *
+ * @brief Define the signature of callback function for API
+ * api_register_resource_handler() to handle request or for API
+ * api_subscribe_event() to handle event.
+ *
+ * @param request pointer of the request to be handled
+ *
+ * @see api_register_resource_handler
+ * @see api_subscribe_event
+ */
+typedef void (*request_handler_f)(request_t *request);
+
+/**
+ * @typedef response_handler_f
+ *
+ * @brief Define the signature of callback function for API
+ * api_send_request() to handle response of a request.
+ *
+ * @param response pointer of the response to be handled
+ * @param user_data user data associated with the request which is set when
+ * calling api_send_request().
+ *
+ * @see api_send_request
+ */
+typedef void (*response_handler_f)(response_t *response, void *user_data);
+
+/*
+ *****************
+ * Request APIs
+ *****************
+ */
+
+/**
+ * @brief Register resource.
+ *
+ * @param url url of the resource
+ * @param handler callback function to handle the request to the resource
+ *
+ * @return true if success, false otherwise
+ */
+bool
+api_register_resource_handler(const char *url, request_handler_f handler);
+
+/**
+ * @brief Send request asynchronously.
+ *
+ * @param request pointer of the request to be sent
+ * @param response_handler callback function to handle the response
+ * @param user_data user data
+ */
+void
+api_send_request(request_t *request, response_handler_f response_handler,
+ void *user_data);
+
+/**
+ * @brief Send response.
+ *
+ * @param response pointer of the response to be sent
+ *
+ * @par
+ * @code
+ * void res1_handler(request_t *request)
+ * {
+ * response_t response[1];
+ * make_response_for_request(request, response);
+ * set_response(response, DELETED_2_02, 0, NULL, 0);
+ * api_response_send(response);
+ * }
+ * @endcode
+ */
+void
+api_response_send(response_t *response);
+
+/*
+ *****************
+ * Event APIs
+ *****************
+ */
+
+/**
+ * @brief Publish an event.
+ *
+ * @param url url of the event
+ * @param fmt format of the event payload
+ * @param payload payload of the event
+ * @param payload_len length in bytes of the event payload
+ *
+ * @return true if success, false otherwise
+ */
+bool
+api_publish_event(const char *url, int fmt, void *payload, int payload_len);
+
+/**
+ * @brief Subscribe an event.
+ *
+ * @param url url of the event
+ * @param handler callback function to handle the event.
+ *
+ * @return true if success, false otherwise
+ */
+bool
+api_subscribe_event(const char *url, request_handler_f handler);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/timer_wasm_app.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/timer_wasm_app.h
new file mode 100644
index 000000000..cf158a365
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wa-inc/timer_wasm_app.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _AEE_TIMER_H_
+#define _AEE_TIMER_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* board producer define user_timer */
+struct user_timer;
+typedef struct user_timer *user_timer_t;
+
+/**
+ * @typedef on_user_timer_update_f
+ *
+ * @brief Define the signature of callback function for API api_timer_create().
+ *
+ * @param timer the timer
+ *
+ * @see api_timer_create
+ */
+typedef void (*on_user_timer_update_f)(user_timer_t timer);
+
+/*
+ *****************
+ * Timer APIs
+ *****************
+ */
+
+/**
+ * @brief Create timer.
+ *
+ * @param interval timer interval
+ * @param is_period whether the timer is periodic
+ * @param auto_start whether start the timer immediately after created
+ * @param on_timer_update callback function called when timer expired
+ *
+ * @return the timer created if success, NULL otherwise
+ */
+user_timer_t
+api_timer_create(int interval, bool is_period, bool auto_start,
+ on_user_timer_update_f on_timer_update);
+
+/**
+ * @brief Cancel timer.
+ *
+ * @param timer the timer to cancel
+ */
+void
+api_timer_cancel(user_timer_t timer);
+
+/**
+ * @brief Restart timer.
+ *
+ * @param timer the timer to cancel
+ * @param interval the timer interval
+ */
+void
+api_timer_restart(user_timer_t timer, int interval);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.cmake
new file mode 100644
index 000000000..2313df99d
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.cmake
@@ -0,0 +1,13 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_APP_BASE_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_APP_BASE_DIR})
+
+add_definitions (-DWASM_ENABLE_BASE_LIB)
+
+file (GLOB_RECURSE source_all ${WASM_APP_BASE_DIR}/*.c)
+
+set (WASM_APP_CURRENT_SOURCE ${source_all})
+set (WASM_APP_BASE_DIR ${WASM_APP_BASE_DIR} PARENT_SCOPE)
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.h
new file mode 100644
index 000000000..e7be8a4c1
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/app/wasm_app.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _LIB_AEE_H_
+#define _LIB_AEE_H_
+
+#include "bi-inc/shared_utils.h"
+#include "bi-inc/attr_container.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _LIB_AEE_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib.inl b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib.inl
new file mode 100644
index 000000000..3c228cc93
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib.inl
@@ -0,0 +1,14 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+ EXPORT_WASM_API_WITH_SIG(wasm_register_resource, "($)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_response_send, "(*~)i"),
+ EXPORT_WASM_API_WITH_SIG(wasm_post_request, "(*~)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_sub_event, "($)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_create_timer, "(iii)i"),
+ EXPORT_WASM_API_WITH_SIG(wasm_timer_destroy, "(i)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_timer_cancel, "(i)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_timer_restart, "(ii)"),
+ EXPORT_WASM_API_WITH_SIG(wasm_get_sys_tick_ms, "()i"),
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib_export.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib_export.c
new file mode 100644
index 000000000..19ac7185c
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/base_lib_export.c
@@ -0,0 +1,24 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include "lib_export.h"
+#include "req_resp_native_api.h"
+#include "timer_native_api.h"
+
+static NativeSymbol extended_native_symbol_defs[] = {
+/* TODO: use macro EXPORT_WASM_API() or EXPORT_WASM_API2() to
+ add functions to register. */
+#include "base_lib.inl"
+};
+
+uint32
+get_base_lib_export_apis(NativeSymbol **p_base_lib_apis)
+{
+ *p_base_lib_apis = extended_native_symbol_defs;
+ return sizeof(extended_native_symbol_defs) / sizeof(NativeSymbol);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/req_resp_native_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/req_resp_native_api.h
new file mode 100644
index 000000000..3e5938772
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/req_resp_native_api.h
@@ -0,0 +1,29 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _REQ_RESP_API_H_
+#define _REQ_RESP_API_H_
+
+#include "bh_platform.h"
+#include "wasm_export.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+bool
+wasm_response_send(wasm_exec_env_t exec_env, char *buffer, int size);
+void
+wasm_register_resource(wasm_exec_env_t exec_env, char *url);
+void
+wasm_post_request(wasm_exec_env_t exec_env, char *buffer, int size);
+void
+wasm_sub_event(wasm_exec_env_t exec_env, char *url);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _REQ_RESP_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/request_response.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/request_response.c
new file mode 100644
index 000000000..674ba5e9d
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/request_response.c
@@ -0,0 +1,84 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "app_manager_export.h"
+#include "coap_ext.h"
+#include "wasm_export.h"
+#include "bh_assert.h"
+
+extern void
+module_request_handler(request_t *request, void *user_data);
+
+bool
+wasm_response_send(wasm_exec_env_t exec_env, char *buffer, int size)
+{
+ if (buffer != NULL) {
+ response_t response[1];
+
+ if (NULL == unpack_response(buffer, size, response))
+ return false;
+
+ am_send_response(response);
+
+ return true;
+ }
+
+ return false;
+}
+
+void
+wasm_register_resource(wasm_exec_env_t exec_env, char *url)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+
+ if (url != NULL) {
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+ bh_assert(mod_id != ID_NONE);
+ am_register_resource(url, module_request_handler, mod_id);
+ }
+}
+
+void
+wasm_post_request(wasm_exec_env_t exec_env, char *buffer, int size)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+
+ if (buffer != NULL) {
+ request_t req[1];
+
+ if (!unpack_request(buffer, size, req))
+ return;
+
+ // TODO: add permission check, ensure app can't do harm
+
+ // set sender to help dispatch the response to the sender ap
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+ bh_assert(mod_id != ID_NONE);
+ req->sender = mod_id;
+
+ if (req->action == COAP_EVENT) {
+ am_publish_event(req);
+ return;
+ }
+
+ am_dispatch_request(req);
+ }
+}
+
+void
+wasm_sub_event(wasm_exec_env_t exec_env, char *url)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+
+ if (url != NULL) {
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+
+ bh_assert(mod_id != ID_NONE);
+ am_register_event(url, mod_id);
+ }
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/runtime_lib.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/runtime_lib.h
new file mode 100644
index 000000000..477b663b2
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/runtime_lib.h
@@ -0,0 +1,22 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef LIB_BASE_RUNTIME_LIB_H_
+#define LIB_BASE_RUNTIME_LIB_H_
+
+#include "runtime_timer.h"
+
+bool
+init_wasm_timer();
+void
+exit_wasm_timer();
+timer_ctx_t
+get_wasm_timer_ctx();
+timer_ctx_t
+create_wasm_timer_ctx(unsigned int module_id, int prealloc_num);
+void
+destroy_module_timer_ctx(unsigned int module_id);
+
+#endif /* LIB_BASE_RUNTIME_LIB_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_native_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_native_api.h
new file mode 100644
index 000000000..138e7c60d
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_native_api.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _TIMER_API_H_
+#define _TIMER_API_H_
+
+#include "bh_platform.h"
+#include "wasm_export.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef unsigned int timer_id_t;
+
+/*
+ * timer interfaces
+ */
+
+typedef unsigned int timer_id_t;
+
+timer_id_t
+wasm_create_timer(wasm_exec_env_t exec_env, int interval, bool is_period,
+ bool auto_start);
+void
+wasm_timer_destroy(wasm_exec_env_t exec_env, timer_id_t timer_id);
+void
+wasm_timer_cancel(wasm_exec_env_t exec_env, timer_id_t timer_id);
+void
+wasm_timer_restart(wasm_exec_env_t exec_env, timer_id_t timer_id, int interval);
+uint32
+wasm_get_sys_tick_ms(wasm_exec_env_t exec_env);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _TIMER_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_wrapper.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_wrapper.c
new file mode 100644
index 000000000..246868849
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/timer_wrapper.c
@@ -0,0 +1,220 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "bh_platform.h"
+#include "app_manager_export.h"
+#include "../app-manager/module_wasm_app.h"
+#include "timer_native_api.h"
+
+typedef struct {
+ bh_list_link l;
+ timer_ctx_t timer_ctx;
+} timer_ctx_node_t;
+
+static bool timer_thread_run = true;
+
+static bh_list g_timer_ctx_list;
+static korp_cond g_timer_ctx_list_cond;
+static korp_mutex g_timer_ctx_list_mutex;
+
+void
+wasm_timer_callback(timer_id_t id, unsigned int mod_id)
+{
+ module_data *module = module_data_list_lookup_id(mod_id);
+ if (module == NULL)
+ return;
+
+ // !!! the length parameter must be 0, so the receiver will
+ // not free the payload pointer.
+ bh_post_msg(module->queue, TIMER_EVENT_WASM, (char *)(uintptr_t)id, 0);
+}
+
+/**
+ * why we create a separate link for module timer contexts
+ * rather than traverse the module list?
+ * It helps to reduce the lock frequency for the module list.
+ * Also when we lock the module list and then call the callback for
+ * timer expire, the callback is request the list lock again for lookup
+ * the module from module id. It is for avoiding that situation.
+ */
+
+void *
+thread_modulers_timer_check(void *arg)
+{
+ uint32 ms_to_expiry;
+ uint64 us_to_wait;
+
+ while (timer_thread_run) {
+ ms_to_expiry = (uint32)-1;
+ os_mutex_lock(&g_timer_ctx_list_mutex);
+ timer_ctx_node_t *elem =
+ (timer_ctx_node_t *)bh_list_first_elem(&g_timer_ctx_list);
+ while (elem) {
+ uint32 next = check_app_timers(elem->timer_ctx);
+ if (next != (uint32)-1) {
+ if (ms_to_expiry == (uint32)-1 || ms_to_expiry > next)
+ ms_to_expiry = next;
+ }
+
+ elem = (timer_ctx_node_t *)bh_list_elem_next(elem);
+ }
+ os_mutex_unlock(&g_timer_ctx_list_mutex);
+
+ if (ms_to_expiry == (uint32)-1)
+ us_to_wait = BHT_WAIT_FOREVER;
+ else
+ us_to_wait = (uint64)ms_to_expiry * 1000;
+ os_mutex_lock(&g_timer_ctx_list_mutex);
+ os_cond_reltimedwait(&g_timer_ctx_list_cond, &g_timer_ctx_list_mutex,
+ us_to_wait);
+ os_mutex_unlock(&g_timer_ctx_list_mutex);
+ }
+
+ return NULL;
+}
+
+void
+wakeup_modules_timer_thread(timer_ctx_t ctx)
+{
+ os_mutex_lock(&g_timer_ctx_list_mutex);
+ os_cond_signal(&g_timer_ctx_list_cond);
+ os_mutex_unlock(&g_timer_ctx_list_mutex);
+}
+
+bool
+init_wasm_timer()
+{
+ korp_tid tm_tid;
+ bh_list_init(&g_timer_ctx_list);
+
+ if (os_cond_init(&g_timer_ctx_list_cond) != 0) {
+ return false;
+ }
+ /* temp solution for: thread_modulers_timer_check thread
+ would recursive lock the mutex */
+ if (os_recursive_mutex_init(&g_timer_ctx_list_mutex) != 0) {
+ goto fail1;
+ }
+
+ if (0
+ != os_thread_create(&tm_tid, thread_modulers_timer_check, NULL,
+ BH_APPLET_PRESERVED_STACK_SIZE)) {
+ goto fail2;
+ }
+
+ return true;
+
+fail2:
+ os_mutex_destroy(&g_timer_ctx_list_mutex);
+
+fail1:
+ os_cond_destroy(&g_timer_ctx_list_cond);
+
+ return false;
+}
+
+void
+exit_wasm_timer()
+{
+ timer_thread_run = false;
+}
+
+timer_ctx_t
+create_wasm_timer_ctx(unsigned int module_id, int prealloc_num)
+{
+ timer_ctx_t ctx =
+ create_timer_ctx(wasm_timer_callback, wakeup_modules_timer_thread,
+ prealloc_num, module_id);
+
+ if (ctx == NULL)
+ return NULL;
+
+ timer_ctx_node_t *node =
+ (timer_ctx_node_t *)wasm_runtime_malloc(sizeof(timer_ctx_node_t));
+ if (node == NULL) {
+ destroy_timer_ctx(ctx);
+ return NULL;
+ }
+ memset(node, 0, sizeof(*node));
+ node->timer_ctx = ctx;
+
+ os_mutex_lock(&g_timer_ctx_list_mutex);
+ bh_list_insert(&g_timer_ctx_list, node);
+ os_mutex_unlock(&g_timer_ctx_list_mutex);
+
+ return ctx;
+}
+
+void
+destroy_module_timer_ctx(unsigned int module_id)
+{
+ timer_ctx_node_t *elem;
+
+ os_mutex_lock(&g_timer_ctx_list_mutex);
+ elem = (timer_ctx_node_t *)bh_list_first_elem(&g_timer_ctx_list);
+ while (elem) {
+ if (timer_ctx_get_owner(elem->timer_ctx) == module_id) {
+ bh_list_remove(&g_timer_ctx_list, elem);
+ destroy_timer_ctx(elem->timer_ctx);
+ wasm_runtime_free(elem);
+ break;
+ }
+
+ elem = (timer_ctx_node_t *)bh_list_elem_next(elem);
+ }
+ os_mutex_unlock(&g_timer_ctx_list_mutex);
+}
+
+timer_ctx_t
+get_wasm_timer_ctx(wasm_module_inst_t module_inst)
+{
+ module_data *m = app_manager_get_module_data(Module_WASM_App, module_inst);
+ if (m == NULL)
+ return NULL;
+ return m->timer_ctx;
+}
+
+timer_id_t
+wasm_create_timer(wasm_exec_env_t exec_env, int interval, bool is_period,
+ bool auto_start)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ timer_ctx_t timer_ctx = get_wasm_timer_ctx(module_inst);
+ bh_assert(timer_ctx);
+ return sys_create_timer(timer_ctx, interval, is_period, auto_start);
+}
+
+void
+wasm_timer_destroy(wasm_exec_env_t exec_env, timer_id_t timer_id)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ timer_ctx_t timer_ctx = get_wasm_timer_ctx(module_inst);
+ bh_assert(timer_ctx);
+ sys_timer_destroy(timer_ctx, timer_id);
+}
+
+void
+wasm_timer_cancel(wasm_exec_env_t exec_env, timer_id_t timer_id)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ timer_ctx_t timer_ctx = get_wasm_timer_ctx(module_inst);
+ bh_assert(timer_ctx);
+ sys_timer_cancel(timer_ctx, timer_id);
+}
+
+void
+wasm_timer_restart(wasm_exec_env_t exec_env, timer_id_t timer_id, int interval)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ timer_ctx_t timer_ctx = get_wasm_timer_ctx(module_inst);
+ bh_assert(timer_ctx);
+ sys_timer_restart(timer_ctx, timer_id, interval);
+}
+
+uint32
+wasm_get_sys_tick_ms(wasm_exec_env_t exec_env)
+{
+ return (uint32)bh_get_tick_ms();
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/wasm_lib.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/wasm_lib.cmake
new file mode 100644
index 000000000..223320b32
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/base/native/wasm_lib.cmake
@@ -0,0 +1,13 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_BASE_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+add_definitions (-DWASM_ENABLE_BASE_LIB)
+
+include_directories(${WASM_LIB_BASE_DIR})
+
+file (GLOB_RECURSE source_all ${WASM_LIB_BASE_DIR}/*.c)
+
+set (WASM_APP_LIB_CURRENT_SOURCE ${source_all})
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection.c
new file mode 100644
index 000000000..b5b2bfc54
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection.c
@@ -0,0 +1,118 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "wa-inc/connection.h"
+#include "connection_api.h"
+
+/* Raw connection structure */
+typedef struct _connection {
+ /* Next connection */
+ struct _connection *next;
+
+ /* Handle of the connection */
+ uint32 handle;
+
+ /* Callback function called when event on this connection occurs */
+ on_connection_event_f on_event;
+
+ /* User data */
+ void *user_data;
+} connection_t;
+
+/* Raw connections list */
+static connection_t *g_conns = NULL;
+
+connection_t *
+api_open_connection(const char *name, attr_container_t *args,
+ on_connection_event_f on_event, void *user_data)
+{
+ connection_t *conn;
+ char *args_buffer = (char *)args;
+ uint32 handle, args_len = attr_container_get_serialize_length(args);
+
+ handle = wasm_open_connection(name, args_buffer, args_len);
+ if (handle == -1)
+ return NULL;
+
+ conn = (connection_t *)malloc(sizeof(*conn));
+ if (conn == NULL) {
+ wasm_close_connection(handle);
+ return NULL;
+ }
+
+ memset(conn, 0, sizeof(*conn));
+ conn->handle = handle;
+ conn->on_event = on_event;
+ conn->user_data = user_data;
+
+ if (g_conns != NULL) {
+ conn->next = g_conns;
+ g_conns = conn;
+ }
+ else {
+ g_conns = conn;
+ }
+
+ return conn;
+}
+
+void
+api_close_connection(connection_t *c)
+{
+ connection_t *conn = g_conns, *prev = NULL;
+
+ while (conn) {
+ if (conn == c) {
+ wasm_close_connection(c->handle);
+ if (prev != NULL)
+ prev->next = conn->next;
+ else
+ g_conns = conn->next;
+ free(conn);
+ return;
+ }
+ else {
+ prev = conn;
+ conn = conn->next;
+ }
+ }
+}
+
+int
+api_send_on_connection(connection_t *conn, const char *data, uint32 len)
+{
+ return wasm_send_on_connection(conn->handle, data, len);
+}
+
+bool
+api_config_connection(connection_t *conn, attr_container_t *cfg)
+{
+ char *cfg_buffer = (char *)cfg;
+ uint32 cfg_len = attr_container_get_serialize_length(cfg);
+
+ return wasm_config_connection(conn->handle, cfg_buffer, cfg_len);
+}
+
+void
+on_connection_data(uint32 handle, char *buffer, uint32 len)
+{
+ connection_t *conn = g_conns;
+
+ while (conn != NULL) {
+ if (conn->handle == handle) {
+ if (len == 0) {
+ conn->on_event(conn, CONN_EVENT_TYPE_DISCONNECT, NULL, 0,
+ conn->user_data);
+ }
+ else {
+ conn->on_event(conn, CONN_EVENT_TYPE_DATA, buffer, len,
+ conn->user_data);
+ }
+
+ return;
+ }
+ conn = conn->next;
+ }
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection_api.h
new file mode 100644
index 000000000..22bd5a182
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/connection_api.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONNECTION_API_H_
+#define CONNECTION_API_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+uint32
+wasm_open_connection(const char *name, char *args_buf, uint32 args_buf_len);
+
+void
+wasm_close_connection(uint32 handle);
+
+int
+wasm_send_on_connection(uint32 handle, const char *data, uint32 data_len);
+
+bool
+wasm_config_connection(uint32 handle, const char *cfg_buf, uint32 cfg_buf_len);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of CONNECTION_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wa-inc/connection.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wa-inc/connection.h
new file mode 100644
index 000000000..823eaec74
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wa-inc/connection.h
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _CONNECTION_H_
+#define _CONNECTION_H_
+
+#include "bi-inc/attr_container.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct _connection;
+typedef struct _connection connection_t;
+
+/* 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 on_connection_event_f
+ *
+ * @param conn the connection that the event belongs to
+ * @param type event type
+ * @param data the data received for CONN_EVENT_TYPE_DATA event
+ * @param len length of the data in byte
+ * @param user_data user data
+ */
+typedef void (*on_connection_event_f)(connection_t *conn,
+ conn_event_type_t type, const char *data,
+ uint32 len, void *user_data);
+
+/*
+ *****************
+ * Connection API's
+ *****************
+ */
+
+/*
+ * @brief Open a connection.
+ *
+ * @param name name of the connection, "TCP", "UDP" or "UART"
+ * @param args connection arguments, such as: ip:127.0.0.1, port:8888
+ * @param on_event callback function called when event occurs
+ * @param user_data user data
+ *
+ * @return the connection or NULL means fail
+ */
+connection_t *
+api_open_connection(const char *name, attr_container_t *args,
+ on_connection_event_f on_event, void *user_data);
+
+/*
+ * @brief Close a connection.
+ *
+ * @param conn connection
+ */
+void
+api_close_connection(connection_t *conn);
+
+/*
+ * Send data to the connection in non-blocking manner which returns immediately
+ *
+ * @param conn the connection
+ * @param data data buffer to be sent
+ * @param len length of the data in byte
+ *
+ * @return actual length sent, or -1 if fail(maybe underlying buffer is full)
+ */
+int
+api_send_on_connection(connection_t *conn, const char *data, uint32 len);
+
+/*
+ * @brief Configure connection.
+ *
+ * @param conn the connection
+ * @param cfg configurations
+ *
+ * @return true if success, false otherwise
+ */
+bool
+api_config_connection(connection_t *conn, attr_container_t *cfg);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wasm_app.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wasm_app.cmake
new file mode 100644
index 000000000..ca4e02599
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/app/wasm_app.cmake
@@ -0,0 +1,11 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_APP_CONN_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_APP_CONN_DIR})
+
+
+file (GLOB source_all ${WASM_APP_CONN_DIR}/*.c)
+
+set (WASM_APP_CURRENT_SOURCE ${source_all})
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection.inl b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection.inl
new file mode 100644
index 000000000..b2d01aa9f
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection.inl
@@ -0,0 +1,9 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+EXPORT_WASM_API_WITH_SIG(wasm_open_connection, "($*~)i"),
+EXPORT_WASM_API_WITH_SIG(wasm_close_connection, "(i)"),
+EXPORT_WASM_API_WITH_SIG(wasm_send_on_connection, "(i*~)i"),
+EXPORT_WASM_API_WITH_SIG(wasm_config_connection, "(i*~)i"),
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_lib.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_lib.h
new file mode 100644
index 000000000..3e182cbb8
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_lib.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONNECTION_LIB_H_
+#define CONNECTION_LIB_H_
+
+#include "bi-inc/attr_container.h"
+#include "wasm_export.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * This file defines connection library which should be implemented by
+ * different platforms
+ */
+
+/*
+ * @brief Open a connection.
+ *
+ * @param name name of the connection, "TCP", "UDP" or "UART"
+ * @param args connection arguments, such as: ip:127.0.0.1, port:8888
+ *
+ * @return 0~0xFFFFFFFE means id of the connection, otherwise(-1) means fail
+ */
+typedef uint32 (*connection_open_f)(wasm_module_inst_t module_inst,
+ const char *name, attr_container_t *args);
+
+/*
+ * @brief Close a connection.
+ *
+ * @param handle of the connection
+ */
+typedef void (*connection_close_f)(uint32 handle);
+
+/*
+ * @brief Send data to the connection in non-blocking manner.
+ *
+ * @param handle of the connection
+ * @param data data buffer to be sent
+ * @param len length of the data in byte
+ *
+ * @return actual length sent, -1 if fail
+ */
+typedef int (*connection_send_f)(uint32 handle, const char *data, int len);
+
+/*
+ * @brief Configure connection.
+ *
+ * @param handle of the connection
+ * @param cfg configurations
+ *
+ * @return true if success, false otherwise
+ */
+typedef bool (*connection_config_f)(uint32 handle, attr_container_t *cfg);
+
+/* Raw connection interface for platform to implement */
+typedef struct _connection_interface {
+ connection_open_f _open;
+ connection_close_f _close;
+ connection_send_f _send;
+ connection_config_f _config;
+} connection_interface_t;
+
+/* Platform must define this interface */
+extern connection_interface_t connection_impl;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* CONNECTION_LIB_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_native_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_native_api.h
new file mode 100644
index 000000000..42a2508f1
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_native_api.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONNECTION_API_H_
+#define CONNECTION_API_H_
+
+#include "bh_platform.h"
+#include "wasm_export.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+ * connection interfaces
+ */
+
+uint32
+wasm_open_connection(wasm_exec_env_t exec_env, char *name, char *args_buf,
+ uint32 len);
+void
+wasm_close_connection(wasm_exec_env_t exec_env, uint32 handle);
+int
+wasm_send_on_connection(wasm_exec_env_t exec_env, uint32 handle, char *data,
+ uint32 len);
+bool
+wasm_config_connection(wasm_exec_env_t exec_env, uint32 handle, char *cfg_buf,
+ uint32 len);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of CONNECTION_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_wrapper.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_wrapper.c
new file mode 100644
index 000000000..7c20b51d0
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/connection_wrapper.c
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "connection_lib.h"
+#include "wasm_export.h"
+#include "native_interface.h"
+#include "connection_native_api.h"
+
+/* Note:
+ *
+ * This file is the consumer of connection lib which is implemented by different
+ * platforms
+ */
+
+uint32
+wasm_open_connection(wasm_exec_env_t exec_env, char *name, char *args_buf,
+ uint32 len)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ attr_container_t *args;
+
+ args = (attr_container_t *)args_buf;
+
+ if (connection_impl._open != NULL)
+ return connection_impl._open(module_inst, name, args);
+
+ return -1;
+}
+
+void
+wasm_close_connection(wasm_exec_env_t exec_env, uint32 handle)
+{
+ if (connection_impl._close != NULL)
+ connection_impl._close(handle);
+}
+
+int
+wasm_send_on_connection(wasm_exec_env_t exec_env, uint32 handle, char *data,
+ uint32 len)
+{
+ if (connection_impl._send != NULL)
+ return connection_impl._send(handle, data, len);
+
+ return -1;
+}
+
+bool
+wasm_config_connection(wasm_exec_env_t exec_env, uint32 handle, char *cfg_buf,
+ uint32 len)
+{
+ attr_container_t *cfg;
+
+ cfg = (attr_container_t *)cfg_buf;
+
+ if (connection_impl._config != NULL)
+ return connection_impl._config(handle, cfg);
+
+ return false;
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.c
new file mode 100644
index 000000000..054eb59fd
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.c
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "conn_tcp.h"
+
+#include <sys/socket.h>
+#include <netdb.h>
+#include <arpa/inet.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+int
+tcp_open(char *address, uint16 port)
+{
+ int sock, ret;
+ struct sockaddr_in servaddr;
+
+ memset(&servaddr, 0, sizeof(servaddr));
+ servaddr.sin_family = AF_INET;
+ servaddr.sin_addr.s_addr = inet_addr(address);
+ servaddr.sin_port = htons(port);
+
+ sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
+ if (sock == -1)
+ return -1;
+
+ ret = connect(sock, (struct sockaddr *)&servaddr, sizeof(servaddr));
+ if (ret == -1) {
+ close(sock);
+ return -1;
+ }
+
+ /* Put the socket in non-blocking mode */
+ if (fcntl(sock, F_SETFL, fcntl(sock, F_GETFL) | O_NONBLOCK) < 0) {
+ close(sock);
+ return -1;
+ }
+
+ return sock;
+}
+
+int
+tcp_send(int sock, const char *data, int size)
+{
+ return send(sock, data, size, 0);
+}
+
+int
+tcp_recv(int sock, char *buffer, int buf_size)
+{
+ return recv(sock, buffer, buf_size, 0);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.h
new file mode 100644
index 000000000..c4d5cc86a
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_tcp.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONN_LINUX_TCP_H_
+#define CONN_LINUX_TCP_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int
+tcp_open(char *address, uint16 port);
+
+int
+tcp_send(int sock, const char *data, int size);
+
+int
+tcp_recv(int sock, char *buffer, int buf_size);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.c
new file mode 100644
index 000000000..0bcdc93f7
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.c
@@ -0,0 +1,103 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "conn_uart.h"
+
+#include <fcntl.h>
+#include <termios.h>
+#include <unistd.h>
+
+static int
+parse_baudrate(int baud)
+{
+ switch (baud) {
+ case 9600:
+ return B9600;
+ case 19200:
+ return B19200;
+ case 38400:
+ return B38400;
+ case 57600:
+ return B57600;
+ case 115200:
+ return B115200;
+ case 230400:
+ return B230400;
+ case 460800:
+ return B460800;
+ case 500000:
+ return B500000;
+ case 576000:
+ return B576000;
+ case 921600:
+ return B921600;
+ case 1000000:
+ return B1000000;
+ case 1152000:
+ return B1152000;
+ case 1500000:
+ return B1500000;
+ case 2000000:
+ return B2000000;
+ case 2500000:
+ return B2500000;
+ case 3000000:
+ return B3000000;
+ case 3500000:
+ return B3500000;
+ case 4000000:
+ return B4000000;
+ default:
+ return -1;
+ }
+}
+
+int
+uart_open(char *device, int baudrate)
+{
+ int uart_fd;
+ struct termios uart_term;
+
+ uart_fd = open(device, O_RDWR | O_NOCTTY);
+
+ if (uart_fd < 0)
+ return -1;
+
+ memset(&uart_term, 0, sizeof(uart_term));
+ uart_term.c_cflag = parse_baudrate(baudrate) | CS8 | CLOCAL | CREAD;
+ uart_term.c_iflag = IGNPAR;
+ uart_term.c_oflag = 0;
+
+ /* set noncanonical mode */
+ uart_term.c_lflag = 0;
+ uart_term.c_cc[VTIME] = 30;
+ uart_term.c_cc[VMIN] = 1;
+ tcflush(uart_fd, TCIFLUSH);
+
+ if (tcsetattr(uart_fd, TCSANOW, &uart_term) != 0) {
+ close(uart_fd);
+ return -1;
+ }
+
+ /* Put the fd in non-blocking mode */
+ if (fcntl(uart_fd, F_SETFL, fcntl(uart_fd, F_GETFL) | O_NONBLOCK) < 0) {
+ close(uart_fd);
+ return -1;
+ }
+
+ return uart_fd;
+}
+
+int
+uart_send(int fd, const char *data, int size)
+{
+ return write(fd, data, size);
+}
+
+int
+uart_recv(int fd, char *buffer, int buf_size)
+{
+ return read(fd, buffer, buf_size);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.h
new file mode 100644
index 000000000..443167026
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_uart.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONN_LINUX_UART_H_
+#define CONN_LINUX_UART_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int
+uart_open(char *device, int baudrate);
+
+int
+uart_send(int fd, const char *data, int size);
+
+int
+uart_recv(int fd, char *buffer, int buf_size);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.c
new file mode 100644
index 000000000..61652b14d
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.c
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "conn_udp.h"
+
+#include <sys/socket.h>
+#include <netdb.h>
+#include <arpa/inet.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+int
+udp_open(uint16 port)
+{
+ int sock, ret;
+ struct sockaddr_in addr;
+
+ sock = socket(AF_INET, SOCK_DGRAM, 0);
+ if (sock == -1)
+ return -1;
+
+ memset(&addr, 0, sizeof(addr));
+ addr.sin_family = AF_INET;
+ addr.sin_addr.s_addr = htonl(INADDR_ANY);
+ addr.sin_port = htons(port);
+
+ ret = bind(sock, (struct sockaddr *)&addr, sizeof(addr));
+ if (ret == -1) {
+ close(sock);
+ return -1;
+ }
+
+ /* Put the socket in non-blocking mode */
+ if (fcntl(sock, F_SETFL, fcntl(sock, F_GETFL) | O_NONBLOCK) < 0) {
+ close(sock);
+ return -1;
+ }
+
+ return sock;
+}
+
+int
+udp_send(int sock, struct sockaddr *dest, const char *data, int size)
+{
+ return sendto(sock, data, size, MSG_CONFIRM, dest, sizeof(*dest));
+}
+
+int
+udp_recv(int sock, char *buffer, int buf_size)
+{
+ struct sockaddr_in remaddr;
+ socklen_t addrlen = sizeof(remaddr);
+
+ return recvfrom(sock, buffer, buf_size, 0, (struct sockaddr *)&remaddr,
+ &addrlen);
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.h
new file mode 100644
index 000000000..377c26eb1
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/conn_udp.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef CONN_LINUX_UDP_H_
+#define CONN_LINUX_UDP_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int
+udp_open(uint16 port);
+
+int
+udp_send(int sock, struct sockaddr *dest, const char *data, int size);
+
+int
+udp_recv(int sock, char *buffer, int buf_size);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.c
new file mode 100644
index 000000000..001446206
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.c
@@ -0,0 +1,609 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+/*
+ * Note:
+ * This file implements the linux version connection library which is
+ * defined in connection_lib.h.
+ * It also provides a reference implementation of connections manager.
+ */
+
+#include "connection_lib.h"
+#include "bh_platform.h"
+#include "app_manager_export.h"
+#include "module_wasm_app.h"
+#include "conn_tcp.h"
+#include "conn_udp.h"
+#include "conn_uart.h"
+
+#include <unistd.h>
+#include <sys/epoll.h>
+#include <sys/types.h>
+#include <arpa/inet.h>
+#include <fcntl.h>
+
+#define MAX_EVENTS 10
+#define IO_BUF_SIZE 256
+
+static bool polling_thread_run = true;
+
+/* Connection type */
+typedef enum conn_type {
+ CONN_TYPE_TCP,
+ CONN_TYPE_UDP,
+ CONN_TYPE_UART,
+ CONN_TYPE_UNKNOWN
+} conn_type_t;
+
+/* Sys connection */
+typedef struct sys_connection {
+ /* Next connection */
+ struct sys_connection *next;
+
+ /* Type */
+ conn_type_t type;
+
+ /* Handle to interact with wasm app */
+ uint32 handle;
+
+ /* Underlying connection ID, may be socket fd */
+ int fd;
+
+ /* Module id that the connection belongs to */
+ uint32 module_id;
+
+ /* Argument, such as dest addr for udp */
+ void *arg;
+} sys_connection_t;
+
+/* Epoll instance */
+static int epollfd;
+
+/* Connections list */
+static sys_connection_t *g_connections = NULL;
+
+/* Max handle */
+static uint32 g_handle_max = 0;
+
+/* Lock to protect g_connections and g_handle_max */
+static korp_mutex g_lock;
+
+/* Epoll events */
+static struct epoll_event epoll_events[MAX_EVENTS];
+
+/* Buffer to receive data */
+static char io_buf[IO_BUF_SIZE];
+
+static uint32
+_conn_open(wasm_module_inst_t module_inst, const char *name,
+ attr_container_t *args);
+static void
+_conn_close(uint32 handle);
+static int
+_conn_send(uint32 handle, const char *data, int len);
+static bool
+_conn_config(uint32 handle, attr_container_t *cfg);
+
+/* clang-format off */
+/*
+ * Platform implementation of connection library
+ */
+connection_interface_t connection_impl = {
+ ._open = _conn_open,
+ ._close = _conn_close,
+ ._send = _conn_send,
+ ._config = _conn_config
+};
+/* clang-format on */
+
+static void
+add_connection(sys_connection_t *conn)
+{
+ os_mutex_lock(&g_lock);
+
+ g_handle_max++;
+ if (g_handle_max == -1)
+ g_handle_max++;
+ conn->handle = g_handle_max;
+
+ if (g_connections) {
+ conn->next = g_connections;
+ g_connections = conn;
+ }
+ else {
+ g_connections = conn;
+ }
+
+ os_mutex_unlock(&g_lock);
+}
+
+#define FREE_CONNECTION(conn) \
+ do { \
+ if (conn->arg) \
+ wasm_runtime_free(conn->arg); \
+ wasm_runtime_free(conn); \
+ } while (0)
+
+static int
+get_app_conns_num(uint32 module_id)
+{
+ sys_connection_t *conn;
+ int num = 0;
+
+ os_mutex_lock(&g_lock);
+
+ conn = g_connections;
+ while (conn) {
+ if (conn->module_id == module_id)
+ num++;
+ conn = conn->next;
+ }
+
+ os_mutex_unlock(&g_lock);
+
+ return num;
+}
+
+static sys_connection_t *
+find_connection(uint32 handle, bool remove_found)
+{
+ sys_connection_t *conn, *prev = NULL;
+
+ os_mutex_lock(&g_lock);
+
+ conn = g_connections;
+ while (conn) {
+ if (conn->handle == handle) {
+ if (remove_found) {
+ if (prev != NULL) {
+ prev->next = conn->next;
+ }
+ else {
+ g_connections = conn->next;
+ }
+ }
+ os_mutex_unlock(&g_lock);
+ return conn;
+ }
+ else {
+ prev = conn;
+ conn = conn->next;
+ }
+ }
+
+ os_mutex_unlock(&g_lock);
+
+ return NULL;
+}
+
+static void
+cleanup_connections(uint32 module_id)
+{
+ sys_connection_t *conn, *prev = NULL;
+
+ os_mutex_lock(&g_lock);
+
+ conn = g_connections;
+ while (conn) {
+ if (conn->module_id == module_id) {
+ epoll_ctl(epollfd, EPOLL_CTL_DEL, conn->fd, NULL);
+ close(conn->fd);
+
+ if (prev != NULL) {
+ prev->next = conn->next;
+ FREE_CONNECTION(conn);
+ conn = prev->next;
+ }
+ else {
+ g_connections = conn->next;
+ FREE_CONNECTION(conn);
+ conn = g_connections;
+ }
+ }
+ else {
+ prev = conn;
+ conn = conn->next;
+ }
+ }
+
+ os_mutex_unlock(&g_lock);
+}
+
+static conn_type_t
+get_conn_type(const char *name)
+{
+ if (strcmp(name, "TCP") == 0)
+ return CONN_TYPE_TCP;
+ if (strcmp(name, "UDP") == 0)
+ return CONN_TYPE_UDP;
+ if (strcmp(name, "UART") == 0)
+ return CONN_TYPE_UART;
+
+ return CONN_TYPE_UNKNOWN;
+}
+
+/* --- connection lib function --- */
+static uint32
+_conn_open(wasm_module_inst_t module_inst, const char *name,
+ attr_container_t *args)
+{
+ int fd;
+ sys_connection_t *conn;
+ struct epoll_event ev;
+ uint32 module_id = app_manager_get_module_id(Module_WASM_App, module_inst);
+ bh_assert(module_id != ID_NONE);
+
+ if (get_app_conns_num(module_id) >= MAX_CONNECTION_PER_APP)
+ return -1;
+
+ conn = (sys_connection_t *)wasm_runtime_malloc(sizeof(*conn));
+ if (conn == NULL)
+ return -1;
+
+ memset(conn, 0, sizeof(*conn));
+ conn->module_id = module_id;
+ conn->type = get_conn_type(name);
+
+ /* Generate a handle and add to list */
+ add_connection(conn);
+
+ if (conn->type == CONN_TYPE_TCP) {
+ char *address;
+ uint16 port;
+
+ /* Check and parse connection parameters */
+ if (!attr_container_contain_key(args, "address")
+ || !attr_container_contain_key(args, "port"))
+ goto fail;
+
+ address = attr_container_get_as_string(args, "address");
+ port = attr_container_get_as_uint16(args, "port");
+
+ /* Connect to TCP server */
+ if (!address || (fd = tcp_open(address, port)) == -1)
+ goto fail;
+ }
+ else if (conn->type == CONN_TYPE_UDP) {
+ uint16 port;
+
+ /* Check and parse connection parameters */
+ if (!attr_container_contain_key(args, "bind port"))
+ goto fail;
+ port = attr_container_get_as_uint16(args, "bind port");
+
+ /* Bind port */
+ if ((fd = udp_open(port)) == -1)
+ goto fail;
+ }
+ else if (conn->type == CONN_TYPE_UART) {
+ char *device;
+ int baud;
+
+ /* Check and parse connection parameters */
+ if (!attr_container_contain_key(args, "device")
+ || !attr_container_contain_key(args, "baudrate"))
+ goto fail;
+ device = attr_container_get_as_string(args, "device");
+ baud = attr_container_get_as_int(args, "baudrate");
+
+ /* Open device */
+ if (!device || (fd = uart_open(device, baud)) == -1)
+ goto fail;
+ }
+ else {
+ goto fail;
+ }
+
+ conn->fd = fd;
+
+ /* Set current connection as event data */
+ ev.events = EPOLLIN;
+ ev.data.ptr = conn;
+
+ /* Monitor incoming data */
+ if (epoll_ctl(epollfd, EPOLL_CTL_ADD, fd, &ev) == -1) {
+ close(fd);
+ goto fail;
+ }
+
+ return conn->handle;
+
+fail:
+ find_connection(conn->handle, true);
+ wasm_runtime_free(conn);
+ return -1;
+}
+
+/* --- connection lib function --- */
+static void
+_conn_close(uint32 handle)
+{
+ sys_connection_t *conn = find_connection(handle, true);
+
+ if (conn != NULL) {
+ epoll_ctl(epollfd, EPOLL_CTL_DEL, conn->fd, NULL);
+ close(conn->fd);
+ FREE_CONNECTION(conn);
+ }
+}
+
+/* --- connection lib function --- */
+static int
+_conn_send(uint32 handle, const char *data, int len)
+{
+ sys_connection_t *conn = find_connection(handle, false);
+
+ if (conn == NULL)
+ return -1;
+
+ if (conn->type == CONN_TYPE_TCP)
+ return tcp_send(conn->fd, data, len);
+
+ if (conn->type == CONN_TYPE_UDP) {
+ struct sockaddr *addr = (struct sockaddr *)conn->arg;
+ return udp_send(conn->fd, addr, data, len);
+ }
+
+ if (conn->type == CONN_TYPE_UART)
+ return uart_send(conn->fd, data, len);
+
+ return -1;
+}
+
+/* --- connection lib function --- */
+static bool
+_conn_config(uint32 handle, attr_container_t *cfg)
+{
+ sys_connection_t *conn = find_connection(handle, false);
+
+ if (conn == NULL)
+ return false;
+
+ if (conn->type == CONN_TYPE_UDP) {
+ char *address;
+ uint16_t port;
+ struct sockaddr_in *addr;
+
+ /* Parse remote address/port */
+ if (!attr_container_contain_key(cfg, "address")
+ || !attr_container_contain_key(cfg, "port"))
+ return false;
+ if (!(address = attr_container_get_as_string(cfg, "address")))
+ return false;
+ port = attr_container_get_as_uint16(cfg, "port");
+
+ if (conn->arg == NULL) {
+ addr = (struct sockaddr_in *)wasm_runtime_malloc(sizeof(*addr));
+ if (addr == NULL)
+ return false;
+
+ memset(addr, 0, sizeof(*addr));
+ addr->sin_family = AF_INET;
+ addr->sin_addr.s_addr = inet_addr(address);
+ addr->sin_port = htons(port);
+
+ /* Set remote address as connection arg */
+ conn->arg = addr;
+ }
+ else {
+ addr = (struct sockaddr_in *)conn->arg;
+ addr->sin_addr.s_addr = inet_addr(address);
+ addr->sin_port = htons(port);
+ }
+
+ return true;
+ }
+
+ return false;
+}
+
+/* --- connection manager reference implementation ---*/
+
+typedef struct connection_event {
+ uint32 handle;
+ char *data;
+ uint32 len;
+} connection_event_t;
+
+static void
+connection_event_cleaner(connection_event_t *conn_event)
+{
+ if (conn_event->data != NULL)
+ wasm_runtime_free(conn_event->data);
+ wasm_runtime_free(conn_event);
+}
+
+static void
+post_msg_to_module(sys_connection_t *conn, char *data, uint32 len)
+{
+ module_data *module = module_data_list_lookup_id(conn->module_id);
+ char *data_copy = NULL;
+ connection_event_t *conn_data_event;
+ bh_message_t msg;
+
+ if (module == NULL)
+ return;
+
+ conn_data_event =
+ (connection_event_t *)wasm_runtime_malloc(sizeof(*conn_data_event));
+ if (conn_data_event == NULL)
+ return;
+
+ if (len > 0) {
+ data_copy = (char *)wasm_runtime_malloc(len);
+ if (data_copy == NULL) {
+ wasm_runtime_free(conn_data_event);
+ return;
+ }
+ bh_memcpy_s(data_copy, len, data, len);
+ }
+
+ memset(conn_data_event, 0, sizeof(*conn_data_event));
+ conn_data_event->handle = conn->handle;
+ conn_data_event->data = data_copy;
+ conn_data_event->len = len;
+
+ msg = bh_new_msg(CONNECTION_EVENT_WASM, conn_data_event,
+ sizeof(*conn_data_event), connection_event_cleaner);
+ if (!msg) {
+ connection_event_cleaner(conn_data_event);
+ return;
+ }
+
+ bh_post_msg2(module->queue, msg);
+}
+
+static void *
+polling_thread_routine(void *arg)
+{
+ while (polling_thread_run) {
+ int i, n;
+
+ n = epoll_wait(epollfd, epoll_events, MAX_EVENTS, -1);
+
+ if (n == -1 && errno != EINTR)
+ continue;
+
+ for (i = 0; i < n; i++) {
+ sys_connection_t *conn =
+ (sys_connection_t *)epoll_events[i].data.ptr;
+
+ if (conn->type == CONN_TYPE_TCP) {
+ int count = tcp_recv(conn->fd, io_buf, IO_BUF_SIZE);
+ if (count <= 0) {
+ /* Connection is closed by peer */
+ post_msg_to_module(conn, NULL, 0);
+ _conn_close(conn->handle);
+ }
+ else {
+ /* Data is received */
+ post_msg_to_module(conn, io_buf, count);
+ }
+ }
+ else if (conn->type == CONN_TYPE_UDP) {
+ int count = udp_recv(conn->fd, io_buf, IO_BUF_SIZE);
+ if (count > 0)
+ post_msg_to_module(conn, io_buf, count);
+ }
+ else if (conn->type == CONN_TYPE_UART) {
+ int count = uart_recv(conn->fd, io_buf, IO_BUF_SIZE);
+ if (count > 0)
+ post_msg_to_module(conn, io_buf, count);
+ }
+ }
+ }
+
+ return NULL;
+}
+
+void
+app_mgr_connection_event_callback(module_data *m_data, bh_message_t msg)
+{
+ uint32 argv[3];
+ wasm_function_inst_t func_on_conn_data;
+ bh_assert(CONNECTION_EVENT_WASM == bh_message_type(msg));
+ wasm_data *wasm_app_data = (wasm_data *)m_data->internal_data;
+ wasm_module_inst_t inst = wasm_app_data->wasm_module_inst;
+ connection_event_t *conn_event =
+ (connection_event_t *)bh_message_payload(msg);
+ int32 data_offset;
+
+ if (conn_event == NULL)
+ return;
+
+ func_on_conn_data = wasm_runtime_lookup_function(
+ inst, "_on_connection_data", "(i32i32i32)");
+ if (!func_on_conn_data)
+ func_on_conn_data = wasm_runtime_lookup_function(
+ inst, "on_connection_data", "(i32i32i32)");
+ if (!func_on_conn_data) {
+ printf("Cannot find function on_connection_data\n");
+ return;
+ }
+
+ /* 0 len means connection closed */
+ if (conn_event->len == 0) {
+ argv[0] = conn_event->handle;
+ argv[1] = 0;
+ argv[2] = 0;
+ if (!wasm_runtime_call_wasm(wasm_app_data->exec_env, func_on_conn_data,
+ 3, argv)) {
+ const char *exception = wasm_runtime_get_exception(inst);
+ bh_assert(exception);
+ printf(":Got exception running wasm code: %s\n", exception);
+ wasm_runtime_clear_exception(inst);
+ return;
+ }
+ }
+ else {
+ data_offset = wasm_runtime_module_dup_data(inst, conn_event->data,
+ conn_event->len);
+ if (data_offset == 0) {
+ const char *exception = wasm_runtime_get_exception(inst);
+ if (exception) {
+ printf("Got exception running wasm code: %s\n", exception);
+ wasm_runtime_clear_exception(inst);
+ }
+ return;
+ }
+
+ argv[0] = conn_event->handle;
+ argv[1] = (uint32)data_offset;
+ argv[2] = conn_event->len;
+ if (!wasm_runtime_call_wasm(wasm_app_data->exec_env, func_on_conn_data,
+ 3, argv)) {
+ const char *exception = wasm_runtime_get_exception(inst);
+ bh_assert(exception);
+ printf(":Got exception running wasm code: %s\n", exception);
+ wasm_runtime_clear_exception(inst);
+ wasm_runtime_module_free(inst, data_offset);
+ return;
+ }
+ wasm_runtime_module_free(inst, data_offset);
+ }
+}
+
+bool
+init_connection_framework()
+{
+ korp_tid tid;
+
+ epollfd = epoll_create(MAX_EVENTS);
+ if (epollfd == -1)
+ return false;
+
+ if (os_mutex_init(&g_lock) != 0) {
+ close(epollfd);
+ return false;
+ }
+
+ if (!wasm_register_cleanup_callback(cleanup_connections)) {
+ goto fail;
+ }
+
+ if (!wasm_register_msg_callback(CONNECTION_EVENT_WASM,
+ app_mgr_connection_event_callback)) {
+ goto fail;
+ }
+
+ if (os_thread_create(&tid, polling_thread_routine, NULL,
+ BH_APPLET_PRESERVED_STACK_SIZE)
+ != 0) {
+ goto fail;
+ }
+
+ return true;
+
+fail:
+ os_mutex_destroy(&g_lock);
+ close(epollfd);
+ return false;
+}
+
+void
+exit_connection_framework()
+{
+ polling_thread_run = false;
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.cmake
new file mode 100644
index 000000000..c8f2b487e
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/linux/connection_mgr.cmake
@@ -0,0 +1,13 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_CONN_MGR_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_LIB_CONN_MGR_DIR})
+
+
+file (GLOB_RECURSE source_all ${WASM_LIB_CONN_MGR_DIR}/*.c)
+
+set (WASM_LIB_CONN_MGR_SOURCE ${source_all})
+
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/wasm_lib.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/wasm_lib.cmake
new file mode 100644
index 000000000..58db0c1d8
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/wasm_lib.cmake
@@ -0,0 +1,18 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_CONN_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_LIB_CONN_DIR})
+
+add_definitions (-DAPP_FRAMEWORK_CONNECTION)
+
+
+include (${CMAKE_CURRENT_LIST_DIR}/${WAMR_BUILD_PLATFORM}/connection_mgr.cmake)
+
+file (GLOB source_all
+ ${WASM_LIB_CONN_MGR_SOURCE}
+ ${WASM_LIB_CONN_DIR}/*.c
+)
+
+set (WASM_APP_LIB_CURRENT_SOURCE ${source_all})
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_lib_impl.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_lib_impl.c
new file mode 100644
index 000000000..a812a71a2
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_lib_impl.c
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+/*
+ * Note:
+ * This file implements the linux version connection library which is
+ * defined in connection_lib.h.
+ * It also provides a reference impl of connections manager.
+ */
+
+#include "connection_lib.h"
+
+/* clang-format off */
+/*
+ * Platform implementation of connection library
+ */
+connection_interface_t connection_impl = {
+ ._open = NULL,
+ ._close = NULL,
+ ._send = NULL,
+ ._config = NULL
+};
+/* clang-format on */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_mgr.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_mgr.cmake
new file mode 100644
index 000000000..c8f2b487e
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/connection/native/zephyr/connection_mgr.cmake
@@ -0,0 +1,13 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_CONN_MGR_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_LIB_CONN_MGR_DIR})
+
+
+file (GLOB_RECURSE source_all ${WASM_LIB_CONN_MGR_DIR}/*.c)
+
+set (WASM_LIB_CONN_MGR_SOURCE ${source_all})
+
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor.c
new file mode 100644
index 000000000..d898a1d3a
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor.c
@@ -0,0 +1,122 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "wa-inc/sensor.h"
+
+#include "sensor_api.h"
+
+typedef struct _sensor {
+ struct _sensor *next;
+ char *name;
+ uint32 handle;
+ void (*sensor_callback)(sensor_t, attr_container_t *, void *);
+ void *user_data;
+} sensor;
+
+static sensor_t g_sensors = NULL;
+
+sensor_t
+sensor_open(const char *name, int index,
+ sensor_event_handler_f sensor_event_handler, void *user_data)
+{
+ uint32 id = wasm_sensor_open(name, index);
+ if (id == -1)
+ return NULL;
+
+ // create local node for holding the user callback
+ sensor_t sensor = (sensor_t)malloc(sizeof(struct _sensor));
+ if (sensor == NULL)
+ return NULL;
+
+ memset(sensor, 0, sizeof(struct _sensor));
+ sensor->handle = id;
+ sensor->name = strdup(name);
+ sensor->user_data = user_data;
+ sensor->sensor_callback = sensor_event_handler;
+
+ if (!sensor->name) {
+ free(sensor);
+ return NULL;
+ }
+
+ if (g_sensors == NULL) {
+ g_sensors = sensor;
+ }
+ else {
+ sensor->next = g_sensors;
+ g_sensors = sensor;
+ }
+
+ return sensor;
+}
+
+bool
+sensor_config_with_attr_container(sensor_t sensor, attr_container_t *cfg)
+{
+ char *buffer = (char *)cfg;
+ int len = attr_container_get_serialize_length(cfg);
+
+ return wasm_sensor_config_with_attr_container(sensor->handle, buffer, len);
+}
+
+bool
+sensor_config(sensor_t sensor, int interval, int bit_cfg, int delay)
+{
+ bool ret = wasm_sensor_config(sensor->handle, interval, bit_cfg, delay);
+ return ret;
+}
+
+bool
+sensor_close(sensor_t sensor)
+{
+ wasm_sensor_close(sensor->handle);
+
+ // remove local node
+ sensor_t s = g_sensors;
+ sensor_t prev = NULL;
+ while (s) {
+ if (s == sensor) {
+ if (prev == NULL) {
+ g_sensors = s->next;
+ }
+ else {
+ prev->next = s->next;
+ }
+ free(s->name);
+ free(s);
+ return true;
+ }
+ else {
+ prev = s;
+ s = s->next;
+ }
+ }
+
+ return false;
+}
+
+/*
+ *
+ * API for native layer to callback for sensor events
+ *
+ */
+
+void
+on_sensor_event(uint32 sensor_id, char *buffer, int len)
+{
+ attr_container_t *sensor_data = (attr_container_t *)buffer;
+
+ // lookup the sensor and call the handlers
+ sensor_t s = g_sensors;
+ sensor_t prev = NULL;
+ while (s) {
+ if (s->handle == sensor_id) {
+ s->sensor_callback(s, sensor_data, s->user_data);
+ break;
+ }
+
+ s = s->next;
+ }
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor_api.h
new file mode 100644
index 000000000..ad6a7aa24
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/sensor_api.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _SENSOR_API_H_
+#define _SENSOR_API_H_
+
+#include "bh_platform.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+uint32
+wasm_sensor_open(const char *name, int instance);
+
+bool
+wasm_sensor_config(uint32 sensor, uint32 interval, int bit_cfg, uint32 delay);
+
+bool
+wasm_sensor_config_with_attr_container(uint32 sensor, char *buffer, uint32 len);
+
+bool
+wasm_sensor_close(uint32 sensor);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _SENSOR_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wa-inc/sensor.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wa-inc/sensor.h
new file mode 100644
index 000000000..109f895d3
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wa-inc/sensor.h
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _AEE_SENSOR_H_
+#define _AEE_SENSOR_H_
+
+#include "bi-inc/attr_container.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* board producer define sensor */
+struct _sensor;
+typedef struct _sensor *sensor_t;
+
+/**
+ * @typedef sensor_event_handler_f
+ *
+ * @brief Define the signature of callback function for API
+ * sensor_open() to handle sensor event.
+ *
+ * @param sensor the sensor which the event belong to
+ * @param sensor_event the sensor event
+ * @param user_data user data associated with the sensor which is set when
+ * calling sensor_open().
+ *
+ * @see sensor_open
+ */
+typedef void (*sensor_event_handler_f)(sensor_t sensor,
+ attr_container_t *sensor_event,
+ void *user_data);
+
+/*
+ *****************
+ * Sensor APIs
+ *****************
+ */
+
+/**
+ * @brief Open sensor.
+ *
+ * @param name sensor name
+ * @param index sensor index
+ * @param handler callback function to handle the sensor event
+ * @param user_data user data
+ *
+ * @return the sensor opened if success, NULL otherwise
+ */
+sensor_t
+sensor_open(const char *name, int index, sensor_event_handler_f handler,
+ void *user_data);
+
+/**
+ * @brief Configure sensor with interval/bit_cfg/delay values.
+ *
+ * @param sensor the sensor to be configured
+ * @param interval sensor event interval
+ * @param bit_cfg sensor bit config
+ * @param delay sensor delay
+ *
+ * @return true if success, false otherwise
+ */
+bool
+sensor_config(sensor_t sensor, int interval, int bit_cfg, int delay);
+
+/**
+ * @brief Configure sensor with attr_container_t object.
+ *
+ * @param sensor the sensor to be configured
+ * @param cfg the configuration
+ *
+ * @return true if success, false otherwise
+ */
+bool
+sensor_config_with_attr_container(sensor_t sensor, attr_container_t *cfg);
+
+/**
+ * @brief Close sensor.
+ *
+ * @param sensor the sensor to be closed
+ *
+ * @return true if success, false otherwise
+ */
+bool
+sensor_close(sensor_t sensor);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wasm_app.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wasm_app.cmake
new file mode 100644
index 000000000..4b14a8bef
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/app/wasm_app.cmake
@@ -0,0 +1,11 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_APP_SENSOR_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(${WASM_APP_SENSOR_DIR})
+
+
+file (GLOB_RECURSE source_all ${WASM_APP_SENSOR_DIR}/*.c)
+
+set (WASM_APP_CURRENT_SOURCE ${source_all})
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.c
new file mode 100644
index 000000000..ad7a3fbf5
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.c
@@ -0,0 +1,434 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "runtime_sensor.h"
+#include "app_manager_export.h"
+#include "module_wasm_app.h"
+#include "bh_platform.h"
+
+static sys_sensor_t *g_sys_sensors = NULL;
+static uint32 g_sensor_id_max = 0;
+
+static sensor_client_t *
+find_sensor_client(sys_sensor_t *sensor, unsigned int client_id,
+ bool remove_if_found);
+
+void (*rechedule_sensor_callback)() = NULL;
+
+/*
+ * API for the applications to call - don't call it from the runtime
+ *
+ */
+
+static void
+sensor_event_cleaner(sensor_event_data_t *sensor_event)
+{
+ if (sensor_event->data != NULL) {
+ if (sensor_event->data_fmt == FMT_ATTR_CONTAINER)
+ attr_container_destroy(sensor_event->data);
+ else
+ wasm_runtime_free(sensor_event->data);
+ }
+
+ wasm_runtime_free(sensor_event);
+}
+
+static void
+wasm_sensor_callback(void *client, uint32 sensor_id, void *user_data)
+{
+ attr_container_t *sensor_data = (attr_container_t *)user_data;
+ attr_container_t *sensor_data_clone;
+ int sensor_data_len;
+ sensor_event_data_t *sensor_event;
+ bh_message_t msg;
+ sensor_client_t *c = (sensor_client_t *)client;
+
+ module_data *module = module_data_list_lookup_id(c->client_id);
+ if (module == NULL)
+ return;
+
+ if (sensor_data == NULL)
+ return;
+
+ sensor_data_len = attr_container_get_serialize_length(sensor_data);
+ sensor_data_clone =
+ (attr_container_t *)wasm_runtime_malloc(sensor_data_len);
+ if (sensor_data_clone == NULL)
+ return;
+
+ /* multiple sensor clients may use/free the sensor data, so make a copy */
+ bh_memcpy_s(sensor_data_clone, sensor_data_len, sensor_data,
+ sensor_data_len);
+
+ sensor_event =
+ (sensor_event_data_t *)wasm_runtime_malloc(sizeof(*sensor_event));
+ if (sensor_event == NULL) {
+ wasm_runtime_free(sensor_data_clone);
+ return;
+ }
+
+ memset(sensor_event, 0, sizeof(*sensor_event));
+ sensor_event->sensor_id = sensor_id;
+ sensor_event->data = sensor_data_clone;
+ sensor_event->data_fmt = FMT_ATTR_CONTAINER;
+
+ msg = bh_new_msg(SENSOR_EVENT_WASM, sensor_event, sizeof(*sensor_event),
+ sensor_event_cleaner);
+ if (!msg) {
+ sensor_event_cleaner(sensor_event);
+ return;
+ }
+
+ bh_post_msg2(module->queue, msg);
+}
+
+bool
+wasm_sensor_config(wasm_exec_env_t exec_env, uint32 sensor, uint32 interval,
+ int bit_cfg, uint32 delay)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ attr_container_t *attr_cont;
+ sensor_client_t *c;
+ sensor_obj_t s = find_sys_sensor_id(sensor);
+ if (s == NULL)
+ return false;
+
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+ bh_assert(mod_id != ID_NONE);
+
+ os_mutex_lock(&s->lock);
+
+ c = find_sensor_client(s, mod_id, false);
+ if (c == NULL) {
+ os_mutex_unlock(&s->lock);
+ return false;
+ }
+
+ c->interval = interval;
+ c->bit_cfg = bit_cfg;
+ c->delay = delay;
+
+ os_mutex_unlock(&s->lock);
+
+ if (s->config != NULL) {
+ attr_cont = attr_container_create("config sensor");
+ attr_container_set_int(&attr_cont, "interval", (int)interval);
+ attr_container_set_int(&attr_cont, "bit_cfg", bit_cfg);
+ attr_container_set_int(&attr_cont, "delay", (int)delay);
+ s->config(s, attr_cont);
+ attr_container_destroy(attr_cont);
+ }
+
+ refresh_read_interval(s);
+
+ reschedule_sensor_read();
+
+ return true;
+}
+
+uint32
+wasm_sensor_open(wasm_exec_env_t exec_env, char *name, int instance)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+
+ if (name != NULL) {
+ sensor_client_t *c;
+ sys_sensor_t *s = find_sys_sensor(name, instance);
+ if (s == NULL)
+ return (uint32)-1;
+
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+ bh_assert(mod_id != ID_NONE);
+
+ os_mutex_lock(&s->lock);
+
+ c = find_sensor_client(s, mod_id, false);
+ if (c) {
+ // the app already opened this sensor
+ os_mutex_unlock(&s->lock);
+ return (uint32)-1;
+ }
+
+ sensor_client_t *client =
+ (sensor_client_t *)wasm_runtime_malloc(sizeof(sensor_client_t));
+ if (client == NULL) {
+ os_mutex_unlock(&s->lock);
+ return (uint32)-1;
+ }
+
+ memset(client, 0, sizeof(sensor_client_t));
+ client->client_id = mod_id;
+ client->client_callback = (void *)wasm_sensor_callback;
+ client->interval = s->default_interval;
+ client->next = s->clients;
+ s->clients = client;
+
+ os_mutex_unlock(&s->lock);
+
+ refresh_read_interval(s);
+
+ reschedule_sensor_read();
+
+ return s->sensor_id;
+ }
+
+ return (uint32)-1;
+}
+
+bool
+wasm_sensor_config_with_attr_container(wasm_exec_env_t exec_env, uint32 sensor,
+ char *buffer, int len)
+{
+ if (buffer != NULL) {
+ attr_container_t *cfg = (attr_container_t *)buffer;
+ sensor_obj_t s = find_sys_sensor_id(sensor);
+ if (s == NULL)
+ return false;
+
+ if (s->config == NULL)
+ return false;
+
+ return s->config(s, cfg);
+ }
+
+ return false;
+}
+
+bool
+wasm_sensor_close(wasm_exec_env_t exec_env, uint32 sensor)
+{
+ wasm_module_inst_t module_inst = get_module_inst(exec_env);
+ unsigned int mod_id =
+ app_manager_get_module_id(Module_WASM_App, module_inst);
+ unsigned int client_id = mod_id;
+ sensor_obj_t s = find_sys_sensor_id(sensor);
+ sensor_client_t *c;
+
+ bh_assert(mod_id != ID_NONE);
+
+ if (s == NULL)
+ return false;
+
+ os_mutex_lock(&s->lock);
+ if ((c = find_sensor_client(s, client_id, true)) != NULL)
+ wasm_runtime_free(c);
+ os_mutex_unlock(&s->lock);
+
+ refresh_read_interval(s);
+
+ reschedule_sensor_read();
+
+ return true;
+}
+
+/*
+ *
+ * sensor framework API - don't expose to the applications
+ *
+ */
+void
+set_sensor_reshceduler(void (*callback)())
+{
+ rechedule_sensor_callback = callback;
+}
+
+// used for other threads to wakeup the sensor read thread
+void
+reschedule_sensor_read()
+{
+ if (rechedule_sensor_callback)
+ rechedule_sensor_callback();
+}
+
+void
+refresh_read_interval(sensor_obj_t sensor)
+{
+ sensor_client_t *c;
+ uint32 interval = sensor->default_interval;
+ os_mutex_lock(&sensor->lock);
+
+ c = sensor->clients;
+ if (c)
+ interval = c->interval;
+
+ while (c) {
+ if (c->interval < interval)
+ interval = c->interval;
+ c = c->next;
+ }
+
+ os_mutex_unlock(&sensor->lock);
+
+ sensor->read_interval = interval;
+}
+
+sensor_obj_t
+add_sys_sensor(char *name, char *description, int instance,
+ uint32 default_interval, void *read_func, void *config_func)
+{
+ sys_sensor_t *s = (sys_sensor_t *)wasm_runtime_malloc(sizeof(sys_sensor_t));
+ if (s == NULL)
+ return NULL;
+
+ memset(s, 0, sizeof(*s));
+ s->name = bh_strdup(name);
+ s->sensor_instance = instance;
+ s->default_interval = default_interval;
+
+ if (!s->name) {
+ wasm_runtime_free(s);
+ return NULL;
+ }
+
+ if (description) {
+ s->description = bh_strdup(description);
+ if (!s->description) {
+ wasm_runtime_free(s->name);
+ wasm_runtime_free(s);
+ return NULL;
+ }
+ }
+
+ g_sensor_id_max++;
+ if (g_sensor_id_max == UINT32_MAX)
+ g_sensor_id_max++;
+ s->sensor_id = g_sensor_id_max;
+
+ s->read = read_func;
+ s->config = config_func;
+
+ if (g_sys_sensors == NULL) {
+ g_sys_sensors = s;
+ }
+ else {
+ s->next = g_sys_sensors;
+ g_sys_sensors = s;
+ }
+
+ if (os_mutex_init(&s->lock) != 0) {
+ if (s->description) {
+ wasm_runtime_free(s->description);
+ }
+ wasm_runtime_free(s->name);
+ wasm_runtime_free(s);
+ }
+
+ return s;
+}
+
+sensor_obj_t
+find_sys_sensor(const char *name, int instance)
+{
+ sys_sensor_t *s = g_sys_sensors;
+ while (s) {
+ if (strcmp(s->name, name) == 0 && s->sensor_instance == instance)
+ return s;
+
+ s = s->next;
+ }
+ return NULL;
+}
+
+sensor_obj_t
+find_sys_sensor_id(uint32 sensor_id)
+{
+ sys_sensor_t *s = g_sys_sensors;
+ while (s) {
+ if (s->sensor_id == sensor_id)
+ return s;
+
+ s = s->next;
+ }
+ return NULL;
+}
+
+sensor_client_t *
+find_sensor_client(sys_sensor_t *sensor, unsigned int client_id,
+ bool remove_if_found)
+{
+ sensor_client_t *prev = NULL, *c = sensor->clients;
+
+ while (c) {
+ sensor_client_t *next = c->next;
+ if (c->client_id == client_id) {
+ if (remove_if_found) {
+ if (prev)
+ prev->next = next;
+ else
+ sensor->clients = next;
+ }
+ return c;
+ }
+ else {
+ prev = c;
+ c = c->next;
+ }
+ }
+
+ return NULL;
+}
+
+// return the milliseconds to next check
+uint32
+check_sensor_timers()
+{
+ uint32 ms_to_next_check = UINT32_MAX;
+ uint32 now = (uint32)bh_get_tick_ms();
+
+ sys_sensor_t *s = g_sys_sensors;
+ while (s) {
+ uint32 last_read = s->last_read;
+ uint32 elpased_ms = bh_get_elpased_ms(&last_read);
+
+ if (s->read_interval <= 0 || s->clients == NULL) {
+ s = s->next;
+ continue;
+ }
+
+ if (elpased_ms >= s->read_interval) {
+ attr_container_t *data = s->read(s);
+ if (data) {
+ sensor_client_t *client = s->clients;
+ while (client) {
+ client->client_callback(client, s->sensor_id, data);
+ client = client->next;
+ }
+ attr_container_destroy(data);
+ }
+
+ s->last_read = now;
+
+ if (s->read_interval < ms_to_next_check)
+ ms_to_next_check = s->read_interval;
+ }
+ else {
+ uint32 remaining = s->read_interval - elpased_ms;
+ if (remaining < ms_to_next_check)
+ ms_to_next_check = remaining;
+ }
+
+ s = s->next;
+ }
+
+ return ms_to_next_check;
+}
+
+void
+sensor_cleanup_callback(uint32 module_id)
+{
+ sys_sensor_t *s = g_sys_sensors;
+
+ while (s) {
+ sensor_client_t *c;
+ os_mutex_lock(&s->lock);
+ if ((c = find_sensor_client(s, module_id, true)) != NULL) {
+ wasm_runtime_free(c);
+ }
+ os_mutex_unlock(&s->lock);
+ s = s->next;
+ }
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.h
new file mode 100644
index 000000000..d7c893111
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.h
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef LIB_EXTENSION_RUNTIME_SENSOR_H_
+#define LIB_EXTENSION_RUNTIME_SENSOR_H_
+
+#include "bh_platform.h"
+#include "bi-inc/attr_container.h"
+#include "wasm_export.h"
+#include "sensor_native_api.h"
+
+struct _sys_sensor;
+typedef struct _sys_sensor *sensor_obj_t;
+
+typedef struct _sensor_client {
+ struct _sensor_client *next;
+ unsigned int client_id; // the app id
+ uint32 interval;
+ int bit_cfg;
+ uint32 delay;
+ void (*client_callback)(void *client, uint32, attr_container_t *);
+} sensor_client_t;
+
+typedef struct _sys_sensor {
+ struct _sys_sensor *next;
+ char *name;
+ int sensor_instance;
+ char *description;
+ uint32 sensor_id;
+ sensor_client_t *clients;
+ /* app, sensor mgr and app mgr may access the clients at the same time,
+ so need a lock to protect the clients */
+ korp_mutex lock;
+ uint32 last_read;
+ uint32 read_interval;
+ uint32 default_interval;
+
+ /* TODO: may support other type return value, such as 'cbor' */
+ attr_container_t *(*read)(void *);
+ bool (*config)(void *, void *);
+
+} sys_sensor_t;
+
+sensor_obj_t
+add_sys_sensor(char *name, char *description, int instance,
+ uint32 default_interval, void *read_func, void *config_func);
+sensor_obj_t
+find_sys_sensor(const char *name, int instance);
+sensor_obj_t
+find_sys_sensor_id(uint32 sensor_id);
+void
+refresh_read_interval(sensor_obj_t sensor);
+void
+sensor_cleanup_callback(uint32 module_id);
+uint32
+check_sensor_timers();
+void
+reschedule_sensor_read();
+
+bool
+init_sensor_framework();
+void
+start_sensor_framework();
+void
+exit_sensor_framework();
+
+#endif /* LIB_EXTENSION_RUNTIME_SENSOR_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.inl b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.inl
new file mode 100644
index 000000000..a7b9f4778
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/runtime_sensor.inl
@@ -0,0 +1,9 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+EXPORT_WASM_API_WITH_SIG(wasm_sensor_open, "($i)i"),
+EXPORT_WASM_API_WITH_SIG(wasm_sensor_config, "(iiii)i"),
+EXPORT_WASM_API_WITH_SIG(wasm_sensor_config_with_attr_container, "(i*~)i"),
+EXPORT_WASM_API_WITH_SIG(wasm_sensor_close, "(i)i"),
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_mgr_ref.c b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_mgr_ref.c
new file mode 100644
index 000000000..474ec738d
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_mgr_ref.c
@@ -0,0 +1,148 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "bh_platform.h"
+#include "runtime_sensor.h"
+#include "bi-inc/attr_container.h"
+#include "module_wasm_app.h"
+#include "wasm_export.h"
+
+/*
+ *
+ * One reference implementation for sensor manager
+ *
+ *
+ */
+static korp_cond cond;
+static korp_mutex mutex;
+static bool sensor_check_thread_run = true;
+
+void
+app_mgr_sensor_event_callback(module_data *m_data, bh_message_t msg)
+{
+ uint32 argv[3];
+ wasm_function_inst_t func_onSensorEvent;
+
+ bh_assert(SENSOR_EVENT_WASM == bh_message_type(msg));
+ wasm_data *wasm_app_data = (wasm_data *)m_data->internal_data;
+ wasm_module_inst_t inst = wasm_app_data->wasm_module_inst;
+
+ sensor_event_data_t *payload =
+ (sensor_event_data_t *)bh_message_payload(msg);
+ if (payload == NULL)
+ return;
+
+ func_onSensorEvent =
+ wasm_runtime_lookup_function(inst, "_on_sensor_event", "(i32i32i32)");
+ if (!func_onSensorEvent)
+ func_onSensorEvent = wasm_runtime_lookup_function(
+ inst, "on_sensor_event", "(i32i32i32)");
+ if (!func_onSensorEvent) {
+ printf("Cannot find function on_sensor_event\n");
+ }
+ else {
+ int32 sensor_data_offset;
+ uint32 sensor_data_len;
+
+ if (payload->data_fmt == FMT_ATTR_CONTAINER) {
+ sensor_data_len =
+ attr_container_get_serialize_length(payload->data);
+ }
+ else {
+ printf("Unsupported sensor data format: %d\n", payload->data_fmt);
+ return;
+ }
+
+ sensor_data_offset =
+ wasm_runtime_module_dup_data(inst, payload->data, sensor_data_len);
+ if (sensor_data_offset == 0) {
+ const char *exception = wasm_runtime_get_exception(inst);
+ if (exception) {
+ printf("Got exception running wasm code: %s\n", exception);
+ wasm_runtime_clear_exception(inst);
+ }
+ return;
+ }
+
+ argv[0] = payload->sensor_id;
+ argv[1] = (uint32)sensor_data_offset;
+ argv[2] = sensor_data_len;
+
+ if (!wasm_runtime_call_wasm(wasm_app_data->exec_env, func_onSensorEvent,
+ 3, argv)) {
+ const char *exception = wasm_runtime_get_exception(inst);
+ bh_assert(exception);
+ printf(":Got exception running wasm code: %s\n", exception);
+ wasm_runtime_clear_exception(inst);
+ wasm_runtime_module_free(inst, sensor_data_offset);
+ return;
+ }
+
+ wasm_runtime_module_free(inst, sensor_data_offset);
+ }
+}
+
+static void
+thread_sensor_check(void *arg)
+{
+ while (sensor_check_thread_run) {
+ uint32 ms_to_expiry = check_sensor_timers();
+ if (ms_to_expiry == UINT32_MAX)
+ ms_to_expiry = 5000;
+ os_mutex_lock(&mutex);
+ os_cond_reltimedwait(&cond, &mutex, ms_to_expiry * 1000);
+ os_mutex_unlock(&mutex);
+ }
+}
+
+static void
+cb_wakeup_thread()
+{
+ os_cond_signal(&cond);
+}
+
+void
+set_sensor_reshceduler(void (*callback)());
+
+bool
+init_sensor_framework()
+{
+ /* init the mutext and conditions */
+ if (os_cond_init(&cond) != 0) {
+ return false;
+ }
+
+ if (os_mutex_init(&mutex) != 0) {
+ os_cond_destroy(&cond);
+ return false;
+ }
+
+ set_sensor_reshceduler(cb_wakeup_thread);
+
+ wasm_register_msg_callback(SENSOR_EVENT_WASM,
+ app_mgr_sensor_event_callback);
+
+ wasm_register_cleanup_callback(sensor_cleanup_callback);
+
+ return true;
+}
+
+void
+start_sensor_framework()
+{
+ korp_tid tid;
+
+ os_thread_create(&tid, (void *)thread_sensor_check, NULL,
+ BH_APPLET_PRESERVED_STACK_SIZE);
+}
+
+void
+exit_sensor_framework()
+{
+ sensor_check_thread_run = false;
+ reschedule_sensor_read();
+
+ // todo: wait the sensor thread termination
+}
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_native_api.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_native_api.h
new file mode 100644
index 000000000..0bbb315ca
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/sensor_native_api.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _SENSOR_NATIVE_API_H_
+#define _SENSOR_NATIVE_API_H_
+
+#include "bh_platform.h"
+#include "wasm_export.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+bool
+wasm_sensor_config(wasm_exec_env_t exec_env, uint32 sensor, uint32 interval,
+ int bit_cfg, uint32 delay);
+uint32
+wasm_sensor_open(wasm_exec_env_t exec_env, char *name, int instance);
+
+bool
+wasm_sensor_config_with_attr_container(wasm_exec_env_t exec_env, uint32 sensor,
+ char *buffer, int len);
+
+bool
+wasm_sensor_close(wasm_exec_env_t exec_env, uint32 sensor);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _SENSOR_NATIVE_API_H_ */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/wasm_lib.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/wasm_lib.cmake
new file mode 100644
index 000000000..65a83ba59
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/sensor/native/wasm_lib.cmake
@@ -0,0 +1,14 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_SENSOR_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+add_definitions (-DAPP_FRAMEWORK_SENSOR)
+
+include_directories(${WASM_LIB_SENSOR_DIR})
+
+
+file (GLOB_RECURSE source_all ${WASM_LIB_SENSOR_DIR}/*.c)
+
+set (WASM_APP_LIB_CURRENT_SOURCE ${source_all})
+
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wa-inc/app_xxx.h b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wa-inc/app_xxx.h
new file mode 100644
index 000000000..ac30842f0
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wa-inc/app_xxx.h
@@ -0,0 +1,8 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+/*
+ header file for wasm application
+*/ \ No newline at end of file
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wasm_app.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wasm_app.cmake
new file mode 100644
index 000000000..16ca237ae
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/app/wasm_app.cmake
@@ -0,0 +1,16 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_APP_CURRENT_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(
+ ${WASM_APP_CURRENT_DIR}
+ # Add your include dir here
+)
+
+file (GLOB_RECURSE source_all
+ ${WASM_APP_CURRENT_DIR}/*.c
+ # Add your source file here
+)
+
+set (WASM_APP_CURRENT_SOURCE ${source_all})
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/app_xxx.inl b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/app_xxx.inl
new file mode 100644
index 000000000..2503fe454
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/app_xxx.inl
@@ -0,0 +1,6 @@
+/*
+ * Copyright (C) 2019 Intel Corporation. All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+/* EXPORT_WASM_API(your_api_here), */
diff --git a/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/wasm_lib.cmake b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/wasm_lib.cmake
new file mode 100644
index 000000000..2601c1d27
--- /dev/null
+++ b/fluent-bit/lib/wasm-micro-runtime-WAMR-1.2.2/core/app-framework/template/native/wasm_lib.cmake
@@ -0,0 +1,17 @@
+# Copyright (C) 2019 Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (WASM_LIB_CURRENT_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+include_directories(
+ ${WASM_LIB_CURRENT_DIR}
+ # Add your include dir here
+)
+
+file (GLOB_RECURSE source_all
+ ${WASM_LIB_CURRENT_DIR}/*.c
+ # Add your source file here
+)
+
+set (WASM_APP_LIB_CURRENT_SOURCE ${source_all})
+