@@ -17,6 +17,12 @@ inline int32_t LLV8::LoadValue<int32_t>(int64_t addr, Error& err) {
1717 return LoadUnsigned (addr, 4 , err);
1818}
1919
20+ template <>
21+ inline CheckedType<int32_t > LLV8::LoadValue<CheckedType<int32_t >>(
22+ int64_t addr) {
23+ return LoadUnsigned<int32_t >(addr, 4 );
24+ }
25+
2026template <class T >
2127inline T LLV8::LoadValue (int64_t addr, Error& err) {
2228 int64_t ptr;
@@ -363,7 +369,23 @@ inline int64_t String::Encoding(Error& err) {
363369 return type & v8 ()->string ()->kEncodingMask ;
364370}
365371
366- ACCESSOR (String, Length, string()->kLengthOffset , Smi)
372+ inline CheckedType<int32_t > String::Length (Error& err) {
373+ RETURN_IF_INVALID ((*this ), CheckedType<int32_t >());
374+
375+ if (v8 ()->string ()->kLengthIsSmi ) {
376+ Smi len = LoadFieldValue<Smi>(v8 ()->string ()->kLengthOffset , err);
377+ RETURN_IF_INVALID (len, CheckedType<int32_t >());
378+
379+ return CheckedType<int32_t >(len.GetValue ());
380+ }
381+
382+ CheckedType<int32_t > len = v8 ()->LoadValue <CheckedType<int32_t >>(
383+ LeaField (v8 ()->string ()->kLengthOffset ));
384+ RETURN_IF_INVALID (len, CheckedType<int32_t >());
385+
386+ return len;
387+ }
388+
367389
368390ACCESSOR (Script, Name, script()->kNameOffset , String)
369391ACCESSOR (Script, LineOffset, script()->kLineOffsetOffset , Smi)
@@ -610,16 +632,16 @@ inline int64_t FixedTypedArrayBase::GetExternal(Error& err) {
610632
611633inline std::string OneByteString::ToString (Error& err) {
612634 int64_t chars = LeaField (v8 ()->one_byte_string ()->kCharsOffset );
613- Smi len = Length (err);
614- if (err. Fail ()) return std::string ();
615- return v8 ()->LoadString (chars, len. GetValue () , err);
635+ CheckedType< int32_t > len = Length (err);
636+ RETURN_IF_INVALID (len, std::string () );
637+ return v8 ()->LoadString (chars, * len, err);
616638}
617639
618640inline std::string TwoByteString::ToString (Error& err) {
619641 int64_t chars = LeaField (v8 ()->two_byte_string ()->kCharsOffset );
620- Smi len = Length (err);
621- if (err. Fail ()) return std::string ();
622- return v8 ()->LoadTwoByteString (chars, len. GetValue () , err);
642+ CheckedType< int32_t > len = Length (err);
643+ RETURN_IF_INVALID (len, std::string () );
644+ return v8 ()->LoadTwoByteString (chars, * len, err);
623645}
624646
625647inline std::string ConsString::ToString (Error& err) {
@@ -653,24 +675,23 @@ inline std::string SlicedString::ToString(Error& err) {
653675 Smi offset = Offset (err);
654676 if (err.Fail ()) return std::string ();
655677
656- Smi length = Length (err);
657- if (err. Fail ()) return std::string ();
678+ CheckedType< int32_t > length = Length (err);
679+ RETURN_IF_INVALID (length, std::string () );
658680
659681 std::string tmp = parent.ToString (err);
660682 if (err.Fail ()) return std::string ();
661683
662684 int64_t off = offset.GetValue ();
663- int64_t len = length.GetValue ();
664685 int64_t tmp_size = tmp.size ();
665- if (off > tmp_size || len > tmp_size) {
686+ if (off > tmp_size || *length > tmp_size) {
666687 err = Error::Failure (" Failed to display sliced string 0x%016" PRIx64
667- " (offset = 0x%016" PRIx64 " , length = 0x%016 " PRIx64
668- " ) from parent string 0x%016" PRIx64
688+ " (offset = 0x%016" PRIx64
689+ " , length = %d ) from parent string 0x%016" PRIx64
669690 " (length = 0x%016" PRIx64 " )" ,
670- raw (), off, len , parent.raw (), tmp_size);
691+ raw (), off, *length , parent.raw (), tmp_size);
671692 return std::string (err.GetMessage ());
672693 }
673- return tmp.substr (offset.GetValue (), length. GetValue () );
694+ return tmp.substr (offset.GetValue (), * length);
674695}
675696
676697inline std::string ThinString::ToString (Error& err) {
0 commit comments