| OLD | NEW |
| (Empty) |
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #include "v8_binding.h" | |
| 6 | |
| 7 #include "AtomicString.h" | |
| 8 #include "CString.h" | |
| 9 #include "MathExtras.h" | |
| 10 #include "PlatformString.h" | |
| 11 #include "StringBuffer.h" | |
| 12 | |
| 13 #include <v8.h> | |
| 14 | |
| 15 namespace WebCore { | |
| 16 | |
| 17 // WebCoreStringResource is a helper class for v8ExternalString. It is used | |
| 18 // to manage the life-cycle of the underlying buffer of the external string. | |
| 19 class WebCoreStringResource: public v8::String::ExternalStringResource { | |
| 20 public: | |
| 21 explicit WebCoreStringResource(const String& str) | |
| 22 : impl_(str.impl()) { } | |
| 23 | |
| 24 virtual ~WebCoreStringResource() {} | |
| 25 | |
| 26 const uint16_t* data() const { | |
| 27 return reinterpret_cast<const uint16_t*>(impl_.characters()); | |
| 28 } | |
| 29 | |
| 30 size_t length() const { return impl_.length(); } | |
| 31 | |
| 32 String webcore_string() { return impl_; } | |
| 33 | |
| 34 private: | |
| 35 // A shallow copy of the string. | |
| 36 // Keeps the string buffer alive until the V8 engine garbage collects it. | |
| 37 String impl_; | |
| 38 }; | |
| 39 | |
| 40 | |
| 41 String v8StringToWebCoreString( | |
| 42 v8::Handle<v8::String> v8_str, bool externalize) { | |
| 43 WebCoreStringResource* str_resource = static_cast<WebCoreStringResource*>( | |
| 44 v8_str->GetExternalStringResource()); | |
| 45 if (str_resource) { | |
| 46 return str_resource->webcore_string(); | |
| 47 } | |
| 48 | |
| 49 int length = v8_str->Length(); | |
| 50 if (length == 0) { | |
| 51 // Avoid trying to morph empty strings, as they do not have enough room to | |
| 52 // contain the external reference. | |
| 53 return StringImpl::empty(); | |
| 54 } | |
| 55 | |
| 56 UChar* buffer; | |
| 57 String result = String::createUninitialized(length, buffer); | |
| 58 v8_str->Write(reinterpret_cast<uint16_t*>(buffer), 0, length); | |
| 59 | |
| 60 if (externalize) { | |
| 61 WebCoreStringResource* resource = new WebCoreStringResource(result); | |
| 62 if (!v8_str->MakeExternal(resource)) { | |
| 63 // In case of a failure delete the external resource as it was not used. | |
| 64 delete resource; | |
| 65 } | |
| 66 } | |
| 67 return result; | |
| 68 } | |
| 69 | |
| 70 | |
| 71 String v8ValueToWebCoreString(v8::Handle<v8::Value> obj) { | |
| 72 if (obj->IsString()) { | |
| 73 v8::Handle<v8::String> v8_str = v8::Handle<v8::String>::Cast(obj); | |
| 74 String webCoreString = v8StringToWebCoreString(v8_str, true); | |
| 75 return webCoreString; | |
| 76 } else if (obj->IsInt32()) { | |
| 77 int value = obj->Int32Value(); | |
| 78 // Most numbers used are <= 100. Even if they aren't used | |
| 79 // there's very little in using the space. | |
| 80 const int kLowNumbers = 100; | |
| 81 static AtomicString lowNumbers[kLowNumbers + 1]; | |
| 82 String webCoreString; | |
| 83 if (0 <= value && value <= kLowNumbers) { | |
| 84 webCoreString = lowNumbers[value]; | |
| 85 if (!webCoreString) { | |
| 86 AtomicString valueString = AtomicString(String::number(value)); | |
| 87 lowNumbers[value] = valueString; | |
| 88 webCoreString = valueString; | |
| 89 } | |
| 90 } else { | |
| 91 webCoreString = String::number(value); | |
| 92 } | |
| 93 return webCoreString; | |
| 94 } else { | |
| 95 v8::TryCatch block; | |
| 96 v8::Handle<v8::String> v8_str = obj->ToString(); | |
| 97 // Check for empty handles to handle the case where an exception | |
| 98 // is thrown as part of invoking toString on the object. | |
| 99 if (v8_str.IsEmpty()) | |
| 100 return StringImpl::empty(); | |
| 101 return v8StringToWebCoreString(v8_str, false); | |
| 102 } | |
| 103 } | |
| 104 | |
| 105 | |
| 106 AtomicString v8StringToAtomicWebCoreString(v8::Handle<v8::String> v8_str) { | |
| 107 String str = v8StringToWebCoreString(v8_str, true); | |
| 108 return AtomicString(str); | |
| 109 } | |
| 110 | |
| 111 | |
| 112 AtomicString v8ValueToAtomicWebCoreString(v8::Handle<v8::Value> v8_str) { | |
| 113 String str = v8ValueToWebCoreString(v8_str); | |
| 114 return AtomicString(str); | |
| 115 } | |
| 116 | |
| 117 | |
| 118 v8::Handle<v8::String> v8String(const String& str) { | |
| 119 if (!str.length()) | |
| 120 return v8::String::Empty(); | |
| 121 return v8::String::NewExternal(new WebCoreStringResource(str)); | |
| 122 } | |
| 123 | |
| 124 v8::Local<v8::String> v8ExternalString(const String& str) { | |
| 125 if (!str.length()) | |
| 126 return v8::String::Empty(); | |
| 127 return v8::String::NewExternal(new WebCoreStringResource(str)); | |
| 128 } | |
| 129 | |
| 130 } // namespace WebCore | |
| OLD | NEW |