首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >本机扩展- C++本机库

本机扩展- C++本机库
EN

Stack Overflow用户
提问于 2014-01-16 07:54:20
回答 2查看 1.7K关注 0票数 5

samples_extension可以用C库链接工作,但是C++库呢?

我有一个基于类的C++库,我希望使用它作为本机扩展,因此我们有以下例子:-

代码语言:javascript
复制
class Connect {
      open(...);
  ....
}

在C++和我想要一个类似的课在达特。

查看dart_api.h和dart_native_api.h,我不清楚如何将类指针从C++来回传递到Dart,以及如何调用它们上的方法并将其绑定到Dart类实例。ResolveName是如何使用connection->open()类型调用的,还是完全不同。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2014-01-16 11:52:46

好的,我已经查过了,我在达特做这个:-

代码语言:javascript
复制
bool open() native 'Connection::open';

并在我的解析器中查找字符串“Connection::open”,然后调用一个本机函数。因此,这意味着我的本机函数被命名为'connectionOpen‘和'messageOpen’等等,所以我可以解决这些问题。

票数 3
EN

Stack Overflow用户

发布于 2014-01-16 08:41:04

基本的项目,可以得到你的问题的答案:

cpp_extension.cc

代码语言:javascript
复制
#include <string.h>
#include <stdlib.h>
#include <stdio.h>

#ifdef _WIN32
#include "windows.h"
#else
#include <stdbool.h>
#include <dlfcn.h>
#include <unistd.h>
#include <sys/mman.h>
#endif

#include "dart_api.h"

Dart_NativeFunction ResolveName(Dart_Handle name, int argc, bool* auto_setup_scope);

DART_EXPORT Dart_Handle cpp_extension_Init(Dart_Handle parent_library) {
  if (Dart_IsError(parent_library)) { return parent_library; }

  Dart_Handle result_code = Dart_SetNativeResolver(parent_library, ResolveName);
  if (Dart_IsError(result_code)) return result_code;

  return Dart_Null();
}

Dart_Handle HandleError(Dart_Handle handle) {
  if (Dart_IsError(handle)) Dart_PropagateError(handle);
  return handle;
}

class Connection {
  int* buffer;
  bool opened;

  public:
    Connection() {
      opened = false;
      buffer = new int[1000000];
      memset(buffer, 1, 1000000);
    }

    void close() {
      opened = false;
    } 

    void open(const char* connectionString) {
      opened = true;
    }

    ~Connection() {
      delete buffer;
    }
};

void ConnectionClose(Dart_NativeArguments arguments) {
  Connection* connection;
  Dart_Handle dh_handle;

  Dart_EnterScope();
  dh_handle = Dart_GetNativeArgument(arguments, 0);
  connection = (Connection*)dh_handle;
  connection->close();
  Dart_Handle result = Dart_Null();
  Dart_SetReturnValue(arguments, result);
  Dart_ExitScope();
}

void ConnectionCreate(Dart_NativeArguments arguments) {  
  Connection* connection;
  Dart_Handle result;

  Dart_EnterScope();
  connection = new Connection();
  result = Dart_NewInteger((int64_t)connection);
  Dart_SetReturnValue(arguments, result);
  Dart_ExitScope();
}

void ConnectionPeerFinalizer(Dart_WeakPersistentHandle handle, void *peer) {
  delete (Connection*) peer;
}

void ConnectionPeerRegister(Dart_NativeArguments arguments) {
  int64_t peer;
  Dart_Handle dh_object;
  Dart_Handle dh_peer;

  Dart_EnterScope();
  dh_object = Dart_GetNativeArgument(arguments, 0);
  dh_peer = Dart_GetNativeArgument(arguments, 1);
  Dart_IntegerToInt64(dh_peer, &peer);
  Dart_NewWeakPersistentHandle(dh_object, (void*)peer, ConnectionPeerFinalizer);
  Dart_SetReturnValue(arguments, Dart_Null());
  Dart_ExitScope();
}

void ConnectionOpen(Dart_NativeArguments arguments) { 
  Connection* connection;
  const char* connectionString;
  Dart_Handle dh_connectionString;
  Dart_Handle dh_handle;

  Dart_EnterScope();
  dh_handle = Dart_GetNativeArgument(arguments, 0);
  dh_connectionString = Dart_GetNativeArgument(arguments, 1);
  Dart_StringToCString(dh_connectionString, &connectionString);
  connection = (Connection*)dh_handle;
  connection->open(connectionString);  
  Dart_Handle result = Dart_Null();
  Dart_SetReturnValue(arguments, result);
  Dart_ExitScope();
}

struct FunctionLookup {
  const char* name;
  Dart_NativeFunction function;
};

FunctionLookup function_list[] = {
  {"ConnectionClose", ConnectionClose},
  {"ConnectionCreate", ConnectionCreate},
  {"ConnectionOpen", ConnectionOpen},
  {"ConnectionPeerRegister", ConnectionPeerRegister},
  {NULL, NULL}};

Dart_NativeFunction ResolveName(Dart_Handle name, int argc, bool* auto_setup_scope) {
  if (!Dart_IsString(name)) return NULL;
  Dart_NativeFunction result = NULL;
  Dart_EnterScope();
  const char* cname;
  HandleError(Dart_StringToCString(name, &cname));

  for (int i=0; function_list[i].name != NULL; ++i) {
    if (strcmp(function_list[i].name, cname) == 0) {
      result = function_list[i].function;
      break;
    }
  }
  Dart_ExitScope();
  return result;
}

cpp_extension.dart

代码语言:javascript
复制
library dart_and_cpp_classes.ext_cpp_extension;

import "dart-ext:cpp_extension";

class Connection {
  final String connectionString;

  int _handle;

  bool _opened = false;

  Connection(this.connectionString) {
    _handle = _create();
    _peerRegister(this, _handle);
  }

  bool get opened => _opened;

  void close() {
    _close(_handle);
    _opened = false;
  }

  void open() {
    _open(_handle, connectionString);
    _opened = true;
  }

  int _create() native "ConnectionCreate";

  void _close(int handle) native "ConnectionClose";

  void _open(int handle, String connectionString) native "ConnectionOpen";

  void _peerRegister(Object object, int handle) native "ConnectionPeerRegister";
}

use_cpp_extension.dart

代码语言:javascript
复制
import 'package:dart_and_cpp_classes/cpp_extension.dart';

void main() {
  var count = 500;
  var connections = [];
  for(var i = 0; i < count; i++) {
    var connection = new Connection("MYSQL");
    connection.open();
    connection.close();
    connections.add(connection);
  }

  connections = null;
  print("Done");
}

下面是github:classes上的基本(准备使用)包

此包中所需的其他文件。

运行:

  • bin/build_cpp_EXsion.DAT
  • bin/use_cpp_EXsion.DAT

附注:

我不是C++程序员。

请原谅我在这门语言中有任何不准确之处。

票数 6
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/21156185

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档