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

Side by Side Diff: runtime/vm/object.cc

Issue 8383029: Implement external strings. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Finish native peer support Created 9 years, 1 month 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) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, 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/object.h" 5 #include "vm/object.h"
6 6
7 #include "vm/assembler.h" 7 #include "vm/assembler.h"
8 #include "vm/assert.h" 8 #include "vm/assert.h"
9 #include "vm/bigint_operations.h" 9 #include "vm/bigint_operations.h"
10 #include "vm/bootstrap.h" 10 #include "vm/bootstrap.h"
(...skipping 370 matching lines...) Expand 10 before | Expand all | Expand 10 after
381 381
382 cls = Class::New<OneByteString>(); 382 cls = Class::New<OneByteString>();
383 object_store->set_one_byte_string_class(cls); 383 object_store->set_one_byte_string_class(cls);
384 384
385 cls = Class::New<TwoByteString>(); 385 cls = Class::New<TwoByteString>();
386 object_store->set_two_byte_string_class(cls); 386 object_store->set_two_byte_string_class(cls);
387 387
388 cls = Class::New<FourByteString>(); 388 cls = Class::New<FourByteString>();
389 object_store->set_four_byte_string_class(cls); 389 object_store->set_four_byte_string_class(cls);
390 390
391 cls = Class::New<ExternalOneByteString>();
392 object_store->set_external_one_byte_string_class(cls);
393
394 cls = Class::New<ExternalTwoByteString>();
395 object_store->set_external_two_byte_string_class(cls);
396
397 cls = Class::New<ExternalFourByteString>();
398 object_store->set_external_four_byte_string_class(cls);
399
391 cls = Class::New<Bool>(); 400 cls = Class::New<Bool>();
392 object_store->set_bool_class(cls); 401 object_store->set_bool_class(cls);
393 402
394 cls = Class::New<UnhandledException>(); 403 cls = Class::New<UnhandledException>();
395 object_store->set_unhandled_exception_class(cls); 404 object_store->set_unhandled_exception_class(cls);
396 405
397 cls = Class::New<Stacktrace>(); 406 cls = Class::New<Stacktrace>();
398 object_store->set_stacktrace_class(cls); 407 object_store->set_stacktrace_class(cls);
399 // Set the super type so that the 'toString' method is implemented. 408 // Set the super type so that the 'toString' method is implemented.
400 type = object_store->object_type(); 409 type = object_store->object_type();
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
450 cls.set_name(name); 459 cls.set_name(name);
451 cls.set_script(impl_script); 460 cls.set_script(impl_script);
452 core_impl_lib.AddClass(cls); 461 core_impl_lib.AddClass(cls);
453 462
454 name = String::NewSymbol("FourByteString"); 463 name = String::NewSymbol("FourByteString");
455 cls = object_store->four_byte_string_class(); 464 cls = object_store->four_byte_string_class();
456 cls.set_name(name); 465 cls.set_name(name);
457 cls.set_script(impl_script); 466 cls.set_script(impl_script);
458 core_impl_lib.AddClass(cls); 467 core_impl_lib.AddClass(cls);
459 468
469 name = String::NewSymbol("ExternalOneByteString");
470 cls = object_store->external_one_byte_string_class();
471 cls.set_name(name);
472 cls.set_script(impl_script);
473 core_impl_lib.AddClass(cls);
474
475 name = String::NewSymbol("ExternalTwoByteString");
476 cls = object_store->external_two_byte_string_class();
477 cls.set_name(name);
478 cls.set_script(impl_script);
479 core_impl_lib.AddClass(cls);
480
481 name = String::NewSymbol("ExternalFourByteString");
482 cls = object_store->external_four_byte_string_class();
483 cls.set_name(name);
484 cls.set_script(impl_script);
485 core_impl_lib.AddClass(cls);
486
460 name = String::NewSymbol("Mint"); 487 name = String::NewSymbol("Mint");
461 cls = object_store->mint_class(); 488 cls = object_store->mint_class();
462 cls.set_name(name); 489 cls.set_name(name);
463 cls.set_script(impl_script); 490 cls.set_script(impl_script);
464 core_impl_lib.AddClass(cls); 491 core_impl_lib.AddClass(cls);
465 492
466 name = String::NewSymbol("Bigint"); 493 name = String::NewSymbol("Bigint");
467 cls = object_store->bigint_class(); 494 cls = object_store->bigint_class();
468 cls.set_name(name); 495 cls.set_name(name);
469 cls.set_script(impl_script); 496 cls.set_script(impl_script);
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after
625 652
626 cls = Class::New<OneByteString>(); 653 cls = Class::New<OneByteString>();
627 object_store->set_one_byte_string_class(cls); 654 object_store->set_one_byte_string_class(cls);
628 655
629 cls = Class::New<TwoByteString>(); 656 cls = Class::New<TwoByteString>();
630 object_store->set_two_byte_string_class(cls); 657 object_store->set_two_byte_string_class(cls);
631 658
632 cls = Class::New<FourByteString>(); 659 cls = Class::New<FourByteString>();
633 object_store->set_four_byte_string_class(cls); 660 object_store->set_four_byte_string_class(cls);
634 661
662 cls = Class::New<ExternalOneByteString>();
663 object_store->set_external_one_byte_string_class(cls);
664
665 cls = Class::New<ExternalTwoByteString>();
666 object_store->set_external_two_byte_string_class(cls);
667
668 cls = Class::New<ExternalFourByteString>();
669 object_store->set_external_four_byte_string_class(cls);
670
635 cls = Class::New<Bool>(); 671 cls = Class::New<Bool>();
636 object_store->set_bool_class(cls); 672 object_store->set_bool_class(cls);
637 673
638 cls = Class::New<UnhandledException>(); 674 cls = Class::New<UnhandledException>();
639 object_store->set_unhandled_exception_class(cls); 675 object_store->set_unhandled_exception_class(cls);
640 676
641 cls = Class::New<Stacktrace>(); 677 cls = Class::New<Stacktrace>();
642 object_store->set_stacktrace_class(cls); 678 object_store->set_stacktrace_class(cls);
643 679
644 cls = Class::New<JSRegExp>(); 680 cls = Class::New<JSRegExp>();
(...skipping 430 matching lines...) Expand 10 before | Expand all | Expand 10 after
1075 return object_store->double_class(); 1111 return object_store->double_class();
1076 case kOneByteString: 1112 case kOneByteString:
1077 ASSERT(object_store->one_byte_string_class() != Class::null()); 1113 ASSERT(object_store->one_byte_string_class() != Class::null());
1078 return object_store->one_byte_string_class(); 1114 return object_store->one_byte_string_class();
1079 case kTwoByteString: 1115 case kTwoByteString:
1080 ASSERT(object_store->two_byte_string_class() != Class::null()); 1116 ASSERT(object_store->two_byte_string_class() != Class::null());
1081 return object_store->two_byte_string_class(); 1117 return object_store->two_byte_string_class();
1082 case kFourByteString: 1118 case kFourByteString:
1083 ASSERT(object_store->four_byte_string_class() != Class::null()); 1119 ASSERT(object_store->four_byte_string_class() != Class::null());
1084 return object_store->four_byte_string_class(); 1120 return object_store->four_byte_string_class();
1121 case kExternalOneByteString:
1122 ASSERT(object_store->external_one_byte_string_class() != Class::null());
1123 return object_store->external_one_byte_string_class();
1124 case kExternalTwoByteString:
1125 ASSERT(object_store->external_two_byte_string_class() != Class::null());
1126 return object_store->external_two_byte_string_class();
1127 case kExternalFourByteString:
1128 ASSERT(object_store->external_four_byte_string_class() != Class::null());
1129 return object_store->external_four_byte_string_class();
1085 case kBool: 1130 case kBool:
1086 ASSERT(object_store->bool_class() != Class::null()); 1131 ASSERT(object_store->bool_class() != Class::null());
1087 return object_store->bool_class(); 1132 return object_store->bool_class();
1088 case kArray: 1133 case kArray:
1089 ASSERT(object_store->array_class() != Class::null()); 1134 ASSERT(object_store->array_class() != Class::null());
1090 return object_store->array_class(); 1135 return object_store->array_class();
1091 case kImmutableArray: 1136 case kImmutableArray:
1092 ASSERT(object_store->immutable_array_class() != Class::null()); 1137 ASSERT(object_store->immutable_array_class() != Class::null());
1093 return object_store->immutable_array_class(); 1138 return object_store->immutable_array_class();
1094 case kStacktrace: 1139 case kStacktrace:
(...skipping 4204 matching lines...) Expand 10 before | Expand all | Expand 10 after
5299 } 5344 }
5300 5345
5301 5346
5302 int32_t String::CharAt(intptr_t index) const { 5347 int32_t String::CharAt(intptr_t index) const {
5303 // String is an abstract class. 5348 // String is an abstract class.
5304 UNREACHABLE(); 5349 UNREACHABLE();
5305 return 0; 5350 return 0;
5306 } 5351 }
5307 5352
5308 5353
5354 intptr_t String::CharSize() const {
5355 // String is an abstract class.
5356 UNREACHABLE();
5357 return 0;
5358 }
5359
5360
5309 bool String::Equals(const Instance& other) const { 5361 bool String::Equals(const Instance& other) const {
5310 if (this->raw() == other.raw()) { 5362 if (this->raw() == other.raw()) {
5311 // Both handles point to the same raw instance. 5363 // Both handles point to the same raw instance.
5312 return true; 5364 return true;
5313 } 5365 }
5314 5366
5315 if (!other.IsString() || other.IsNull()) { 5367 if (!other.IsString() || other.IsNull()) {
5316 return false; 5368 return false;
5317 } 5369 }
5318 5370
(...skipping 243 matching lines...) Expand 10 before | Expand all | Expand 10 after
5562 } 5614 }
5563 return FourByteString::New(characters, len, space); 5615 return FourByteString::New(characters, len, space);
5564 } 5616 }
5565 5617
5566 5618
5567 RawString* String::New(const String& str, Heap::Space space) { 5619 RawString* String::New(const String& str, Heap::Space space) {
5568 // Currently this just creates a copy of the string in the correct space. 5620 // Currently this just creates a copy of the string in the correct space.
5569 // Once we have external string support, this will also create a heap copy of 5621 // Once we have external string support, this will also create a heap copy of
5570 // the string if necessary. Some optimizations are possible, such as not 5622 // the string if necessary. Some optimizations are possible, such as not
5571 // copying internal strings into the same space. 5623 // copying internal strings into the same space.
5572 if (str.IsOneByteString()) { 5624 intptr_t len = str.Length();
5573 OneByteString& one_byte_str = OneByteString::Handle(); 5625 String& result = String::Handle();
5574 one_byte_str ^= str.raw(); 5626 intptr_t char_size = str.CharSize();
5575 return OneByteString::New(one_byte_str, space); 5627 if (char_size == kOneByteChar) {
5576 } else if (str.IsTwoByteString()) { 5628 result ^= OneByteString::New(len, space);
5577 TwoByteString& two_byte_str = TwoByteString::Handle(); 5629 } else if (char_size == kTwoByteChar) {
5578 two_byte_str ^= str.raw(); 5630 result ^= TwoByteString::New(len, space);
5579 return TwoByteString::New(two_byte_str, space); 5631 } else {
5632 ASSERT(char_size == kFourByteChar);
5633 result ^= FourByteString::New(len, space);
5580 } 5634 }
5581 ASSERT(str.IsFourByteString()); 5635 String::Copy(result, 0, str, 0, len);
5582 FourByteString& four_byte_str = FourByteString::Handle(); 5636 return result.raw();
5583 four_byte_str ^= str.raw();
5584 return FourByteString::New(four_byte_str, space);
5585 } 5637 }
5586 5638
5587 5639
5640 RawString* String::NewExternal(const uint8_t* characters,
5641 intptr_t len,
5642 void* peer,
5643 Heap::Space space) {
5644 return ExternalOneByteString::New(characters, len, peer, space);
5645 }
5646
5647
5648 RawString* String::NewExternal(const uint16_t* characters,
5649 intptr_t len,
5650 void* peer,
5651 Heap::Space space) {
5652 return ExternalTwoByteString::New(characters, len, peer, space);
5653 }
5654
5655
5656 RawString* String::NewExternal(const uint32_t* characters,
5657 intptr_t len,
5658 void* peer,
5659 Heap::Space space) {
5660 return ExternalFourByteString::New(characters, len, peer, space);
5661 }
5662
5663
5588 void String::Copy(const String& dst, intptr_t dst_offset, 5664 void String::Copy(const String& dst, intptr_t dst_offset,
5589 const uint8_t* characters, 5665 const uint8_t* characters,
5590 intptr_t len) { 5666 intptr_t len) {
5591 ASSERT(dst_offset >= 0); 5667 ASSERT(dst_offset >= 0);
5592 ASSERT(len >= 0); 5668 ASSERT(len >= 0);
5593 ASSERT(len <= (dst.Length() - dst_offset)); 5669 ASSERT(len <= (dst.Length() - dst_offset));
5594 if (dst.IsOneByteString()) { 5670 if (dst.IsOneByteString()) {
5595 OneByteString& onestr = OneByteString::Handle(); 5671 OneByteString& onestr = OneByteString::Handle();
5596 onestr ^= dst.raw(); 5672 onestr ^= dst.raw();
5597 NoGCScope no_gc; 5673 NoGCScope no_gc;
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after
5686 5762
5687 void String::Copy(const String& dst, intptr_t dst_offset, 5763 void String::Copy(const String& dst, intptr_t dst_offset,
5688 const String& src, intptr_t src_offset, 5764 const String& src, intptr_t src_offset,
5689 intptr_t len) { 5765 intptr_t len) {
5690 ASSERT(dst_offset >= 0); 5766 ASSERT(dst_offset >= 0);
5691 ASSERT(src_offset >= 0); 5767 ASSERT(src_offset >= 0);
5692 ASSERT(len >= 0); 5768 ASSERT(len >= 0);
5693 ASSERT(len <= (dst.Length() - dst_offset)); 5769 ASSERT(len <= (dst.Length() - dst_offset));
5694 ASSERT(len <= (src.Length() - src_offset)); 5770 ASSERT(len <= (src.Length() - src_offset));
5695 if (len > 0) { 5771 if (len > 0) {
5696 if (src.IsOneByteString()) { 5772 intptr_t char_size = src.CharSize();
5697 OneByteString& onestr = OneByteString::Handle(); 5773 if (char_size == kOneByteChar) {
5698 onestr ^= src.raw(); 5774 if (src.IsOneByteString()) {
5699 NoGCScope no_gc; 5775 OneByteString& onestr = OneByteString::Handle();
5700 String::Copy(dst, dst_offset, onestr.CharAddr(0) + src_offset, len); 5776 onestr ^= src.raw();
5701 } else if (src.IsTwoByteString()) { 5777 NoGCScope no_gc;
5702 TwoByteString& twostr = TwoByteString::Handle(); 5778 String::Copy(dst, dst_offset, onestr.CharAddr(0) + src_offset, len);
5703 twostr ^= src.raw(); 5779 } else {
5704 NoGCScope no_gc; 5780 ASSERT(src.IsExternalOneByteString());
5705 String::Copy(dst, dst_offset, twostr.CharAddr(0) + src_offset, len); 5781 ExternalOneByteString& onestr = ExternalOneByteString::Handle();
5782 onestr ^= src.raw();
5783 NoGCScope no_gc;
5784 String::Copy(dst, dst_offset, onestr.CharAddr(0) + src_offset, len);
5785 }
5786 } else if (char_size == kTwoByteChar) {
5787 if (src.IsTwoByteString()) {
5788 TwoByteString& twostr = TwoByteString::Handle();
5789 twostr ^= src.raw();
5790 NoGCScope no_gc;
5791 String::Copy(dst, dst_offset, twostr.CharAddr(0) + src_offset, len);
5792 } else {
5793 ASSERT(src.IsExternalTwoByteString());
5794 ExternalTwoByteString& twostr = ExternalTwoByteString::Handle();
5795 twostr ^= src.raw();
5796 NoGCScope no_gc;
5797 String::Copy(dst, dst_offset, twostr.CharAddr(0) + src_offset, len);
5798 }
5706 } else { 5799 } else {
5707 ASSERT(src.IsFourByteString()); 5800 ASSERT(char_size == kFourByteChar);
5708 FourByteString& fourstr = FourByteString::Handle(); 5801 if (src.IsFourByteString()) {
5709 fourstr ^= src.raw(); 5802 FourByteString& fourstr = FourByteString::Handle();
5710 NoGCScope no_gc; 5803 fourstr ^= src.raw();
5711 String::Copy(dst, dst_offset, fourstr.CharAddr(0) + src_offset, len); 5804 NoGCScope no_gc;
5805 String::Copy(dst, dst_offset, fourstr.CharAddr(0) + src_offset, len);
5806 } else {
5807 ASSERT(src.IsExternalFourByteString());
5808 ExternalFourByteString& fourstr = ExternalFourByteString::Handle();
5809 fourstr ^= src.raw();
5810 NoGCScope no_gc;
5811 String::Copy(dst, dst_offset, fourstr.CharAddr(0) + src_offset, len);
5812 }
5712 } 5813 }
5713 } 5814 }
5714 } 5815 }
5715 5816
5716 5817
5717 static void GrowSymbolTable(const Array& symbol_table, intptr_t table_size) { 5818 static void GrowSymbolTable(const Array& symbol_table, intptr_t table_size) {
5718 // TODO(iposva): Avoid exponential growth. 5819 // TODO(iposva): Avoid exponential growth.
5719 intptr_t new_table_size = table_size * 2; 5820 intptr_t new_table_size = table_size * 2;
5720 Array& new_symbol_table = Array::Handle(Array::New(new_table_size + 1)); 5821 Array& new_symbol_table = Array::Handle(Array::New(new_table_size + 1));
5721 // Copy all elements from the original symbol table to the newly allocated 5822 // Copy all elements from the original symbol table to the newly allocated
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after
5863 } 5964 }
5864 ASSERT(symbol.IsSymbol()); 5965 ASSERT(symbol.IsSymbol());
5865 return symbol.raw(); 5966 return symbol.raw();
5866 } 5967 }
5867 5968
5868 5969
5869 RawString* String::Concat(const String& str1, 5970 RawString* String::Concat(const String& str1,
5870 const String& str2, 5971 const String& str2,
5871 Heap::Space space) { 5972 Heap::Space space) {
5872 ASSERT(!str1.IsNull() && !str2.IsNull()); 5973 ASSERT(!str1.IsNull() && !str2.IsNull());
5873 if (str1.IsFourByteString() || str2.IsFourByteString()) { 5974 intptr_t char_size = Utils::Maximum(str1.CharSize(), str2.CharSize());
5975 if (char_size == kFourByteChar) {
5874 return FourByteString::Concat(str1, str2, space); 5976 return FourByteString::Concat(str1, str2, space);
5875 } 5977 }
5876 if (str1.IsTwoByteString() || str2.IsTwoByteString()) { 5978 if (char_size == kTwoByteChar) {
5877 return TwoByteString::Concat(str1, str2, space); 5979 return TwoByteString::Concat(str1, str2, space);
5878 } 5980 }
5879 ASSERT(str1.IsOneByteString() && str2.IsOneByteString());
5880 return OneByteString::Concat(str1, str2, space); 5981 return OneByteString::Concat(str1, str2, space);
5881 } 5982 }
5882 5983
5883 5984
5884 RawString* String::ConcatAll(const Array& strings, 5985 RawString* String::ConcatAll(const Array& strings,
5885 Heap::Space space) { 5986 Heap::Space space) {
5886 ASSERT(!strings.IsNull()); 5987 ASSERT(!strings.IsNull());
5887 bool is_one_byte_string = true;
5888 bool is_two_byte_string = true;
5889 intptr_t result_len = 0; 5988 intptr_t result_len = 0;
5890 intptr_t strings_len = strings.Length(); 5989 intptr_t strings_len = strings.Length();
5891 String& str = String::Handle(); 5990 String& str = String::Handle();
5991 intptr_t char_size = kOneByteChar;
5892 for (intptr_t i = 0; i < strings_len; i++) { 5992 for (intptr_t i = 0; i < strings_len; i++) {
5893 str ^= strings.At(i); 5993 str ^= strings.At(i);
5894 result_len += str.Length(); 5994 result_len += str.Length();
5895 if (str.IsFourByteString()) { 5995 char_size = Utils::Maximum(char_size, str.CharSize());
5896 is_one_byte_string = false;
5897 is_two_byte_string = false;
5898 } else if (str.IsTwoByteString()) {
5899 is_one_byte_string = false;
5900 }
5901 } 5996 }
5902 if (is_one_byte_string) { 5997 if (char_size == kOneByteChar) {
5903 return OneByteString::ConcatAll(strings, result_len, space); 5998 return OneByteString::ConcatAll(strings, result_len, space);
5904 } else if (is_two_byte_string) { 5999 } else if (char_size == kTwoByteChar) {
5905 return TwoByteString::ConcatAll(strings, result_len, space); 6000 return TwoByteString::ConcatAll(strings, result_len, space);
5906 } 6001 }
6002 ASSERT(char_size == kFourByteChar);
5907 return FourByteString::ConcatAll(strings, result_len, space); 6003 return FourByteString::ConcatAll(strings, result_len, space);
5908 } 6004 }
5909 6005
5910 6006
5911 RawString* String::SubString(const String& str, 6007 RawString* String::SubString(const String& str,
5912 intptr_t begin_index, 6008 intptr_t begin_index,
5913 Heap::Space space) { 6009 Heap::Space space) {
5914 ASSERT(!str.IsNull()); 6010 ASSERT(!str.IsNull());
5915 if (begin_index >= str.Length()) { 6011 if (begin_index >= str.Length()) {
5916 return String::null(); 6012 return String::null();
5917 } 6013 }
5918 return String::SubString(str, begin_index, (str.Length() - begin_index)); 6014 return String::SubString(str, begin_index, (str.Length() - begin_index));
5919 } 6015 }
5920 6016
5921 6017
5922 RawString* String::SubString(const String& str, 6018 RawString* String::SubString(const String& str,
5923 intptr_t begin_index, 6019 intptr_t begin_index,
5924 intptr_t length, 6020 intptr_t length,
5925 Heap::Space space) { 6021 Heap::Space space) {
5926 ASSERT(!str.IsNull()); 6022 ASSERT(!str.IsNull());
5927 ASSERT(begin_index >= 0); 6023 ASSERT(begin_index >= 0);
5928 ASSERT(length >= 0); 6024 ASSERT(length >= 0);
5929 if (begin_index >= str.Length()) { 6025 if (begin_index >= str.Length()) {
5930 return String::null(); 6026 return String::null();
5931 } 6027 }
5932 if (str.IsOneByteString()) { 6028 String& result = String::Handle();
5933 OneByteString& obstr = OneByteString::Handle(); 6029 bool is_one_byte_string = true;
5934 obstr ^= str.raw(); 6030 bool is_two_byte_string = true;
5935 return OneByteString::SubString(obstr, begin_index, length, space); 6031 intptr_t char_size = str.CharSize();
5936 } else if (str.IsTwoByteString()) { 6032 if (char_size == kTwoByteChar) {
5937 TwoByteString& twostr = TwoByteString::Handle(); 6033 for (intptr_t i = begin_index; i < begin_index + length; ++i) {
5938 twostr ^= str.raw(); 6034 if (str.CharAt(i) > 0xFF) {
5939 return TwoByteString::SubString(twostr, begin_index, length, space); 6035 is_one_byte_string = false;
6036 break;
6037 }
6038 }
6039 } else if (char_size == kFourByteChar) {
6040 for (intptr_t i = begin_index; i < begin_index + length; ++i) {
6041 if (str.CharAt(i) > 0xFFFF) {
6042 is_one_byte_string = false;
6043 is_two_byte_string = false;
6044 break;
6045 } else if (str.CharAt(i) > 0xFF) {
6046 is_one_byte_string = false;
6047 }
6048 }
5940 } 6049 }
5941 ASSERT(str.IsFourByteString()); 6050 if (is_one_byte_string) {
5942 FourByteString& fourstr = FourByteString::Handle(); 6051 result ^= OneByteString::New(length, space);
5943 fourstr ^= str.raw(); 6052 } else if (is_two_byte_string) {
5944 return FourByteString::SubString(fourstr, begin_index, length, space); 6053 result ^= TwoByteString::New(length, space);
6054 } else {
6055 result ^= FourByteString::New(length, space);
6056 }
6057 String::Copy(result, 0, str, begin_index, length);
6058 return result.raw();
5945 } 6059 }
5946 6060
5947 6061
5948 const char* String::ToCString() const { 6062 const char* String::ToCString() const {
5949 intptr_t len = Utf8::Length(*this); 6063 intptr_t len = Utf8::Length(*this);
5950 Zone* zone = Isolate::Current()->current_zone(); 6064 Zone* zone = Isolate::Current()->current_zone();
5951 char* result = reinterpret_cast<char*>(zone->Allocate(len + 1)); 6065 char* result = reinterpret_cast<char*>(zone->Allocate(len + 1));
5952 Utf8::Encode(*this, result, len); 6066 Utf8::Encode(*this, result, len);
5953 result[len] = 0; 6067 result[len] = 0;
5954 return result; 6068 return result;
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after
6082 for (intptr_t i = 0; i < strings_len; i++) { 6196 for (intptr_t i = 0; i < strings_len; i++) {
6083 str ^= strings.At(i); 6197 str ^= strings.At(i);
6084 intptr_t str_len = str.Length(); 6198 intptr_t str_len = str.Length();
6085 String::Copy(result, pos, str, 0, str_len); 6199 String::Copy(result, pos, str, 0, str_len);
6086 pos += str_len; 6200 pos += str_len;
6087 } 6201 }
6088 return result.raw(); 6202 return result.raw();
6089 } 6203 }
6090 6204
6091 6205
6092 RawString* OneByteString::SubString(const OneByteString& str,
6093 intptr_t begin_index,
6094 intptr_t length,
6095 Heap::Space space) {
6096 ASSERT(!str.IsNull());
6097 ASSERT(begin_index < str.Length());
6098 OneByteString& result = OneByteString::Handle();
6099 if (length <= (str.Length() - begin_index)) {
6100 result ^= OneByteString::New(length, space);
6101 String::Copy(result, 0, str, begin_index, length);
6102 }
6103 // TODO(5418937): return a non-null object on error.
6104 return result.raw();
6105 }
6106
6107
6108 RawOneByteString* OneByteString::Transform(int32_t (*mapping)(int32_t ch), 6206 RawOneByteString* OneByteString::Transform(int32_t (*mapping)(int32_t ch),
6109 const String& str, 6207 const String& str,
6110 Heap::Space space) { 6208 Heap::Space space) {
6111 ASSERT(!str.IsNull()); 6209 ASSERT(!str.IsNull());
6112 intptr_t len = str.Length(); 6210 intptr_t len = str.Length();
6113 const OneByteString& result = 6211 const OneByteString& result =
6114 OneByteString::Handle(OneByteString::New(len, space)); 6212 OneByteString::Handle(OneByteString::New(len, space));
6115 for (intptr_t i = 0; i < len; ++i) { 6213 for (intptr_t i = 0; i < len; ++i) {
6116 int32_t ch = mapping(str.CharAt(i)); 6214 int32_t ch = mapping(str.CharAt(i));
6117 ASSERT(ch >= 0 && ch <= 0xFF); 6215 ASSERT(ch >= 0 && ch <= 0xFF);
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
6201 for (intptr_t i = 0; i < strings_len; i++) { 6299 for (intptr_t i = 0; i < strings_len; i++) {
6202 str ^= strings.At(i); 6300 str ^= strings.At(i);
6203 intptr_t str_len = str.Length(); 6301 intptr_t str_len = str.Length();
6204 String::Copy(result, pos, str, 0, str_len); 6302 String::Copy(result, pos, str, 0, str_len);
6205 pos += str_len; 6303 pos += str_len;
6206 } 6304 }
6207 return result.raw(); 6305 return result.raw();
6208 } 6306 }
6209 6307
6210 6308
6211 RawString* TwoByteString::SubString(const TwoByteString& str,
6212 intptr_t begin_index,
6213 intptr_t length,
6214 Heap::Space space) {
6215 ASSERT(!str.IsNull());
6216 ASSERT(begin_index < str.Length());
6217 String& result = String::Handle();
6218 if (length <= (str.Length() - begin_index)) {
6219 bool is_one_byte_string = true;
6220 for (intptr_t i = begin_index; i < begin_index + length; ++i) {
6221 if (str.CharAt(i) > 0xFF) {
6222 is_one_byte_string = false;
6223 break;
6224 }
6225 }
6226 if (is_one_byte_string) {
6227 result ^= OneByteString::New(length, space);
6228 } else {
6229 result ^= TwoByteString::New(length, space);
6230 }
6231 String::Copy(result, 0, str, begin_index, length);
6232 }
6233 // TODO(5418937): return a non-null object on error.
6234 return result.raw();
6235 }
6236
6237
6238 RawTwoByteString* TwoByteString::Transform(int32_t (*mapping)(int32_t ch), 6309 RawTwoByteString* TwoByteString::Transform(int32_t (*mapping)(int32_t ch),
6239 const String& str, 6310 const String& str,
6240 Heap::Space space) { 6311 Heap::Space space) {
6241 ASSERT(!str.IsNull()); 6312 ASSERT(!str.IsNull());
6242 intptr_t len = str.Length(); 6313 intptr_t len = str.Length();
6243 const TwoByteString& result = 6314 const TwoByteString& result =
6244 TwoByteString::Handle(TwoByteString::New(len, space)); 6315 TwoByteString::Handle(TwoByteString::New(len, space));
6245 for (intptr_t i = 0; i < len; ++i) { 6316 for (intptr_t i = 0; i < len; ++i) {
6246 int32_t ch = mapping(str.CharAt(i)); 6317 int32_t ch = mapping(str.CharAt(i));
6247 ASSERT(ch >= 0 && ch <= 0xFFFF); 6318 ASSERT(ch >= 0 && ch <= 0xFFFF);
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after
6319 str ^= strings.At(i); 6390 str ^= strings.At(i);
6320 intptr_t str_len = str.Length(); 6391 intptr_t str_len = str.Length();
6321 String::Copy(result, pos, str, 0, str_len); 6392 String::Copy(result, pos, str, 0, str_len);
6322 pos += str_len; 6393 pos += str_len;
6323 } 6394 }
6324 } 6395 }
6325 return result.raw(); 6396 return result.raw();
6326 } 6397 }
6327 6398
6328 6399
6329 RawString* FourByteString::SubString(const FourByteString& str,
6330 intptr_t begin_index,
6331 intptr_t length,
6332 Heap::Space space) {
6333 ASSERT(!str.IsNull());
6334 ASSERT(begin_index < str.Length());
6335 String& result = String::Handle();
6336 if (length <= (str.Length() - begin_index)) {
6337 bool is_one_byte_string = true;
6338 bool is_two_byte_string = true;
6339 for (intptr_t i = begin_index; i < begin_index + length; ++i) {
6340 if (str.CharAt(i) > 0xFFFF) {
6341 is_one_byte_string = false;
6342 is_two_byte_string = false;
6343 break;
6344 } else if (str.CharAt(i) > 0xFF) {
6345 is_one_byte_string = false;
6346 }
6347 }
6348 if (is_one_byte_string) {
6349 result ^= OneByteString::New(length, space);
6350 } else if (is_two_byte_string) {
6351 result ^= TwoByteString::New(length, space);
6352 } else {
6353 result ^= FourByteString::New(length, space);
6354 }
6355 String::Copy(result, 0, str, begin_index, length);
6356 }
6357 // TODO(5418937): return a non-null object on error.
6358 return result.raw();
6359 }
6360
6361
6362 RawFourByteString* FourByteString::Transform(int32_t (*mapping)(int32_t ch), 6400 RawFourByteString* FourByteString::Transform(int32_t (*mapping)(int32_t ch),
6363 const String& str, 6401 const String& str,
6364 Heap::Space space) { 6402 Heap::Space space) {
6365 ASSERT(!str.IsNull()); 6403 ASSERT(!str.IsNull());
6366 intptr_t len = str.Length(); 6404 intptr_t len = str.Length();
6367 const FourByteString& result = 6405 const FourByteString& result =
6368 FourByteString::Handle(FourByteString::New(len, space)); 6406 FourByteString::Handle(FourByteString::New(len, space));
6369 for (intptr_t i = 0; i < len; ++i) { 6407 for (intptr_t i = 0; i < len; ++i) {
6370 int32_t ch = mapping(str.CharAt(i)); 6408 int32_t ch = mapping(str.CharAt(i));
6371 ASSERT(ch >= 0 && ch <= 0x10FFFF); 6409 ASSERT(ch >= 0 && ch <= 0x10FFFF);
6372 *result.CharAddr(i) = ch; 6410 *result.CharAddr(i) = ch;
6373 } 6411 }
6374 return result.raw(); 6412 return result.raw();
6375 } 6413 }
6376 6414
6377 6415
6378 const char* FourByteString::ToCString() const { 6416 const char* FourByteString::ToCString() const {
6379 return String::ToCString(); 6417 return String::ToCString();
6380 } 6418 }
6381 6419
6382 6420
6421 RawExternalOneByteString* ExternalOneByteString::New(const uint8_t* data,
6422 intptr_t len,
6423 void* peer,
6424 Heap::Space space) {
6425 Isolate* isolate = Isolate::Current();
6426
6427 const Class& cls =
6428 Class::Handle(isolate->object_store()->external_one_byte_string_class());
6429 ExternalOneByteString& result = ExternalOneByteString::Handle();
6430 {
6431 RawObject* raw = Object::Allocate(cls,
6432 ExternalOneByteString::InstanceSize(),
6433 space);
6434 NoGCScope no_gc;
6435 result ^= raw;
6436 result.SetLength(len);
6437 result.SetHash(0);
6438 result.SetData(data);
6439 result.SetPeer(peer);
6440 }
6441 return result.raw();
6442 }
6443
6444
6445 const char* ExternalOneByteString::ToCString() const {
6446 return String::ToCString();
6447 }
6448
6449
6450 RawExternalTwoByteString* ExternalTwoByteString::New(const uint16_t* data,
6451 intptr_t len,
6452 void* peer,
6453 Heap::Space space) {
6454 Isolate* isolate = Isolate::Current();
6455
6456 const Class& cls =
6457 Class::Handle(isolate->object_store()->external_two_byte_string_class());
6458 ExternalTwoByteString& result = ExternalTwoByteString::Handle();
6459 {
6460 RawObject* raw = Object::Allocate(cls,
6461 ExternalTwoByteString::InstanceSize(),
6462 space);
6463 NoGCScope no_gc;
6464 result ^= raw;
6465 result.SetLength(len);
6466 result.SetHash(0);
6467 result.SetData(data);
6468 result.SetPeer(peer);
6469 }
6470 return result.raw();
6471 }
6472
6473
6474 const char* ExternalTwoByteString::ToCString() const {
6475 return String::ToCString();
6476 }
6477
6478
6479 RawExternalFourByteString* ExternalFourByteString::New(const uint32_t* data,
6480 intptr_t len,
6481 void* peer,
6482 Heap::Space space) {
6483 Isolate* isolate = Isolate::Current();
6484
6485 const Class& cls =
6486 Class::Handle(isolate->object_store()->external_four_byte_string_class());
6487 ExternalFourByteString& result = ExternalFourByteString::Handle();
6488 {
6489 RawObject* raw = Object::Allocate(cls,
6490 ExternalFourByteString::InstanceSize(),
6491 space);
6492 NoGCScope no_gc;
6493 result ^= raw;
6494 result.SetLength(len);
6495 result.SetHash(0);
6496 result.SetData(data);
6497 result.SetPeer(peer);
6498 }
6499 return result.raw();
6500 }
6501
6502
6503 const char* ExternalFourByteString::ToCString() const {
6504 return String::ToCString();
6505 }
6506
6507
6383 RawBool* Bool::True() { 6508 RawBool* Bool::True() {
6384 return Isolate::Current()->object_store()->true_value(); 6509 return Isolate::Current()->object_store()->true_value();
6385 } 6510 }
6386 6511
6387 6512
6388 RawBool* Bool::False() { 6513 RawBool* Bool::False() {
6389 return Isolate::Current()->object_store()->false_value(); 6514 return Isolate::Current()->object_store()->false_value();
6390 } 6515 }
6391 6516
6392 6517
(...skipping 413 matching lines...) Expand 10 before | Expand all | Expand 10 after
6806 const String& str = String::Handle(pattern()); 6931 const String& str = String::Handle(pattern());
6807 const char* format = "JSRegExp: pattern=%s flags=%s"; 6932 const char* format = "JSRegExp: pattern=%s flags=%s";
6808 intptr_t len = OS::SNPrint(NULL, 0, format, str.ToCString(), Flags()); 6933 intptr_t len = OS::SNPrint(NULL, 0, format, str.ToCString(), Flags());
6809 char* chars = reinterpret_cast<char*>( 6934 char* chars = reinterpret_cast<char*>(
6810 Isolate::Current()->current_zone()->Allocate(len + 1)); 6935 Isolate::Current()->current_zone()->Allocate(len + 1));
6811 OS::SNPrint(chars, (len + 1), format, str.ToCString(), Flags()); 6936 OS::SNPrint(chars, (len + 1), format, str.ToCString(), Flags());
6812 return chars; 6937 return chars;
6813 } 6938 }
6814 6939
6815 } // namespace dart 6940 } // namespace dart
OLDNEW
« runtime/include/dart_api.h ('K') | « runtime/vm/object.h ('k') | runtime/vm/object_store.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698