mesa gn build: suppress -Wstring-conversion warnings
[chromium-blink-merge.git] / content / renderer / pepper / pepper_try_catch.cc
blobec8436922149e57695e320c4c49e2ec606e2a308
1 // Copyright 2014 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.
5 #include "content/renderer/pepper/pepper_try_catch.h"
7 #include "content/renderer/pepper/pepper_plugin_instance_impl.h"
8 #include "content/renderer/pepper/v8_var_converter.h"
9 #include "gin/converter.h"
10 #include "ppapi/shared_impl/ppapi_globals.h"
11 #include "ppapi/shared_impl/var_tracker.h"
13 namespace content {
15 namespace {
17 const char kConversionException[] =
18 "Error: Failed conversion between PP_Var and V8 value";
19 const char kInvalidException[] = "Error: An invalid exception was thrown.";
21 } // namespace
23 PepperTryCatch::PepperTryCatch(PepperPluginInstanceImpl* instance,
24 V8VarConverter* var_converter)
25 : instance_(instance), var_converter_(var_converter) {}
27 PepperTryCatch::~PepperTryCatch() {}
29 v8::Handle<v8::Value> PepperTryCatch::ToV8(PP_Var var) {
30 if (HasException()) {
31 SetException(kConversionException);
32 return v8::Handle<v8::Value>();
35 v8::Handle<v8::Value> result;
36 bool success = var_converter_->ToV8Value(var, GetContext(), &result);
37 if (!success) {
38 SetException(kConversionException);
39 return v8::Handle<v8::Value>();
41 return result;
44 ppapi::ScopedPPVar PepperTryCatch::FromV8(v8::Handle<v8::Value> v8_value) {
45 if (HasException() || v8_value.IsEmpty()) {
46 SetException(kConversionException);
47 return ppapi::ScopedPPVar();
49 ppapi::ScopedPPVar result;
50 bool success =
51 var_converter_->FromV8ValueSync(v8_value, GetContext(), &result);
52 if (!success) {
53 SetException(kConversionException);
54 return ppapi::ScopedPPVar();
56 return result;
59 PepperTryCatchV8::PepperTryCatchV8(PepperPluginInstanceImpl* instance,
60 V8VarConverter* var_converter,
61 v8::Isolate* isolate)
62 : PepperTryCatch(instance, var_converter),
63 exception_(PP_MakeUndefined()) {
64 // Typically when using PepperTryCatchV8 we are passed an isolate. We verify
65 // that this isolate is the same as the plugin isolate.
66 DCHECK(isolate == instance_->GetIsolate());
68 // We assume that a handle scope and context has been setup by the user of
69 // this class. This is typically true because this class is used when calling
70 // into the plugin from JavaScript. We want to use whatever v8 context the
71 // caller is in.
74 PepperTryCatchV8::~PepperTryCatchV8() {
75 ppapi::PpapiGlobals::Get()->GetVarTracker()->ReleaseVar(exception_);
78 bool PepperTryCatchV8::HasException() {
79 return GetContext().IsEmpty() || exception_.type != PP_VARTYPE_UNDEFINED;
82 v8::Handle<v8::Context> PepperTryCatchV8::GetContext() {
83 // When calling from JS into the plugin always use the current context.
84 return instance_->GetIsolate()->GetCurrentContext();
87 bool PepperTryCatchV8::ThrowException() {
88 if (!HasException())
89 return false;
91 // If there is no context then we have an exception but we don't try to throw
92 // it into v8.
93 if (GetContext().IsEmpty())
94 return true;
96 std::string message(kInvalidException);
97 ppapi::StringVar* message_var = ppapi::StringVar::FromPPVar(exception_);
98 if (message_var)
99 message = message_var->value();
100 instance_->GetIsolate()->ThrowException(v8::Exception::Error(
101 gin::StringToV8(instance_->GetIsolate(), message)));
103 ppapi::PpapiGlobals::Get()->GetVarTracker()->ReleaseVar(exception_);
104 exception_ = PP_MakeUndefined();
105 return true;
108 void PepperTryCatchV8::ThrowException(const char* message) {
109 SetException(message);
110 ThrowException();
113 void PepperTryCatchV8::SetException(const char* message) {
114 if (HasException())
115 return;
117 exception_ = ppapi::StringVar::StringToPPVar(message);
120 PepperTryCatchVar::PepperTryCatchVar(PepperPluginInstanceImpl* instance,
121 V8VarConverter* var_converter,
122 PP_Var* exception)
123 : PepperTryCatch(instance, var_converter),
124 handle_scope_(instance_->GetIsolate()),
125 context_(GetContext()),
126 exception_(exception),
127 exception_is_set_(false) {
128 // We switch to the plugin context if it's not empty.
129 if (!context_.IsEmpty())
130 context_->Enter();
133 PepperTryCatchVar::~PepperTryCatchVar() {
134 if (!context_.IsEmpty())
135 context_->Exit();
138 bool PepperTryCatchVar::HasException() {
139 if (exception_is_set_)
140 return true;
142 std::string exception_message;
143 if (GetContext().IsEmpty()) {
144 exception_message = "The v8 context has been destroyed.";
145 } else if (try_catch_.HasCaught()) {
146 v8::String::Utf8Value utf8(try_catch_.Message()->Get());
147 exception_message = std::string(*utf8, utf8.length());
150 if (!exception_message.empty()) {
151 exception_is_set_ = true;
152 if (exception_)
153 *exception_ = ppapi::StringVar::StringToPPVar(exception_message);
156 return exception_is_set_;
159 v8::Handle<v8::Context> PepperTryCatchVar::GetContext() {
160 // When calling into JS from the plugin, always use the plugin context.
161 return instance_->GetMainWorldContext();
164 void PepperTryCatchVar::SetException(const char* message) {
165 if (exception_is_set_)
166 return;
168 if (exception_)
169 *exception_ = ppapi::StringVar::StringToPPVar(message, strlen(message));
170 exception_is_set_ = true;
173 } // namespace content