Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(44)

Side by Side Diff: runtime/bin/file.cc

Issue 9415043: Port async file operations to be using native ports instead or an isolate (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Fixed remaining issues Created 8 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, 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 "bin/file.h" 5 #include "bin/file.h"
6 6
7 #include "bin/builtin.h" 7 #include "bin/builtin.h"
8 #include "bin/dartutils.h" 8 #include "bin/dartutils.h"
9 9
10 #include "include/dart_api.h" 10 #include "include/dart_api.h"
(...skipping 22 matching lines...) Expand all
33 if (bytes_read < 0) { 33 if (bytes_read < 0) {
34 return false; 34 return false;
35 } 35 }
36 remaining -= bytes_read; // Reduce the number of remaining bytes. 36 remaining -= bytes_read; // Reduce the number of remaining bytes.
37 current_buffer += bytes_read; // Move the buffer forward. 37 current_buffer += bytes_read; // Move the buffer forward.
38 } 38 }
39 return true; 39 return true;
40 } 40 }
41 41
42 42
43 File::FileOpenMode File::DartModeToFileMode(DartFileOpenMode mode) {
44 ASSERT(mode == File::kDartRead ||
45 mode == File::kDartWrite ||
46 mode == File::kDartAppend);
47 if (mode == File::kDartWrite) {
48 return File::kWriteTruncate;
49 }
50 if (mode == File::kDartAppend) {
51 return File::kWrite;
52 }
53 return File::kRead;
54 }
55
56
43 void FUNCTION_NAME(File_Open)(Dart_NativeArguments args) { 57 void FUNCTION_NAME(File_Open)(Dart_NativeArguments args) {
44 // These values have to be kept in sync with the mode values of
45 // FileMode.READ, FileMode.WRITE and FileMode.APPEND in file.dart.
46 static const int kRead = 0;
47 static const int kWrite = 1;
48 static const int kAppend = 2;
49
50 Dart_EnterScope(); 58 Dart_EnterScope();
51 const char* filename = 59 const char* filename =
52 DartUtils::GetStringValue(Dart_GetNativeArgument(args, 0)); 60 DartUtils::GetStringValue(Dart_GetNativeArgument(args, 0));
53 int mode = DartUtils::GetIntegerValue(Dart_GetNativeArgument(args, 1)); 61 File::DartFileOpenMode dart_file_mode;
54 ASSERT(mode == kRead || mode == kWrite || mode == kAppend); 62 dart_file_mode = static_cast<File::DartFileOpenMode>(
Mads Ager (google) 2012/02/23 08:57:44 How about extracting the int first? int mode = Da
Søren Gjesse 2012/02/23 10:26:42 Done.
55 File::FileOpenMode file_mode = File::kRead; 63 DartUtils::GetIntegerValue(Dart_GetNativeArgument(args, 1)));
56 if (mode == kWrite) { 64 File::FileOpenMode file_mode = File::DartModeToFileMode(dart_file_mode);
57 file_mode = File::kWriteTruncate;
58 }
59 if (mode == kAppend) {
60 file_mode = File::kWrite;
61 }
62 // Check that the file exists before opening it only for 65 // Check that the file exists before opening it only for
63 // reading. This is to prevent the opening of directories as 66 // reading. This is to prevent the opening of directories as
64 // files. Directories can be opened for reading using the posix 67 // files. Directories can be opened for reading using the posix
65 // 'open' call. 68 // 'open' call.
66 File* file = NULL; 69 File* file = NULL;
67 if (((file_mode & File::kWrite) != 0) || File::Exists(filename)) { 70 if (((file_mode & File::kWrite) != 0) || File::Exists(filename)) {
68 file = File::Open(filename, file_mode); 71 file = File::Open(filename, file_mode);
69 } 72 }
70 Dart_SetReturnValue(args, Dart_NewInteger(reinterpret_cast<intptr_t>(file))); 73 Dart_SetReturnValue(args, Dart_NewInteger(reinterpret_cast<intptr_t>(file)));
71 Dart_ExitScope(); 74 Dart_ExitScope();
(...skipping 270 matching lines...) Expand 10 before | Expand all | Expand 10 after
342 } 345 }
343 346
344 347
345 void FUNCTION_NAME(File_GetStdioHandleType)(Dart_NativeArguments args) { 348 void FUNCTION_NAME(File_GetStdioHandleType)(Dart_NativeArguments args) {
346 Dart_EnterScope(); 349 Dart_EnterScope();
347 int fd = DartUtils::GetIntegerValue(Dart_GetNativeArgument(args, 0)); 350 int fd = DartUtils::GetIntegerValue(Dart_GetNativeArgument(args, 0));
348 File::StdioHandleType type = File::GetStdioHandleType(fd); 351 File::StdioHandleType type = File::GetStdioHandleType(fd);
349 Dart_SetReturnValue(args, Dart_NewInteger(type)); 352 Dart_SetReturnValue(args, Dart_NewInteger(type));
350 Dart_ExitScope(); 353 Dart_ExitScope();
351 } 354 }
355
356
357 static int64_t CObjectInt32OrInt64ToInt64(CObject* cobject) {
358 ASSERT(cobject->IsInt32OrInt64());
359 int64_t result;
360 if (cobject->IsInt32()) {
361 CObjectInt32 value(cobject);
362 result = value.Value();
363 } else {
364 CObjectInt64 value(cobject);
365 result = value.Value();
366 }
367 return result;
368 }
369
370
371 File* CObjectToFilePointer(CObject* cobject) {
372 CObjectIntptr value(cobject);
373 return reinterpret_cast<File*>(value.Value());
374 }
375
376
377 static CObject* FileExistsRequest(const CObjectArray& request) {
378 if (request.Length() == 2 && request[1]->IsString()) {
379 CObjectString filename(request[1]);
380 bool result = File::Exists(filename.CString());
381 return CObject::Bool(result);
382 }
383 return CObject::False();
384 }
385
386
387 static CObject* FileCreateRequest(const CObjectArray& request) {
388 if (request.Length() == 2 && request[1]->IsString()) {
389 CObjectString filename(request[1]);
390 bool result = File::Create(filename.CString());
391 return CObject::Bool(result);
392 }
393 return CObject::False();
394 }
395
396
397 static CObject* FileOpenRequest(const CObjectArray& request) {
398 File* file = NULL;
399 if (request.Length() == 3 &&
400 request[1]->IsString() &&
401 request[2]->IsInt32()) {
402 CObjectString filename(request[1]);
403 CObjectInt32 mode(request[2]);
404 File::DartFileOpenMode dart_file_mode =
405 static_cast<File::DartFileOpenMode>(mode.Value());
406 File::FileOpenMode file_mode = File::DartModeToFileMode(dart_file_mode);
407 if (((file_mode & File::kWrite) != 0) || File::Exists(filename.CString())) {
408 file = File::Open(filename.CString(), file_mode);
409 }
410 }
411 return new CObjectIntptr(
412 CObject::NewIntptr(reinterpret_cast<intptr_t>(file)));
413 }
414
415
416 static CObject* FileDeleteRequest(const CObjectArray& request) {
417 if (request.Length() == 2 && request[1]->IsString()) {
418 CObjectString filename(request[1]);
419 bool result = File::Delete(filename.CString());
420 return CObject::Bool(result);
421 }
422 return CObject::False();
423 }
424
425
426 static CObject* FileFullPathRequest(const CObjectArray& request) {
427 if (request.Length() == 2 && request[1]->IsString()) {
428 CObjectString filename(request[1]);
429 char* path = File::GetCanonicalPath(filename.CString());
430 return new CObjectString(CObject::NewString(path));
431 }
432 return CObject::Null();
433 }
434
435
436 static CObject* FileCloseRequest(const CObjectArray& request) {
437 intptr_t return_value = -1;
438 if (request.Length() == 2 && request[1]->IsIntptr()) {
439 File* file = CObjectToFilePointer(request[1]);
440 if (file != NULL) {
441 delete file;
442 return_value = 0;
443 }
444 }
445 return new CObjectIntptr(CObject::NewIntptr(return_value));
446 }
447
448
449 static CObject* FilePositionRequest(const CObjectArray& request) {
450 intptr_t return_value = -1;
451 if (request.Length() == 2 && request[1]->IsIntptr()) {
452 File* file = CObjectToFilePointer(request[1]);
453 if (file != NULL) {
454 return_value = file->Position();
455 }
456 }
457 return new CObjectIntptr(CObject::NewIntptr(return_value));
458 }
459
460
461 static CObject* FileSetPositionRequest(const CObjectArray& request) {
462 bool return_value = false;
463 if (request.Length() == 3 &&
464 request[1]->IsIntptr() &&
465 request[2]->IsInt32OrInt64()) {
466 File* file = CObjectToFilePointer(request[1]);
467 if (file != NULL) {
468 int64_t position = CObjectInt32OrInt64ToInt64(request[2]);
469 return_value = file->SetPosition(position);
470 }
471 }
472 return CObject::Bool(return_value);
473 }
474
475
476 static CObject* FileTruncateRequest(const CObjectArray& request) {
477 bool return_value = false;
478 if (request.Length() == 3 &&
479 request[1]->IsIntptr() &&
480 request[2]->IsInt32OrInt64()) {
481 File* file = CObjectToFilePointer(request[1]);
482 if (file != NULL) {
483 int64_t length = CObjectInt32OrInt64ToInt64(request[2]);
484 return_value = file->Truncate(length);
485 }
486 }
487 return CObject::Bool(return_value);
488 }
489
490
491 static CObject* FileLengthRequest(const CObjectArray& request) {
492 intptr_t return_value = -1;
493 if (request.Length() == 2 && request[1]->IsIntptr()) {
494 File* file = CObjectToFilePointer(request[1]);
495 if (file != NULL) {
496 return_value = file->Length();
497 }
498 }
499 return new CObjectIntptr(CObject::NewIntptr(return_value));
500 }
501
502
503 static CObject* FileFlushRequest(const CObjectArray& request) {
504 intptr_t return_value = -1;
505 if (request.Length() == 2 && request[1]->IsIntptr()) {
506 File* file = CObjectToFilePointer(request[1]);
507 if (file != NULL) {
508 file->Flush();
509 return_value = 0;
510 }
511 }
512 return new CObjectIntptr(CObject::NewIntptr(return_value));
513 }
514
515
516 static CObject* FileReadByteRequest(const CObjectArray& request) {
517 intptr_t return_value = -1;
518 if (request.Length() == 2 && request[1]->IsIntptr()) {
519 File* file = CObjectToFilePointer(request[1]);
520 if (file != NULL) {
521 uint8_t buffer;
522 int bytes_read = file->Read(reinterpret_cast<void*>(&buffer), 1);
523 if (bytes_read == 1) {
524 return_value = static_cast<intptr_t>(buffer);
525 } else {
526 return_value = -1;
527 }
528 }
529 }
530 return new CObjectIntptr(CObject::NewIntptr(return_value));
531 }
532
533 static CObject* FileWriteByteRequest(const CObjectArray& request) {
534 intptr_t return_value = -1;
535 if (request.Length() == 3 &&
536 request[1]->IsIntptr() &&
537 request[2]->IsInt32OrInt64()) {
538 File* file = CObjectToFilePointer(request[1]);
539 if (file != NULL) {
540 int64_t byte = CObjectInt32OrInt64ToInt64(request[2]);
541 uint8_t buffer = static_cast<uint8_t>(byte & 0xff);
542 int bytes_written = file->Write(reinterpret_cast<void*>(&buffer), 1);
543 if (bytes_written >= 0) {
544 return_value = bytes_written;
545 }
546 }
547 }
548 return new CObjectIntptr(CObject::NewIntptr(return_value));
549 }
550
551 static CObject* FileReadListRequest(const CObjectArray& request) {
552 if (request.Length() == 3 &&
553 request[1]->IsIntptr() &&
554 request[2]->IsInt32OrInt64()) {
555 File* file = CObjectToFilePointer(request[1]);
556 int64_t length = CObjectInt32OrInt64ToInt64(request[2]);
557 CObjectByteArray* byte_array =
558 new CObjectByteArray(CObject::NewByteArray(length));
559 void* buffer = reinterpret_cast<void*>(byte_array->Buffer());
560 int total_bytes_read = file->Read(buffer, byte_array->Length());
561 CObjectArray* result = new CObjectArray(CObject::NewArray(2));
562 result->SetAt(0, new CObjectIntptr(CObject::NewIntptr(total_bytes_read)));
563 result->SetAt(1, byte_array);
564 return result;
565 }
566 return CObject::Null();
567 }
568
569
570 static CObject* FileWriteListRequest(const CObjectArray& request) {
571 if (request.Length() == 5 &&
572 request[1]->IsIntptr() &&
573 (request[2]->IsByteArray() || request[2]->IsArray()) &&
574 request[3]->IsInt32OrInt64() &&
575 request[4]->IsInt32OrInt64()) {
576 File* file = CObjectToFilePointer(request[1]);
577 int64_t offset = CObjectInt32OrInt64ToInt64(request[3]);
578 int64_t length = CObjectInt32OrInt64ToInt64(request[4]);
579 uint8_t* buffer_start;
580 if (request[2]->IsByteArray()) {
581 CObjectByteArray byte_array(request[2]);
582 buffer_start = byte_array.Buffer() + offset;
583 } else {
584 CObjectArray array(request[2]);
585 buffer_start = new uint8_t[length];
586 for (int i = 0; i < length; i++) {
587 if (array[i + offset]->IsInt32OrInt64()) {
588 int64_t value = CObjectInt32OrInt64ToInt64(array[i + offset]);
589 buffer_start[i] = value & 0xFF;
590 } else {
591 // Unsupported type.
592 delete[] buffer_start;
593 return new CObjectInt32(CObject::NewInt32(-1));
594 }
595 }
596 offset = 0;
597 }
598 int64_t total_bytes_written =
599 file->Write(reinterpret_cast<void*>(buffer_start), length);
600 ASSERT(total_bytes_written == length);
601 if (!request[2]->IsByteArray()) {
602 delete[] buffer_start;
603 }
604 return new CObjectInt64(CObject::NewInt64(total_bytes_written));
605 }
606 return CObject::Null();
607 }
608
609
610 static CObject* FileWriteStringRequest(const CObjectArray& request) {
611 if (request.Length() == 3 &&
612 request[1]->IsIntptr() &&
613 request[2]->IsString()) {
614 File* file = CObjectToFilePointer(request[1]);
615 CObjectString str(request[2]);
616 const void* buffer = reinterpret_cast<const void*>(str.CString());
617 int64_t total_bytes_written = file->Write(buffer, str.Length());
618 ASSERT(total_bytes_written == str.Length());
619 return new CObjectInt64(CObject::NewInt64(total_bytes_written));
620 }
621 return CObject::Null();
622 }
623
624
625 void FileService(Dart_Port dest_port_id,
626 Dart_Port reply_port_id,
627 Dart_CObject* message) {
628 CObject* response = CObject::False();
629 CObjectArray request(message);
630 if (message->type == Dart_CObject::kArray) {
631 if (request.Length() > 1 && request[0]->IsInt32()) {
632 CObjectInt32 requestType(request[0]);
633 switch (requestType.Value()) {
634 case File::kExistsRequest:
635 response = FileExistsRequest(request);
636 break;
637 case File::kCreateRequest:
638 response = FileCreateRequest(request);
639 break;
640 case File::kOpenRequest:
641 response = FileOpenRequest(request);
642 break;
643 case File::kDeleteRequest:
644 response = FileDeleteRequest(request);
645 break;
646 case File::kFullPathRequest:
647 response = FileFullPathRequest(request);
648 break;
649 case File::kCloseRequest:
650 response = FileCloseRequest(request);
651 break;
652 case File::kPositionRequest:
653 response = FilePositionRequest(request);
654 break;
655 case File::kSetPositionRequest:
656 response = FileSetPositionRequest(request);
657 break;
658 case File::kTruncateRequest:
659 response = FileTruncateRequest(request);
660 break;
661 case File::kLengthRequest:
662 response = FileLengthRequest(request);
663 break;
664 case File::kFlushRequest:
665 response = FileFlushRequest(request);
666 break;
667 case File::kReadByteRequest:
668 response = FileReadByteRequest(request);
669 break;
670 case File::kWriteByteRequest:
671 response = FileWriteByteRequest(request);
672 break;
673 case File::kReadListRequest:
674 response = FileReadListRequest(request);
675 break;
676 case File::kWriteListRequest:
677 response = FileWriteListRequest(request);
678 break;
679 case File::kWriteStringRequest:
680 response = FileWriteStringRequest(request);
681 break;
682 default:
683 UNREACHABLE();
684 }
685 }
686 }
687
688 Dart_PostCObject(reply_port_id, response->AsApiCObject());
689 }
690
691
692 void FUNCTION_NAME(File_NewServicePort)(Dart_NativeArguments args) {
693 Dart_EnterScope();
694 Dart_SetReturnValue(args, Dart_Null());
695 Dart_Port service_port = kIllegalPort;
696 service_port = Dart_NewNativePort("FileService",
697 FileService,
698 true);
699 if (service_port != kIllegalPort) {
700 // Return a send port for the service port.
701 Dart_Handle send_port = Dart_NewSendPort(service_port);
702 Dart_SetReturnValue(args, send_port);
703 }
704 Dart_ExitScope();
705 }
OLDNEW
« no previous file with comments | « runtime/bin/file.h ('k') | runtime/bin/file_impl.dart » ('j') | runtime/bin/file_impl.dart » ('J')

Powered by Google App Engine
This is Rietveld 408576698