void WasmEdge::registerHostFunctionImpl()

in plugins/experimental/wasm/lib/src/wasmedge/wasmedge.cc [455:499]


void WasmEdge::registerHostFunctionImpl(std::string_view module_name,
                                        std::string_view function_name, R (*function)(Args...)) {
  auto it = host_modules_.find(std::string(module_name));
  if (it == host_modules_.end()) {
    host_modules_.emplace(module_name, std::make_unique<HostModuleData>(module_name));
    it = host_modules_.find(std::string(module_name));
  }

  auto data = std::make_unique<HostFuncData>(module_name, function_name);
  auto *func_type = newWasmEdgeFuncType<R, std::tuple<Args...>>();
  data->vm_ = this;
  data->raw_func_ = reinterpret_cast<void *>(function);
  data->callback_ = [](void *data, const WasmEdge_CallingFrameContext * /*CallFrameCxt*/,
                       const WasmEdge_Value *Params, WasmEdge_Value *Returns) -> WasmEdge_Result {
    auto *func_data = reinterpret_cast<HostFuncData *>(data);
    const bool log = func_data->vm_->cmpLogLevel(LogLevel::trace);
    if (log) {
      func_data->vm_->integration()->trace("[vm->host] " + func_data->modname_ + "." +
                                           func_data->name_ + "(" +
                                           printValues(Params, sizeof...(Args)) + ")");
    }
    auto args = convValTypesToArgsTuple<std::tuple<Args...>>(Params);
    auto fn = reinterpret_cast<R (*)(Args...)>(func_data->raw_func_);
    R res = std::apply(fn, args);
    Returns[0] = makeVal<R>(res);
    if (log) {
      func_data->vm_->integration()->trace("[vm<-host] " + func_data->modname_ + "." +
                                           func_data->name_ + " return: " + std::to_string(res));
    }
    return WasmEdge_Result_Success;
  };

  auto *hostfunc_cxt = WasmEdge_FunctionInstanceCreate(func_type, data->callback_, data.get(), 0);
  WasmEdge_FunctionTypeDelete(func_type);
  if (hostfunc_cxt == nullptr) {
    fail(FailState::MissingFunction, "Failed to allocate host function instance");
    return;
  }

  WasmEdge_ModuleInstanceAddFunction(
      it->second->cxt_, WasmEdge_StringWrap(function_name.data(), function_name.length()),
      hostfunc_cxt);
  host_functions_.insert_or_assign(std::string(module_name) + "." + std::string(function_name),
                                   std::move(data));
}