OLD | NEW |
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/bootstrap_natives.h" | 5 #include "vm/bootstrap_natives.h" |
6 #include "vm/dart_api_impl.h" | 6 #include "vm/dart_api_impl.h" |
7 #include "vm/datastream.h" | 7 #include "vm/datastream.h" |
8 #include "vm/exceptions.h" | 8 #include "vm/exceptions.h" |
9 #include "vm/flags.h" | 9 #include "vm/flags.h" |
10 #include "vm/growable_array.h" | 10 #include "vm/growable_array.h" |
| 11 #include "vm/kernel_isolate.h" |
11 #include "vm/message.h" | 12 #include "vm/message.h" |
12 #include "vm/message_handler.h" | 13 #include "vm/message_handler.h" |
13 #include "vm/native_entry.h" | 14 #include "vm/native_entry.h" |
14 #include "vm/object.h" | 15 #include "vm/object.h" |
15 #include "vm/port.h" | 16 #include "vm/port.h" |
16 #include "vm/service_event.h" | 17 #include "vm/service_event.h" |
17 #include "vm/service_isolate.h" | 18 #include "vm/service_isolate.h" |
18 #include "vm/symbols.h" | 19 #include "vm/symbols.h" |
19 #include "vm/kernel_isolate.h" | |
20 | 20 |
21 namespace dart { | 21 namespace dart { |
22 | 22 |
23 DECLARE_FLAG(bool, trace_service); | 23 DECLARE_FLAG(bool, trace_service); |
24 DECLARE_FLAG(bool, show_kernel_isolate); | 24 DECLARE_FLAG(bool, show_kernel_isolate); |
25 | 25 |
26 static uint8_t* malloc_allocator(uint8_t* ptr, | 26 static uint8_t* malloc_allocator(uint8_t* ptr, |
27 intptr_t old_size, | 27 intptr_t old_size, |
28 intptr_t new_size) { | 28 intptr_t new_size) { |
29 void* new_ptr = realloc(reinterpret_cast<void*>(ptr), new_size); | 29 void* new_ptr = realloc(reinterpret_cast<void*>(ptr), new_size); |
30 return reinterpret_cast<uint8_t*>(new_ptr); | 30 return reinterpret_cast<uint8_t*>(new_ptr); |
31 } | 31 } |
32 | 32 |
33 static void malloc_deallocator(uint8_t* ptr) { | 33 static void malloc_deallocator(uint8_t* ptr) { |
34 free(reinterpret_cast<void*>(ptr)); | 34 free(reinterpret_cast<void*>(ptr)); |
35 } | 35 } |
36 | 36 |
37 | |
38 #ifndef PRODUCT | 37 #ifndef PRODUCT |
39 class RegisterRunningIsolatesVisitor : public IsolateVisitor { | 38 class RegisterRunningIsolatesVisitor : public IsolateVisitor { |
40 public: | 39 public: |
41 explicit RegisterRunningIsolatesVisitor(Thread* thread) | 40 explicit RegisterRunningIsolatesVisitor(Thread* thread) |
42 : IsolateVisitor(), | 41 : IsolateVisitor(), |
43 register_function_(Function::Handle(thread->zone())), | 42 register_function_(Function::Handle(thread->zone())), |
44 service_isolate_(thread->isolate()) { | 43 service_isolate_(thread->isolate()) { |
45 ASSERT(ServiceIsolate::IsServiceIsolate(Isolate::Current())); | 44 ASSERT(ServiceIsolate::IsServiceIsolate(Isolate::Current())); |
46 // Get library. | 45 // Get library. |
47 const String& library_url = Symbols::DartVMService(); | 46 const String& library_url = Symbols::DartVMService(); |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
111 uint8_t* data = NULL; | 110 uint8_t* data = NULL; |
112 MessageWriter writer(&data, &malloc_allocator, &malloc_deallocator, false); | 111 MessageWriter writer(&data, &malloc_allocator, &malloc_deallocator, false); |
113 writer.WriteMessage(message); | 112 writer.WriteMessage(message); |
114 | 113 |
115 // TODO(turnidge): Throw an exception when the return value is false? | 114 // TODO(turnidge): Throw an exception when the return value is false? |
116 bool result = PortMap::PostMessage( | 115 bool result = PortMap::PostMessage( |
117 new Message(sp.Id(), data, writer.BytesWritten(), Message::kOOBPriority)); | 116 new Message(sp.Id(), data, writer.BytesWritten(), Message::kOOBPriority)); |
118 return Bool::Get(result).raw(); | 117 return Bool::Get(result).raw(); |
119 } | 118 } |
120 | 119 |
121 | |
122 DEFINE_NATIVE_ENTRY(VMService_SendRootServiceMessage, 1) { | 120 DEFINE_NATIVE_ENTRY(VMService_SendRootServiceMessage, 1) { |
123 GET_NON_NULL_NATIVE_ARGUMENT(Array, message, arguments->NativeArgAt(0)); | 121 GET_NON_NULL_NATIVE_ARGUMENT(Array, message, arguments->NativeArgAt(0)); |
124 if (FLAG_support_service) { | 122 if (FLAG_support_service) { |
125 return Service::HandleRootMessage(message); | 123 return Service::HandleRootMessage(message); |
126 } | 124 } |
127 return Object::null(); | 125 return Object::null(); |
128 } | 126 } |
129 | 127 |
130 | |
131 DEFINE_NATIVE_ENTRY(VMService_SendObjectRootServiceMessage, 1) { | 128 DEFINE_NATIVE_ENTRY(VMService_SendObjectRootServiceMessage, 1) { |
132 GET_NON_NULL_NATIVE_ARGUMENT(Array, message, arguments->NativeArgAt(0)); | 129 GET_NON_NULL_NATIVE_ARGUMENT(Array, message, arguments->NativeArgAt(0)); |
133 if (FLAG_support_service) { | 130 if (FLAG_support_service) { |
134 return Service::HandleObjectRootMessage(message); | 131 return Service::HandleObjectRootMessage(message); |
135 } | 132 } |
136 return Object::null(); | 133 return Object::null(); |
137 } | 134 } |
138 | 135 |
139 | |
140 DEFINE_NATIVE_ENTRY(VMService_OnStart, 0) { | 136 DEFINE_NATIVE_ENTRY(VMService_OnStart, 0) { |
141 if (FLAG_trace_service) { | 137 if (FLAG_trace_service) { |
142 OS::Print("vm-service: Booting dart:vmservice library.\n"); | 138 OS::Print("vm-service: Booting dart:vmservice library.\n"); |
143 } | 139 } |
144 // Boot the dart:vmservice library. | 140 // Boot the dart:vmservice library. |
145 ServiceIsolate::BootVmServiceLibrary(); | 141 ServiceIsolate::BootVmServiceLibrary(); |
146 if (!FLAG_support_service) { | 142 if (!FLAG_support_service) { |
147 return Object::null(); | 143 return Object::null(); |
148 } | 144 } |
149 #ifndef PRODUCT | 145 #ifndef PRODUCT |
150 // Register running isolates with service. | 146 // Register running isolates with service. |
151 RegisterRunningIsolatesVisitor register_isolates(thread); | 147 RegisterRunningIsolatesVisitor register_isolates(thread); |
152 if (FLAG_trace_service) { | 148 if (FLAG_trace_service) { |
153 OS::Print("vm-service: Registering running isolates.\n"); | 149 OS::Print("vm-service: Registering running isolates.\n"); |
154 } | 150 } |
155 Isolate::VisitIsolates(®ister_isolates); | 151 Isolate::VisitIsolates(®ister_isolates); |
156 #endif | 152 #endif |
157 return Object::null(); | 153 return Object::null(); |
158 } | 154 } |
159 | 155 |
160 | |
161 DEFINE_NATIVE_ENTRY(VMService_OnExit, 0) { | 156 DEFINE_NATIVE_ENTRY(VMService_OnExit, 0) { |
162 if (FLAG_trace_service) { | 157 if (FLAG_trace_service) { |
163 OS::Print("vm-service: processed exit message.\n"); | 158 OS::Print("vm-service: processed exit message.\n"); |
164 MessageHandler* message_handler = isolate->message_handler(); | 159 MessageHandler* message_handler = isolate->message_handler(); |
165 OS::Print("vm-service: live ports = %" Pd "\n", | 160 OS::Print("vm-service: live ports = %" Pd "\n", |
166 message_handler->live_ports()); | 161 message_handler->live_ports()); |
167 } | 162 } |
168 return Object::null(); | 163 return Object::null(); |
169 } | 164 } |
170 | 165 |
171 | |
172 DEFINE_NATIVE_ENTRY(VMService_OnServerAddressChange, 1) { | 166 DEFINE_NATIVE_ENTRY(VMService_OnServerAddressChange, 1) { |
173 if (!FLAG_support_service) { | 167 if (!FLAG_support_service) { |
174 return Object::null(); | 168 return Object::null(); |
175 } | 169 } |
176 GET_NATIVE_ARGUMENT(String, address, arguments->NativeArgAt(0)); | 170 GET_NATIVE_ARGUMENT(String, address, arguments->NativeArgAt(0)); |
177 if (address.IsNull()) { | 171 if (address.IsNull()) { |
178 ServiceIsolate::SetServerAddress(NULL); | 172 ServiceIsolate::SetServerAddress(NULL); |
179 } else { | 173 } else { |
180 ServiceIsolate::SetServerAddress(address.ToCString()); | 174 ServiceIsolate::SetServerAddress(address.ToCString()); |
181 } | 175 } |
182 return Object::null(); | 176 return Object::null(); |
183 } | 177 } |
184 | 178 |
185 | |
186 DEFINE_NATIVE_ENTRY(VMService_ListenStream, 1) { | 179 DEFINE_NATIVE_ENTRY(VMService_ListenStream, 1) { |
187 GET_NON_NULL_NATIVE_ARGUMENT(String, stream_id, arguments->NativeArgAt(0)); | 180 GET_NON_NULL_NATIVE_ARGUMENT(String, stream_id, arguments->NativeArgAt(0)); |
188 bool result = false; | 181 bool result = false; |
189 if (FLAG_support_service) { | 182 if (FLAG_support_service) { |
190 result = Service::ListenStream(stream_id.ToCString()); | 183 result = Service::ListenStream(stream_id.ToCString()); |
191 } | 184 } |
192 return Bool::Get(result).raw(); | 185 return Bool::Get(result).raw(); |
193 } | 186 } |
194 | 187 |
195 | |
196 DEFINE_NATIVE_ENTRY(VMService_CancelStream, 1) { | 188 DEFINE_NATIVE_ENTRY(VMService_CancelStream, 1) { |
197 GET_NON_NULL_NATIVE_ARGUMENT(String, stream_id, arguments->NativeArgAt(0)); | 189 GET_NON_NULL_NATIVE_ARGUMENT(String, stream_id, arguments->NativeArgAt(0)); |
198 if (FLAG_support_service) { | 190 if (FLAG_support_service) { |
199 Service::CancelStream(stream_id.ToCString()); | 191 Service::CancelStream(stream_id.ToCString()); |
200 } | 192 } |
201 return Object::null(); | 193 return Object::null(); |
202 } | 194 } |
203 | 195 |
204 | |
205 DEFINE_NATIVE_ENTRY(VMService_RequestAssets, 0) { | 196 DEFINE_NATIVE_ENTRY(VMService_RequestAssets, 0) { |
206 if (!FLAG_support_service) { | 197 if (!FLAG_support_service) { |
207 return Object::null(); | 198 return Object::null(); |
208 } | 199 } |
209 return Service::RequestAssets(); | 200 return Service::RequestAssets(); |
210 } | 201 } |
211 | 202 |
212 | |
213 #ifndef PRODUCT | 203 #ifndef PRODUCT |
214 // TODO(25041): When reading, this class copies out the filenames and contents | 204 // TODO(25041): When reading, this class copies out the filenames and contents |
215 // into new buffers. It does this because the lifetime of |bytes| is uncertain. | 205 // into new buffers. It does this because the lifetime of |bytes| is uncertain. |
216 // If |bytes| is pinned in memory, then we could instead load up | 206 // If |bytes| is pinned in memory, then we could instead load up |
217 // |filenames_| and |contents_| with pointers into |bytes| without making | 207 // |filenames_| and |contents_| with pointers into |bytes| without making |
218 // copies. | 208 // copies. |
219 class TarArchive { | 209 class TarArchive { |
220 public: | 210 public: |
221 TarArchive(uint8_t* bytes, intptr_t bytes_length) | 211 TarArchive(uint8_t* bytes, intptr_t bytes_length) |
222 : rs_(bytes, bytes_length) {} | 212 : rs_(bytes, bytes_length) {} |
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
366 } | 356 } |
367 | 357 |
368 ReadStream rs_; | 358 ReadStream rs_; |
369 GrowableArray<char*> filenames_; | 359 GrowableArray<char*> filenames_; |
370 GrowableArray<uint8_t*> contents_; | 360 GrowableArray<uint8_t*> contents_; |
371 GrowableArray<intptr_t> content_lengths_; | 361 GrowableArray<intptr_t> content_lengths_; |
372 | 362 |
373 DISALLOW_COPY_AND_ASSIGN(TarArchive); | 363 DISALLOW_COPY_AND_ASSIGN(TarArchive); |
374 }; | 364 }; |
375 | 365 |
376 | |
377 static void ContentsFinalizer(void* isolate_callback_data, | 366 static void ContentsFinalizer(void* isolate_callback_data, |
378 Dart_WeakPersistentHandle handle, | 367 Dart_WeakPersistentHandle handle, |
379 void* peer) { | 368 void* peer) { |
380 uint8_t* data = reinterpret_cast<uint8_t*>(peer); | 369 uint8_t* data = reinterpret_cast<uint8_t*>(peer); |
381 delete[] data; | 370 delete[] data; |
382 } | 371 } |
383 | 372 |
384 | |
385 static void FilenameFinalizer(void* peer) { | 373 static void FilenameFinalizer(void* peer) { |
386 char* filename = reinterpret_cast<char*>(peer); | 374 char* filename = reinterpret_cast<char*>(peer); |
387 delete[] filename; | 375 delete[] filename; |
388 } | 376 } |
389 | 377 |
390 | |
391 #endif | 378 #endif |
392 | 379 |
393 | |
394 DEFINE_NATIVE_ENTRY(VMService_DecodeAssets, 1) { | 380 DEFINE_NATIVE_ENTRY(VMService_DecodeAssets, 1) { |
395 #ifndef PRODUCT | 381 #ifndef PRODUCT |
396 if (!FLAG_support_service) { | 382 if (!FLAG_support_service) { |
397 return Object::null(); | 383 return Object::null(); |
398 } | 384 } |
399 GET_NON_NULL_NATIVE_ARGUMENT(TypedData, data, arguments->NativeArgAt(0)); | 385 GET_NON_NULL_NATIVE_ARGUMENT(TypedData, data, arguments->NativeArgAt(0)); |
400 TransitionVMToNative transition(thread); | 386 TransitionVMToNative transition(thread); |
401 Api::Scope scope(thread); | 387 Api::Scope scope(thread); |
402 | 388 |
403 Dart_Handle data_handle = Api::NewHandle(thread, data.raw()); | 389 Dart_Handle data_handle = Api::NewHandle(thread, data.raw()); |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
440 Dart_ListSetAt(result_list, idx, dart_filename); | 426 Dart_ListSetAt(result_list, idx, dart_filename); |
441 Dart_ListSetAt(result_list, (idx + 1), dart_contents); | 427 Dart_ListSetAt(result_list, (idx + 1), dart_contents); |
442 idx += 2; | 428 idx += 2; |
443 } | 429 } |
444 return Api::UnwrapArrayHandle(thread->zone(), result_list).raw(); | 430 return Api::UnwrapArrayHandle(thread->zone(), result_list).raw(); |
445 #else | 431 #else |
446 return Object::null(); | 432 return Object::null(); |
447 #endif | 433 #endif |
448 } | 434 } |
449 | 435 |
450 | |
451 DEFINE_NATIVE_ENTRY(VMService_spawnUriNotify, 2) { | 436 DEFINE_NATIVE_ENTRY(VMService_spawnUriNotify, 2) { |
452 #ifndef PRODUCT | 437 #ifndef PRODUCT |
453 if (!FLAG_support_service) { | 438 if (!FLAG_support_service) { |
454 return Object::null(); | 439 return Object::null(); |
455 } | 440 } |
456 GET_NON_NULL_NATIVE_ARGUMENT(Instance, result, arguments->NativeArgAt(0)); | 441 GET_NON_NULL_NATIVE_ARGUMENT(Instance, result, arguments->NativeArgAt(0)); |
457 GET_NON_NULL_NATIVE_ARGUMENT(String, token, arguments->NativeArgAt(1)); | 442 GET_NON_NULL_NATIVE_ARGUMENT(String, token, arguments->NativeArgAt(1)); |
458 | 443 |
459 if (result.IsSendPort()) { | 444 if (result.IsSendPort()) { |
460 Dart_Port id = SendPort::Cast(result).Id(); | 445 Dart_Port id = SendPort::Cast(result).Id(); |
(...skipping 18 matching lines...) Expand all Loading... |
479 ServiceEvent spawn_event(NULL, ServiceEvent::kIsolateSpawn); | 464 ServiceEvent spawn_event(NULL, ServiceEvent::kIsolateSpawn); |
480 spawn_event.set_spawn_token(&token); | 465 spawn_event.set_spawn_token(&token); |
481 spawn_event.set_spawn_error(&String::Cast(result)); | 466 spawn_event.set_spawn_error(&String::Cast(result)); |
482 Service::HandleEvent(&spawn_event); | 467 Service::HandleEvent(&spawn_event); |
483 } | 468 } |
484 #endif // PRODUCT | 469 #endif // PRODUCT |
485 return Object::null(); | 470 return Object::null(); |
486 } | 471 } |
487 | 472 |
488 } // namespace dart | 473 } // namespace dart |
OLD | NEW |