2014-01-16 4 views
4

samples_extension은 C 라이브러리 링키지에서 정상적으로 작동하지만 C++ 라이브러리는 어떻게됩니까?네이티브 확장 - C++ 네이티브 라이브러리

은 내가 네이티브 확장으로 사용할 ++ 라이브러리 클래스를 기반으로 C, 그래서 우리는 예를 들어 가지고있다 -

class Connect { 
     open(...); 
    .... 
} 
C에서

++ 내가 다트에 비슷한 클래스를 원한다.

dart_api.h와 dart_native_api.h를 보면 나에게 클래스 포인터를 C++에서 Dart로 전달하는 방법과 그 메소드를 호출하여 Dart 클래스 인스턴스에 다시 연결하는 방법을 알지 못합니다. ResolveName은 connection-> open() 유형 호출과 어떻게 작동합니까? 아니면 완전히 다르게 처리합니까? 질문에 대한 답변을 얻을 수 있습니다

답변

2

OK, 파고의 비트와 나는 지금이 sussed 한, 내가 다트에이 일을 해요 : -

bool open() native 'Connection::open'; 

내 해결에

문자열을 찾고 '연결 : 열린'다음 호출 네이티브 함수. 그래서 내 네이티브 함수는 'connectionOpen'및 'messageOpen'등으로 이름이 지정되므로이를 해결할 수 있습니다.

5

Basic 프로젝트 :

cpp_extension.cc

#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

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

0 이 패키지의 https://github.com/mezoni/dart_and_cpp_classes

기타 필요한 파일 : 여기

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의에 대한 기본 (사용 준비) 패키지입니다.

실행 :

  • 빈/build_cpp_extension.dart
  • 빈/use_cpp_extension.dart

P.S.

저는 C++ 프로그래머가 아닙니다.

이 언어의 부정확성에 대해 저에게 용서하십시오.

+0

예, getVersionString()에 대한 정적 호출이 아니므로 'myclass-> getVersionString()'확장 라이브러리에서이 작업을 수행하려고합니다. 따라서 들어오는 Dart 객체를 네이티브 라이브러리의 인스턴스화 된 클래스에 연결해야합니다. 측면. weakpersistentandles 및 Dart_Invoke API 호출을 사용해야한다고 생각하는데 Dart 'bool open (String url) 네이티브'Connect :: open '에서이 문제를 해결하는 방법에 대해 확신 할 수 없습니다. ResolveName을 사용하여 명명 된 함수에 연결합니다. – user2685314

관련 문제