Skip to content

Commit af97d6e

Browse files
committed
Merge branch 'release/0.3.18'
2 parents 3edffbf + b2c65d4 commit af97d6e

File tree

24 files changed

+285
-188
lines changed

24 files changed

+285
-188
lines changed

.gitignore

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,4 +8,6 @@ build/
88

99
.idea/
1010

11-
.cxx/
11+
.cxx/
12+
13+
.fvm/

dart_native/CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
## 0.3.18
2+
3+
* [Feature] Support multi-isolates.
4+
15
## 0.3.17
26

37
* [Fix] Type encoding issue on iOS.

dart_native/android/src/main/jni/dart_native.cpp

Lines changed: 23 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ static std::map<jobject, int> referenceCount;
3434
static std::map<void *, jobject> callbackObjCache;
3535
static std::map<jlong, std::map<std::string, NativeMethodCallback>> callbackManagerCache;
3636
static std::map<jlong, void *> targetCache;
37+
static std::map<jlong, int64_t> dartPortCache;
3738

3839

3940
void detachThreadDestructor(void* arg) {
@@ -301,7 +302,7 @@ NativeMethodCallback getCallbackMethod(jlong targetAddr, char *functionName) {
301302
return methodsMap[functionName];
302303
}
303304

304-
void registerNativeCallback(void *target, char* targetName, char *funName, void *callback) {
305+
void registerNativeCallback(void *target, char* targetName, char *funName, void *callback, Dart_Port dartPort) {
305306
jclass callbackManager = findClass(getEnv(), "com/dartnative/dart_native/CallbackManager");
306307
jmethodID registerCallback = getEnv()->GetStaticMethodID(callbackManager, "registerCallback", "(JLjava/lang/String;)Ljava/lang/Object;");
307308
jlong targetAddr = (jlong)target;
@@ -311,17 +312,16 @@ void registerNativeCallback(void *target, char* targetName, char *funName, void
311312
jobject callbackOJ = getEnv()->NewGlobalRef(getEnv()->CallStaticObjectMethodA(callbackManager, registerCallback, argValues));
312313
callbackObjCache[target] = callbackOJ;
313314
targetCache[targetAddr] = target;
315+
NSLog("HUIZZ dartport %d", dartPort);
316+
dartPortCache[targetAddr] = dartPort;
314317

315318
registerCallbackManager(targetAddr, funName, callback);
316319
getEnv()->DeleteLocalRef(callbackManager);
317320
free(argValues);
318321
}
319322

320323
// Dart extensions
321-
Dart_Port native_callback_send_port;
322-
323-
intptr_t InitDartApiDL(void *data, Dart_Port port) {
324-
native_callback_send_port = port;
324+
intptr_t InitDartApiDL(void *data) {
325325
return Dart_InitializeApiDL(data);
326326
}
327327

@@ -344,7 +344,7 @@ void PassObjectToCUseDynamicLinking(Dart_Handle h, void *classPtr) {
344344

345345
typedef std::function<void()> Work;
346346

347-
void NotifyDart(Dart_Port send_port, const Work* work) {
347+
bool NotifyDart(Dart_Port send_port, const Work* work) {
348348
const intptr_t work_addr = reinterpret_cast<intptr_t>(work);
349349

350350
Dart_CObject dart_object;
@@ -355,6 +355,7 @@ void NotifyDart(Dart_Port send_port, const Work* work) {
355355
if (!result) {
356356
NSLog("Native callback to Dart failed! Invalid port or isolate died");
357357
}
358+
return result;
358359
}
359360

360361
void ExecuteCallback(Work* work_ptr) {
@@ -371,8 +372,10 @@ JNIEXPORT jobject JNICALL Java_com_dartnative_dart_1native_CallbackInvocationHan
371372
jobjectArray arg_types,
372373
jobjectArray args,
373374
jstring return_type) {
374-
sem_t sem;
375-
bool isSemInitSuccess = sem_init(&sem, 0, 0) == 0;
375+
if (!dartPortCache.count(dartObject)) {
376+
NSLog("not register dart port!");
377+
return NULL;
378+
}
376379

377380
char *funName = (char *) env->GetStringUTFChars(fun_name, 0);
378381
jsize argTypeLength = env->GetArrayLength(arg_types);
@@ -422,6 +425,10 @@ JNIEXPORT jobject JNICALL Java_com_dartnative_dart_1native_CallbackInvocationHan
422425
}
423426
char *returnType = (char *) env->GetStringUTFChars(return_type, 0);
424427
argTypes[argTypeLength] = returnType;
428+
429+
sem_t sem;
430+
bool isSemInitSuccess = sem_init(&sem, 0, 0) == 0;
431+
425432
const Work work = [dartObject, argTypes, arguments, arg_count, funName, &sem, isSemInitSuccess]() {
426433
NativeMethodCallback methodCallback = getCallbackMethod(dartObject, funName);
427434
void *target = targetCache[dartObject];
@@ -435,10 +442,9 @@ JNIEXPORT jobject JNICALL Java_com_dartnative_dart_1native_CallbackInvocationHan
435442
};
436443

437444
const Work* work_ptr = new Work(work);
438-
NotifyDart(native_callback_send_port, work_ptr);
445+
bool notifyResult = NotifyDart(dartPortCache[dartObject], work_ptr);
439446

440447
jobject callbackResult = NULL;
441-
442448
if (isSemInitSuccess) {
443449
NSLog("wait work execute");
444450
sem_wait(&sem);
@@ -448,10 +454,13 @@ JNIEXPORT jobject JNICALL Java_com_dartnative_dart_1native_CallbackInvocationHan
448454
} else if (strcmp(returnType, "Ljava/lang/String;") == 0) {
449455
callbackResult = env->NewStringUTF((char *) arguments[0]);
450456
} else if (strcmp(returnType, "Z") == 0) {
451-
jclass booleanClass = env->FindClass("java/lang/Boolean");
452-
jmethodID methodID = env->GetMethodID(booleanClass, "<init>", "(Z)V");
453-
callbackResult = env->NewObject(booleanClass, methodID, static_cast<jboolean>(*((int *) arguments)));
454-
env->DeleteLocalRef(booleanClass);
457+
jclass booleanClass = env->FindClass("java/lang/Boolean");
458+
jmethodID methodID = env->GetMethodID(booleanClass, "<init>", "(Z)V");
459+
callbackResult = env->NewObject(booleanClass,
460+
methodID,
461+
notifyResult ? static_cast<jboolean>(*((int *) arguments))
462+
: JNI_FALSE);
463+
env->DeleteLocalRef(booleanClass);
455464
}
456465
sem_destroy(&sem);
457466
}

dart_native/example/lib/android/unit_test.dart

Lines changed: 100 additions & 100 deletions
Original file line numberDiff line numberDiff line change
@@ -4,109 +4,109 @@ import 'package:dart_native_example/android/entity.dart';
44
import 'package:dart_native/dart_native.dart';
55

66
testAndroid(RuntimeStub stub) {
7-
int ms = currentTimeMillis();
8-
double resultDouble = stub.getDouble(10.0);
9-
int use = currentTimeMillis() - ms;
10-
print('getDouble result:$resultDouble , cost:$use');
11-
12-
ms = currentTimeMillis();
13-
String resultChar = stub.getChar('a');
14-
use = currentTimeMillis() - ms;
15-
print('getChar result:$resultChar , cost:$use');
16-
17-
ms = currentTimeMillis();
18-
int resultInt = stub.getInt(10);
19-
use = currentTimeMillis() - ms;
20-
print('getInt result:$resultInt , cost:$use');
21-
22-
ms = currentTimeMillis();
23-
bool resultBool = stub.getBool(true);
24-
use = currentTimeMillis() - ms;
25-
print('getBool result:$resultBool , cost:$use');
26-
27-
ms = currentTimeMillis();
28-
double resultFloat = stub.getFloat(10.5);
29-
use = currentTimeMillis() - ms;
30-
print('getFloat result:$resultFloat , cost:$use');
31-
32-
ms = currentTimeMillis();
33-
int resultByte = stub.getByte(1);
34-
use = currentTimeMillis() - ms;
35-
print('getByte result:$resultByte , cost:$use');
36-
37-
ms = currentTimeMillis();
38-
int resultShort = stub.getShort(1);
39-
use = currentTimeMillis() - ms;
40-
print('getShort result:$resultShort , cost:$use');
41-
42-
ms = currentTimeMillis();
43-
int resultLong = stub.getLong(100);
44-
use = currentTimeMillis() - ms;
45-
print('getLong result:$resultLong , cost:$use');
46-
47-
ms = currentTimeMillis();
48-
String resultString = stub.getString("test is success?");
49-
use = currentTimeMillis() - ms;
50-
print('getString result:$resultString, cost:$use');
51-
52-
ms = currentTimeMillis();
53-
int resultAdd = stub.add(10, 20);
54-
use = currentTimeMillis() - ms;
55-
print('add result:$resultAdd, cost:$use');
56-
57-
ms = currentTimeMillis();
58-
stub.log("testlog", "log test");
59-
use = currentTimeMillis() - ms;
60-
print('testlog, cost:$use');
61-
62-
bool resultCall = stub.complexCall(
63-
"test",
64-
10,
65-
'a',
66-
10.0,
67-
12.0,
68-
1,
69-
2,
70-
10000,
71-
false);
72-
print('call result:$resultCall');
73-
74-
Entity entity = stub.createEntity();
75-
print('entity get time : ${entity.getCurrentTime()}');
76-
print('stub get time : ${stub.getTime(entity)}');
77-
78-
print('new entity get time : ${stub.getTime(new Entity())}');
7+
// int ms = currentTimeMillis();
8+
// double resultDouble = stub.getDouble(10.0);
9+
// int use = currentTimeMillis() - ms;
10+
// print('getDouble result:$resultDouble , cost:$use');
11+
//
12+
// ms = currentTimeMillis();
13+
// String resultChar = stub.getChar('a');
14+
// use = currentTimeMillis() - ms;
15+
// print('getChar result:$resultChar , cost:$use');
16+
//
17+
// ms = currentTimeMillis();
18+
// int resultInt = stub.getInt(10);
19+
// use = currentTimeMillis() - ms;
20+
// print('getInt result:$resultInt , cost:$use');
21+
//
22+
// ms = currentTimeMillis();
23+
// bool resultBool = stub.getBool(true);
24+
// use = currentTimeMillis() - ms;
25+
// print('getBool result:$resultBool , cost:$use');
26+
//
27+
// ms = currentTimeMillis();
28+
// double resultFloat = stub.getFloat(10.5);
29+
// use = currentTimeMillis() - ms;
30+
// print('getFloat result:$resultFloat , cost:$use');
31+
//
32+
// ms = currentTimeMillis();
33+
// int resultByte = stub.getByte(1);
34+
// use = currentTimeMillis() - ms;
35+
// print('getByte result:$resultByte , cost:$use');
36+
//
37+
// ms = currentTimeMillis();
38+
// int resultShort = stub.getShort(1);
39+
// use = currentTimeMillis() - ms;
40+
// print('getShort result:$resultShort , cost:$use');
41+
//
42+
// ms = currentTimeMillis();
43+
// int resultLong = stub.getLong(100);
44+
// use = currentTimeMillis() - ms;
45+
// print('getLong result:$resultLong , cost:$use');
46+
//
47+
// ms = currentTimeMillis();
48+
// String resultString = stub.getString("test is success?");
49+
// use = currentTimeMillis() - ms;
50+
// print('getString result:$resultString, cost:$use');
51+
//
52+
// ms = currentTimeMillis();
53+
// int resultAdd = stub.add(10, 20);
54+
// use = currentTimeMillis() - ms;
55+
// print('add result:$resultAdd, cost:$use');
56+
//
57+
// ms = currentTimeMillis();
58+
// stub.log("testlog", "log test");
59+
// use = currentTimeMillis() - ms;
60+
// print('testlog, cost:$use');
61+
//
62+
// bool resultCall = stub.complexCall(
63+
// "test",
64+
// 10,
65+
// 'a',
66+
// 10.0,
67+
// 12.0,
68+
// 1,
69+
// 2,
70+
// 10000,
71+
// false);
72+
// print('call result:$resultCall');
73+
//
74+
// Entity entity = stub.createEntity();
75+
// print('entity get time : ${entity.getCurrentTime()}');
76+
// print('stub get time : ${stub.getTime(entity)}');
77+
//
78+
// print('new entity get time : ${stub.getTime(new Entity())}');
7979

8080
stub.setDelegateListener(DelegateStub());
8181

82-
print("integer ${stub.getInteger()}");
83-
84-
List list = stub.getList([1, 2, 3, 4]);
85-
for (int item in list) {
86-
print("item $item");
87-
}
88-
89-
list = stub.getByteList([byte(1), byte(2), byte(3), byte(4)]);
90-
for (int item in list) {
91-
print("item $item");
92-
}
93-
94-
list = stub.getFloatList([float(1.0), float(2.0), float(3.0), float(4.0)]);
95-
for (double item in list) {
96-
print("item $item");
97-
}
98-
99-
list = stub.getCycleList([[1, 2, 3], [4, 5, 6], [7, 8, 9]]);
100-
for (List items in list) {
101-
for (int item in items) {
102-
print("item $item");
103-
}
104-
}
105-
106-
List byteArray = stub.getByteArray([byte(1), byte(2), byte(3)]);
107-
for (int byte in byteArray) {
108-
print("item $byte");
109-
}
82+
// print("integer ${stub.getInteger()}");
83+
//
84+
// List list = stub.getList([1, 2, 3, 4]);
85+
// for (int item in list) {
86+
// print("item $item");
87+
// }
88+
//
89+
// list = stub.getByteList([byte(1), byte(2), byte(3), byte(4)]);
90+
// for (int item in list) {
91+
// print("item $item");
92+
// }
93+
//
94+
// list = stub.getFloatList([float(1.0), float(2.0), float(3.0), float(4.0)]);
95+
// for (double item in list) {
96+
// print("item $item");
97+
// }
98+
//
99+
// list = stub.getCycleList([[1, 2, 3], [4, 5, 6], [7, 8, 9]]);
100+
// for (List items in list) {
101+
// for (int item in items) {
102+
// print("item $item");
103+
// }
104+
// }
105+
//
106+
// List byteArray = stub.getByteArray([byte(1), byte(2), byte(3)]);
107+
// for (int byte in byteArray) {
108+
// print("item $byte");
109+
// }
110110
}
111111

112112
int currentTimeMillis() {

dart_native/example/lib/ios/unit_test.dart

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1+
import 'dart:async';
12
import 'dart:ffi';
3+
import 'dart:isolate';
24

35
import 'package:dart_native/dart_native.dart';
46
import 'package:dart_native_example/ios/delegatestub.dart';
@@ -153,4 +155,25 @@ testIOS(RuntimeStub stub, DelegateStub delegate) {
153155

154156
NSNotificationCenter.defaultCenter.addObserver(
155157
delegate, delegate.handleNotification, 'SampleDartNotification', nil);
158+
159+
Isolate.spawn(_checkTimer, stub.pointer.address);
160+
Isolate.spawn(_checkTimer1, stub.pointer.address);
161+
}
162+
163+
void _checkTimer(int addr) async {
164+
RuntimeStub stub = RuntimeStub.fromPointer(Pointer.fromAddress(addr));
165+
Timer.periodic(new Duration(seconds: 1), (Timer t) {
166+
stub.fooCompletion(() {
167+
print('hello completion block on another isolate!');
168+
});
169+
});
170+
}
171+
172+
void _checkTimer1(int addr) async {
173+
RuntimeStub stub = RuntimeStub.fromPointer(Pointer.fromAddress(addr));
174+
Timer.periodic(new Duration(seconds: 1), (Timer t) {
175+
stub.fooCompletion(() {
176+
print('hello completion block on third isolate!');
177+
});
178+
});
156179
}

dart_native/example/pubspec.lock

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -168,7 +168,7 @@ packages:
168168
path: ".."
169169
relative: true
170170
source: path
171-
version: "0.3.16"
171+
version: "0.3.18"
172172
dart_native_gen:
173173
dependency: transitive
174174
description:

0 commit comments

Comments
 (0)