Эх сурвалжийг харах

Add Cosmopolitan Libc Platform (#2598)

This PR adds the Cosmopolitan Libc platform enabling compatibility with multiple
x86_64 operating systems with the same binary. The platform is similar to the
Linux platform, but for now only x86_64 with interpreter modes are supported.

The only major change to the core is `posix.c/convert_errno()` was rewritten to use
a switch statement. With Cosmopolitan errno values depend on the currently
running operating system, and so they are non-constant and cannot be used in array
designators. However, the `cosmocc` compiler allows non-constant case labels in
switch statements, enabling the new version.

And updated wamr-test-suites script to add `-j <platform>` option. The spec tests
can be ran via `CC=cosmocc ./test_wamr.sh -j cosmopolitan -t classic-interp`
or `CC=cosmocc ./test_wamr.sh -j cosmopolitan -t fast-interp`.
Gavin Hayes 2 жил өмнө
parent
commit
d8ee771e28

+ 90 - 89
core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/posix.c

@@ -60,98 +60,99 @@ static_assert(sizeof(struct iovec) == sizeof(__wasi_ciovec_t),
 static __wasi_errno_t
 convert_errno(int error)
 {
-    static const __wasi_errno_t errors[] = {
-#define X(v) [v] = __WASI_##v
-        X(E2BIG),
-        X(EACCES),
-        X(EADDRINUSE),
-        X(EADDRNOTAVAIL),
-        X(EAFNOSUPPORT),
-        X(EAGAIN),
-        X(EALREADY),
-        X(EBADF),
-        X(EBADMSG),
-        X(EBUSY),
-        X(ECANCELED),
-        X(ECHILD),
-        X(ECONNABORTED),
-        X(ECONNREFUSED),
-        X(ECONNRESET),
-        X(EDEADLK),
-        X(EDESTADDRREQ),
-        X(EDOM),
-        X(EDQUOT),
-        X(EEXIST),
-        X(EFAULT),
-        X(EFBIG),
-        X(EHOSTUNREACH),
-        X(EIDRM),
-        X(EILSEQ),
-        X(EINPROGRESS),
-        X(EINTR),
-        X(EINVAL),
-        X(EIO),
-        X(EISCONN),
-        X(EISDIR),
-        X(ELOOP),
-        X(EMFILE),
-        X(EMLINK),
-        X(EMSGSIZE),
-        X(EMULTIHOP),
-        X(ENAMETOOLONG),
-        X(ENETDOWN),
-        X(ENETRESET),
-        X(ENETUNREACH),
-        X(ENFILE),
-        X(ENOBUFS),
-        X(ENODEV),
-        X(ENOENT),
-        X(ENOEXEC),
-        X(ENOLCK),
-        X(ENOLINK),
-        X(ENOMEM),
-        X(ENOMSG),
-        X(ENOPROTOOPT),
-        X(ENOSPC),
-        X(ENOSYS),
+    __wasi_errno_t code = __WASI_ENOSYS;
+#define X(v)               \
+    case v:                \
+        code = __WASI_##v; \
+        break;
+    switch (error) {
+        X(E2BIG)
+        X(EACCES)
+        X(EADDRINUSE)
+        X(EADDRNOTAVAIL)
+        X(EAFNOSUPPORT)
+        X(EAGAIN)
+        X(EALREADY)
+        X(EBADF)
+        X(EBADMSG)
+        X(EBUSY)
+        X(ECANCELED)
+        X(ECHILD)
+        X(ECONNABORTED)
+        X(ECONNREFUSED)
+        X(ECONNRESET)
+        X(EDEADLK)
+        X(EDESTADDRREQ)
+        X(EDOM)
+        X(EDQUOT)
+        X(EEXIST)
+        X(EFAULT)
+        X(EFBIG)
+        X(EHOSTUNREACH)
+        X(EIDRM)
+        X(EILSEQ)
+        X(EINPROGRESS)
+        X(EINTR)
+        X(EINVAL)
+        X(EIO)
+        X(EISCONN)
+        X(EISDIR)
+        X(ELOOP)
+        X(EMFILE)
+        X(EMLINK)
+        X(EMSGSIZE)
+        X(EMULTIHOP)
+        X(ENAMETOOLONG)
+        X(ENETDOWN)
+        X(ENETRESET)
+        X(ENETUNREACH)
+        X(ENFILE)
+        X(ENOBUFS)
+        X(ENODEV)
+        X(ENOENT)
+        X(ENOEXEC)
+        X(ENOLCK)
+        X(ENOLINK)
+        X(ENOMEM)
+        X(ENOMSG)
+        X(ENOPROTOOPT)
+        X(ENOSPC)
+        X(ENOSYS)
 #ifdef ENOTCAPABLE
-        X(ENOTCAPABLE),
+        X(ENOTCAPABLE)
 #endif
-        X(ENOTCONN),
-        X(ENOTDIR),
-        X(ENOTEMPTY),
-        X(ENOTRECOVERABLE),
-        X(ENOTSOCK),
-        X(ENOTSUP),
-        X(ENOTTY),
-        X(ENXIO),
-        X(EOVERFLOW),
-        X(EOWNERDEAD),
-        X(EPERM),
-        X(EPIPE),
-        X(EPROTO),
-        X(EPROTONOSUPPORT),
-        X(EPROTOTYPE),
-        X(ERANGE),
-        X(EROFS),
-        X(ESPIPE),
-        X(ESRCH),
-        X(ESTALE),
-        X(ETIMEDOUT),
-        X(ETXTBSY),
-        X(EXDEV),
+        X(ENOTCONN)
+        X(ENOTDIR)
+        X(ENOTEMPTY)
+        X(ENOTRECOVERABLE)
+        X(ENOTSOCK)
+        X(ENOTSUP)
+        X(ENOTTY)
+        X(ENXIO)
+        X(EOVERFLOW)
+        X(EOWNERDEAD)
+        X(EPERM)
+        X(EPIPE)
+        X(EPROTO)
+        X(EPROTONOSUPPORT)
+        X(EPROTOTYPE)
+        X(ERANGE)
+        X(EROFS)
+        X(ESPIPE)
+        X(ESRCH)
+        X(ESTALE)
+        X(ETIMEDOUT)
+        X(ETXTBSY)
+        X(EXDEV)
+        default:
+            if (error == EOPNOTSUPP)
+                code = __WASI_ENOTSUP;
+            else if (code == EWOULDBLOCK)
+                code = __WASI_EAGAIN;
+            break;
+    }
 #undef X
-#if EOPNOTSUPP != ENOTSUP
-        [EOPNOTSUPP] = __WASI_ENOTSUP,
-#endif
-#if EWOULDBLOCK != EAGAIN
-        [EWOULDBLOCK] = __WASI_EAGAIN,
-#endif
-    };
-    if (error < 0 || (size_t)error >= sizeof(errors) / sizeof(errors[0])
-        || errors[error] == 0)
-        return __WASI_ENOSYS;
-    return errors[error];
+    return code;
 }
 
 static bool

+ 3 - 2
core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h

@@ -65,7 +65,7 @@
 #endif
 #endif
 
-#if !defined(__APPLE__) && !defined(ESP_PLATFORM)
+#if !defined(__APPLE__) && !defined(ESP_PLATFORM) && !defined(__COSMOPOLITAN__)
 #define CONFIG_HAS_POSIX_FALLOCATE 1
 #else
 #define CONFIG_HAS_POSIX_FALLOCATE 0
@@ -83,7 +83,8 @@
 #define CONFIG_HAS_PTHREAD_COND_TIMEDWAIT_RELATIVE_NP 0
 #endif
 
-#if !defined(__APPLE__) && !defined(BH_PLATFORM_LINUX_SGX)
+#if !defined(__APPLE__) && !defined(BH_PLATFORM_LINUX_SGX) \
+    && !defined(__COSMOPOLITAN__)
 #define CONFIG_HAS_PTHREAD_CONDATTR_SETCLOCK 1
 #else
 #define CONFIG_HAS_PTHREAD_CONDATTR_SETCLOCK 0

+ 2 - 2
core/shared/platform/common/posix/posix_socket.c

@@ -799,7 +799,7 @@ os_socket_set_ip_add_membership(bh_socket_t socket,
 {
     assert(imr_multiaddr);
     if (is_ipv6) {
-#ifdef IPPROTO_IPV6
+#if defined(IPPROTO_IPV6) && !defined(BH_PLATFORM_COSMOPOLITAN)
         struct ipv6_mreq mreq;
         for (int i = 0; i < 8; i++) {
             ((uint16_t *)mreq.ipv6mr_multiaddr.s6_addr)[i] =
@@ -837,7 +837,7 @@ os_socket_set_ip_drop_membership(bh_socket_t socket,
 {
     assert(imr_multiaddr);
     if (is_ipv6) {
-#ifdef IPPROTO_IPV6
+#if defined(IPPROTO_IPV6) && !defined(BH_PLATFORM_COSMOPOLITAN)
         struct ipv6_mreq mreq;
         for (int i = 0; i < 8; i++) {
             ((uint16_t *)mreq.ipv6mr_multiaddr.s6_addr)[i] =

+ 43 - 0
core/shared/platform/cosmopolitan/platform_init.c

@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2019 Intel Corporation.  All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "platform_api_vmcore.h"
+
+int
+bh_platform_init()
+{
+    return 0;
+}
+
+void
+bh_platform_destroy()
+{}
+
+int
+os_printf(const char *format, ...)
+{
+    int ret = 0;
+    va_list ap;
+
+    va_start(ap, format);
+#ifndef BH_VPRINTF
+    ret += vprintf(format, ap);
+#else
+    ret += BH_VPRINTF(format, ap);
+#endif
+    va_end(ap);
+
+    return ret;
+}
+
+int
+os_vprintf(const char *format, va_list ap)
+{
+#ifndef BH_VPRINTF
+    return vprintf(format, ap);
+#else
+    return BH_VPRINTF(format, ap);
+#endif
+}

+ 122 - 0
core/shared/platform/cosmopolitan/platform_internal.h

@@ -0,0 +1,122 @@
+/*
+ * Copyright (C) 2019 Intel Corporation.  All rights reserved.
+ * Copyright (C) 2023 Dylibso.  All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#ifndef _PLATFORM_INTERNAL_H
+#define _PLATFORM_INTERNAL_H
+
+#include <inttypes.h>
+#include <stdbool.h>
+#include <assert.h>
+#include <time.h>
+#include <string.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <math.h>
+#include <stdarg.h>
+#include <ctype.h>
+#include <pthread.h>
+#include <signal.h>
+#include <semaphore.h>
+#include <limits.h>
+#include <dirent.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <poll.h>
+#include <sched.h>
+#include <errno.h>
+#include <netinet/in.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/mman.h>
+#include <sys/time.h>
+#include <sys/uio.h>
+#include <sys/ioctl.h>
+#include <sys/socket.h>
+#include <sys/resource.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#ifndef BH_PLATFORM_COSMOPOLITAN
+#define BH_PLATFORM_COSMOPOLITAN
+#endif
+
+/* Stack size of applet threads's native part.  */
+#define BH_APPLET_PRESERVED_STACK_SIZE (32 * 1024)
+
+/* Default thread priority */
+#define BH_THREAD_DEFAULT_PRIORITY 0
+
+typedef pthread_t korp_tid;
+typedef pthread_mutex_t korp_mutex;
+typedef pthread_cond_t korp_cond;
+typedef pthread_t korp_thread;
+typedef sem_t korp_sem;
+
+#define OS_THREAD_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER
+
+#define os_thread_local_attribute __thread
+
+#define bh_socket_t int
+
+#if WASM_DISABLE_WRITE_GS_BASE == 0
+#if defined(BUILD_TARGET_X86_64) || defined(BUILD_TARGET_AMD_64)
+#define os_writegsbase(base_addr)                                 \
+    do {                                                          \
+        uint64 __gs_value = (uint64)(uintptr_t)base_addr;         \
+        asm volatile("wrgsbase %0" ::"r"(__gs_value) : "memory"); \
+    } while (0)
+#if 0
+/* _writegsbase_u64 also works, but need to add -mfsgsbase flag for gcc */
+#include <immintrin.h>
+#define os_writegsbase(base_addr) \
+    _writegsbase_u64(((uint64)(uintptr_t)base_addr))
+#endif
+#endif
+#endif
+
+#if WASM_DISABLE_HW_BOUND_CHECK == 0
+#if defined(BUILD_TARGET_X86_64) || defined(BUILD_TARGET_AMD_64)            \
+    || defined(BUILD_TARGET_AARCH64) || defined(BUILD_TARGET_RISCV64_LP64D) \
+    || defined(BUILD_TARGET_RISCV64_LP64)
+
+#include <setjmp.h>
+
+#define OS_ENABLE_HW_BOUND_CHECK
+
+typedef jmp_buf korp_jmpbuf;
+
+#define os_setjmp setjmp
+#define os_longjmp longjmp
+#define os_alloca alloca
+
+#define os_getpagesize getpagesize
+
+typedef void (*os_signal_handler)(void *sig_addr);
+
+int
+os_thread_signal_init(os_signal_handler handler);
+
+void
+os_thread_signal_destroy();
+
+bool
+os_thread_signal_inited();
+
+void
+os_signal_unmask();
+
+void
+os_sigreturn();
+#endif /* end of BUILD_TARGET_X86_64/AMD_64/AARCH64/RISCV64 */
+#endif /* end of WASM_DISABLE_HW_BOUND_CHECK */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* end of _PLATFORM_INTERNAL_H */

+ 19 - 0
core/shared/platform/cosmopolitan/shared_platform.cmake

@@ -0,0 +1,19 @@
+# Copyright (C) 2019 Intel Corporation.  All rights reserved.
+# Copyright (C) 2023 Dylibso.  All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+set (PLATFORM_SHARED_DIR ${CMAKE_CURRENT_LIST_DIR})
+
+add_definitions(-DBH_PLATFORM_COSMOPOLITAN)
+
+include_directories(${PLATFORM_SHARED_DIR})
+include_directories(${PLATFORM_SHARED_DIR}/../include)
+
+include (${CMAKE_CURRENT_LIST_DIR}/../common/posix/platform_api_posix.cmake)
+
+file (GLOB_RECURSE source_all ${PLATFORM_SHARED_DIR}/*.c)
+
+set (PLATFORM_SHARED_SOURCE ${source_all} ${PLATFORM_COMMON_POSIX_SOURCE})
+
+file (GLOB header ${PLATFORM_SHARED_DIR}/../include/*.h)
+LIST (APPEND RUNTIME_LIB_HEADER_LIST ${header})

+ 20 - 0
product-mini/README.md

@@ -443,3 +443,23 @@ make
    aos make
    ```
    download the binary to developerkit board, check the output from serial port
+
+## Cosmopolitan Libc
+Currently, only x86_64 architecture with interpreter modes is supported.
+
+Clone the Cosmopolitan Libc. Setup `cosmocc` as described in [Getting Started](https://github.com/jart/cosmopolitan/#getting-started) being sure to get it into `PATH`.
+
+Build iwasm
+``` Bash
+export CC=cosmocc
+export CXX=cosmoc++
+rm -rf build
+mkdir build
+cmake -DWAMR_BUILD_INTERP=1 -DWAMR_BUILD_FAST_INTERP=1 -B build
+cmake --build build -j
+```
+
+Run like
+``` Bash
+./build/iwasm.com <wasm file>
+```

+ 175 - 0
product-mini/platforms/cosmopolitan/CMakeLists.txt

@@ -0,0 +1,175 @@
+# Copyright (C) 2019 Intel Corporation.  All rights reserved.
+# Copyright (C) 2023 Dylibso.  All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+
+cmake_minimum_required (VERSION 3.14)
+
+include(CheckPIESupported)
+
+project (iwasm)
+
+set (CMAKE_VERBOSE_MAKEFILE OFF)
+
+set (WAMR_BUILD_PLATFORM "cosmopolitan")
+
+set(CMAKE_EXECUTABLE_SUFFIX ".com")
+
+# Reset default linker flags
+set (CMAKE_SHARED_LIBRARY_LINK_C_FLAGS "")
+set (CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS "")
+
+set (CMAKE_C_STANDARD 99)
+set (CMAKE_CXX_STANDARD 17)
+
+# Set WAMR_BUILD_TARGET, currently values supported:
+# "X86_64", "AMD_64", "X86_32", "AARCH64[sub]", "ARM[sub]", "THUMB[sub]",
+# "MIPS", "XTENSA", "RISCV64[sub]", "RISCV32[sub]"
+if (NOT DEFINED WAMR_BUILD_TARGET)
+  if (CMAKE_SYSTEM_PROCESSOR MATCHES "^(arm64|aarch64)")
+    set (WAMR_BUILD_TARGET "AARCH64")
+  elseif (CMAKE_SYSTEM_PROCESSOR STREQUAL "riscv64")
+    set (WAMR_BUILD_TARGET "RISCV64")
+  elseif (CMAKE_SIZEOF_VOID_P EQUAL 8)
+    # Build as X86_64 by default in 64-bit platform
+    set (WAMR_BUILD_TARGET "X86_64")
+  elseif (CMAKE_SIZEOF_VOID_P EQUAL 4)
+    # Build as X86_32 by default in 32-bit platform
+    set (WAMR_BUILD_TARGET "X86_32")
+  else ()
+    message(SEND_ERROR "Unsupported build target platform!")
+  endif ()
+endif ()
+
+if (NOT CMAKE_BUILD_TYPE)
+  set(CMAKE_BUILD_TYPE Release)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_INTERP)
+  # Enable Interpreter by default
+  set (WAMR_BUILD_INTERP 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_AOT)
+  # Enable AOT by default.
+  set (WAMR_BUILD_AOT 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_JIT)
+  # Disable JIT by default.
+  set (WAMR_BUILD_JIT 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_FAST_JIT)
+  # Disable Fast JIT by default
+  set (WAMR_BUILD_FAST_JIT 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_LIBC_BUILTIN)
+  # Enable libc builtin support by default
+  set (WAMR_BUILD_LIBC_BUILTIN 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_LIBC_WASI)
+  # Enable libc wasi support by default
+  set (WAMR_BUILD_LIBC_WASI 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_FAST_INTERP)
+  # Enable fast interpreter
+  set (WAMR_BUILD_FAST_INTERP 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_MULTI_MODULE)
+  # Disable multiple modules by default
+  set (WAMR_BUILD_MULTI_MODULE 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_LIB_PTHREAD)
+  # Disable pthread library by default
+  set (WAMR_BUILD_LIB_PTHREAD 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_LIB_WASI_THREADS)
+  # Disable wasi threads library by default
+  set (WAMR_BUILD_LIB_WASI_THREADS 0)
+endif()
+
+
+if (NOT DEFINED WAMR_BUILD_MINI_LOADER)
+  # Disable wasm mini loader by default
+  set (WAMR_BUILD_MINI_LOADER 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_SIMD)
+  # Enable SIMD by default
+  set (WAMR_BUILD_SIMD 1)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_REF_TYPES)
+  # Disable reference types by default
+  set (WAMR_BUILD_REF_TYPES 0)
+endif ()
+
+if (NOT DEFINED WAMR_BUILD_DEBUG_INTERP)
+  # Disable Debug feature by default
+  set (WAMR_BUILD_DEBUG_INTERP 0)
+endif ()
+
+if (WAMR_BUILD_DEBUG_INTERP EQUAL 1)
+  set (WAMR_BUILD_FAST_INTERP 0)
+  set (WAMR_BUILD_MINI_LOADER 0)
+  set (WAMR_BUILD_SIMD 0)
+endif ()
+
+set (WAMR_DISABLE_STACK_HW_BOUND_CHECK 1)
+set (WAMR_BUILD_AOT 0)
+set (WAMR_DISABLE_WRITE_GS_BASE 1)
+
+set (WAMR_ROOT_DIR ${CMAKE_CURRENT_SOURCE_DIR}/../../..)
+
+include (${WAMR_ROOT_DIR}/build-scripts/runtime_lib.cmake)
+
+check_pie_supported()
+add_library(vmlib ${WAMR_RUNTIME_LIB_SOURCE})
+set_target_properties (vmlib PROPERTIES POSITION_INDEPENDENT_CODE ON)
+
+set (CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--gc-sections")
+
+set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wextra -Wformat -Wformat-security -Wshadow")
+# set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wconversion -Wsign-conversion")
+
+set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra -Wformat -Wformat-security -Wno-unused")
+
+if (WAMR_BUILD_TARGET MATCHES "X86_.*" OR WAMR_BUILD_TARGET STREQUAL "AMD_64")
+  if (NOT (CMAKE_C_COMPILER MATCHES ".*clang.*" OR CMAKE_C_COMPILER_ID MATCHES ".*Clang"))
+    set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -mindirect-branch-register")
+    set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -mindirect-branch-register")
+    # UNDEFINED BEHAVIOR, refer to https://en.cppreference.com/w/cpp/language/ub
+  endif ()
+endif ()
+
+# The following flags are to enhance security, but it may impact performance,
+# we disable them by default.
+#if (WAMR_BUILD_TARGET MATCHES "X86_.*" OR WAMR_BUILD_TARGET STREQUAL "AMD_64")
+#  set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -ftrapv -D_FORTIFY_SOURCE=2")
+#endif ()
+#set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fstack-protector-strong --param ssp-buffer-size=4")
+#set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wl,-z,noexecstack,-z,relro,-z,now")
+
+include (${SHARED_DIR}/utils/uncommon/shared_uncommon.cmake)
+
+add_executable (iwasm main.c ${UNCOMMON_SHARED_SOURCE})
+
+set_target_properties (iwasm PROPERTIES POSITION_INDEPENDENT_CODE ON)
+
+install (TARGETS iwasm DESTINATION bin)
+
+target_link_libraries (iwasm vmlib ${LLVM_AVAILABLE_LIBS} ${UV_A_LIBS} ${WASI_NN_LIBS} -lm -ldl -lpthread)
+
+add_library (libiwasm STATIC ${WAMR_RUNTIME_LIB_SOURCE})
+
+install (TARGETS libiwasm DESTINATION lib)
+
+set_target_properties (libiwasm PROPERTIES OUTPUT_NAME iwasm)
+
+target_link_libraries (libiwasm ${LLVM_AVAILABLE_LIBS} ${UV_A_LIBS} ${WASI_NN_LIBS} -lm -ldl -lpthread)

+ 10 - 0
product-mini/platforms/cosmopolitan/build_cosmocc.sh

@@ -0,0 +1,10 @@
+#!/bin/sh
+
+# Copyright (C) 2023 Dylibso.  All rights reserved.
+# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+export CC=cosmocc
+export CXX=cosmoc++
+rm -rf build
+mkdir build
+cmake -DWAMR_BUILD_INTERP=1 -DWAMR_BUILD_FAST_INTERP=1 -B build
+cmake --build build -j

+ 6 - 0
product-mini/platforms/cosmopolitan/main.c

@@ -0,0 +1,6 @@
+/*
+ * Copyright (C) 2019 Intel Corporation.  All rights reserved.
+ * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+ */
+
+#include "../posix/main.c"

+ 22 - 1
tests/wamr-test-suites/test_wamr.sh

@@ -31,6 +31,7 @@ function help()
     echo "-Q enable qemu"
     echo "-F set the firmware path used by qemu"
     echo "-C enable code coverage collect"
+    echo "-j set the platform to test"
 }
 
 OPT_PARSED=""
@@ -58,7 +59,7 @@ QEMU_FIRMWARE=""
 # prod/testsuite-all branch
 WASI_TESTSUITE_COMMIT="cf64229727f71043d5849e73934e249e12cb9e06"
 
-while getopts ":s:cabgvt:m:MCpSXxwPGQF:" opt
+while getopts ":s:cabgvt:m:MCpSXxwPGQF:j:" opt
 do
     OPT_PARSED="TRUE"
     case $opt in
@@ -160,6 +161,10 @@ do
         echo "QEMU firmware" ${OPTARG}
         QEMU_FIRMWARE=${OPTARG}
         ;;
+        j)
+        echo "test platform " ${OPTARG}
+        PLATFORM=${OPTARG}
+        ;;
         ?)
         help
         exit 1;;
@@ -383,6 +388,8 @@ function spec_test()
         local WAT2WASM=${WORK_DIR}/wabt/out/gcc/Release/wat2wasm
         if [ ! -f ${WAT2WASM} ]; then
             case ${PLATFORM} in
+                cosmopolitan)
+                    ;&
                 linux)
                     WABT_PLATFORM=ubuntu
                     ;;
@@ -656,6 +663,20 @@ function build_iwasm_with_cfg()
         echo -e "build iwasm failed"
         exit 1
     fi
+
+    if [[ ${PLATFORM} == "cosmopolitan" ]]; then
+        # convert from APE to ELF so it can be ran easier
+        # HACK: link to linux so tests work when platform is detected by uname
+        cp iwasm.com iwasm \
+        && ./iwasm --assimilate \
+        && rm -rf ../../linux/build \
+        && mkdir ../../linux/build \
+        && ln -s ../../cosmopolitan/build/iwasm ../../linux/build/iwasm
+        if [ "$?" != 0 ];then
+            echo -e "build iwasm failed (cosmopolitan)"
+            exit 1
+        fi
+    fi
 }
 
 function build_wamrc()