Home | History | Annotate | Download | only in gin
      1 // Copyright 2013 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 "gin/converter.h"
      6 
      7 #include "v8/include/v8.h"
      8 
      9 using v8::ArrayBuffer;
     10 using v8::Boolean;
     11 using v8::External;
     12 using v8::Function;
     13 using v8::Handle;
     14 using v8::Integer;
     15 using v8::Isolate;
     16 using v8::Number;
     17 using v8::Object;
     18 using v8::String;
     19 using v8::Value;
     20 
     21 namespace gin {
     22 
     23 Handle<Value> Converter<bool>::ToV8(Isolate* isolate, bool val) {
     24   return Boolean::New(isolate, val).As<Value>();
     25 }
     26 
     27 bool Converter<bool>::FromV8(Isolate* isolate, Handle<Value> val, bool* out) {
     28   *out = val->BooleanValue();
     29   return true;
     30 }
     31 
     32 Handle<Value> Converter<int32_t>::ToV8(Isolate* isolate, int32_t val) {
     33   return Integer::New(isolate, val).As<Value>();
     34 }
     35 
     36 bool Converter<int32_t>::FromV8(Isolate* isolate, Handle<Value> val,
     37                                 int32_t* out) {
     38   if (!val->IsInt32())
     39     return false;
     40   *out = val->Int32Value();
     41   return true;
     42 }
     43 
     44 Handle<Value> Converter<uint32_t>::ToV8(Isolate* isolate, uint32_t val) {
     45   return Integer::NewFromUnsigned(isolate, val).As<Value>();
     46 }
     47 
     48 bool Converter<uint32_t>::FromV8(Isolate* isolate, Handle<Value> val,
     49                                  uint32_t* out) {
     50   if (!val->IsUint32())
     51     return false;
     52   *out = val->Uint32Value();
     53   return true;
     54 }
     55 
     56 Handle<Value> Converter<int64_t>::ToV8(Isolate* isolate, int64_t val) {
     57   return Number::New(isolate, static_cast<double>(val)).As<Value>();
     58 }
     59 
     60 bool Converter<int64_t>::FromV8(Isolate* isolate, Handle<Value> val,
     61                                 int64_t* out) {
     62   if (!val->IsNumber())
     63     return false;
     64   // Even though IntegerValue returns int64_t, JavaScript cannot represent
     65   // the full precision of int64_t, which means some rounding might occur.
     66   *out = val->IntegerValue();
     67   return true;
     68 }
     69 
     70 Handle<Value> Converter<uint64_t>::ToV8(Isolate* isolate, uint64_t val) {
     71   return Number::New(isolate, static_cast<double>(val)).As<Value>();
     72 }
     73 
     74 bool Converter<uint64_t>::FromV8(Isolate* isolate, Handle<Value> val,
     75                                  uint64_t* out) {
     76   if (!val->IsNumber())
     77     return false;
     78   *out = static_cast<uint64_t>(val->IntegerValue());
     79   return true;
     80 }
     81 
     82 Handle<Value> Converter<float>::ToV8(Isolate* isolate, float val) {
     83   return Number::New(isolate, val).As<Value>();
     84 }
     85 
     86 bool Converter<float>::FromV8(Isolate* isolate, Handle<Value> val,
     87                               float* out) {
     88   if (!val->IsNumber())
     89     return false;
     90   *out = static_cast<float>(val->NumberValue());
     91   return true;
     92 }
     93 
     94 Handle<Value> Converter<double>::ToV8(Isolate* isolate, double val) {
     95   return Number::New(isolate, val).As<Value>();
     96 }
     97 
     98 bool Converter<double>::FromV8(Isolate* isolate, Handle<Value> val,
     99                                double* out) {
    100   if (!val->IsNumber())
    101     return false;
    102   *out = val->NumberValue();
    103   return true;
    104 }
    105 
    106 Handle<Value> Converter<base::StringPiece>::ToV8(
    107     Isolate* isolate, const base::StringPiece& val) {
    108   return String::NewFromUtf8(isolate, val.data(), String::kNormalString,
    109                              static_cast<uint32_t>(val.length()));
    110 }
    111 
    112 Handle<Value> Converter<std::string>::ToV8(Isolate* isolate,
    113                                            const std::string& val) {
    114   return Converter<base::StringPiece>::ToV8(isolate, val);
    115 }
    116 
    117 bool Converter<std::string>::FromV8(Isolate* isolate, Handle<Value> val,
    118                                     std::string* out) {
    119   if (!val->IsString())
    120     return false;
    121   Handle<String> str = Handle<String>::Cast(val);
    122   int length = str->Utf8Length();
    123   out->resize(length);
    124   str->WriteUtf8(&(*out)[0], length, NULL, String::NO_NULL_TERMINATION);
    125   return true;
    126 }
    127 
    128 bool Converter<Handle<Function> >::FromV8(Isolate* isolate, Handle<Value> val,
    129                                           Handle<Function>* out) {
    130   if (!val->IsFunction())
    131     return false;
    132   *out = Handle<Function>::Cast(val);
    133   return true;
    134 }
    135 
    136 Handle<Value> Converter<Handle<Object> >::ToV8(Isolate* isolate,
    137                                                Handle<Object> val) {
    138   return val.As<Value>();
    139 }
    140 
    141 bool Converter<Handle<Object> >::FromV8(Isolate* isolate, Handle<Value> val,
    142                                         Handle<Object>* out) {
    143   if (!val->IsObject())
    144     return false;
    145   *out = Handle<Object>::Cast(val);
    146   return true;
    147 }
    148 
    149 Handle<Value> Converter<Handle<ArrayBuffer> >::ToV8(Isolate* isolate,
    150                                                     Handle<ArrayBuffer> val) {
    151   return val.As<Value>();
    152 }
    153 
    154 bool Converter<Handle<ArrayBuffer> >::FromV8(Isolate* isolate,
    155                                              Handle<Value> val,
    156                                              Handle<ArrayBuffer>* out) {
    157   if (!val->IsArrayBuffer())
    158     return false;
    159   *out = Handle<ArrayBuffer>::Cast(val);
    160   return true;
    161 }
    162 
    163 Handle<Value> Converter<Handle<External> >::ToV8(Isolate* isolate,
    164                                                  Handle<External> val) {
    165   return val.As<Value>();
    166 }
    167 
    168 bool Converter<Handle<External> >::FromV8(Isolate* isolate,
    169                                           v8::Handle<Value> val,
    170                                           Handle<External>* out) {
    171   if (!val->IsExternal())
    172     return false;
    173   *out = Handle<External>::Cast(val);
    174   return true;
    175 }
    176 
    177 Handle<Value> Converter<Handle<Value> >::ToV8(Isolate* isolate,
    178                                               Handle<Value> val) {
    179   return val;
    180 }
    181 
    182 bool Converter<Handle<Value> >::FromV8(Isolate* isolate, Handle<Value> val,
    183                                        Handle<Value>* out) {
    184   *out = val;
    185   return true;
    186 }
    187 
    188 v8::Handle<v8::String> StringToSymbol(v8::Isolate* isolate,
    189                                       const base::StringPiece& val) {
    190   return String::NewFromUtf8(isolate,
    191                              val.data(),
    192                              String::kInternalizedString,
    193                              static_cast<uint32_t>(val.length()));
    194 }
    195 
    196 std::string V8ToString(v8::Handle<v8::Value> value) {
    197   if (value.IsEmpty())
    198     return std::string();
    199   std::string result;
    200   if (!ConvertFromV8(NULL, value, &result))
    201     return std::string();
    202   return result;
    203 }
    204 
    205 }  // namespace gin
    206