{% if attribute.is_reflect and not attribute.is_url and
attribute.idl_type == 'DOMString' and is_node %}
{% set cpp_class, v8_class = 'Element', 'V8Element' %}
- {# FIXME: Perl skips most of function, but this seems unnecessary #}
{% endif %}
- {% if attribute.is_unforgeable %}
+ {# imp #}
+ {# FIXME: use a local variable for holder more often and simplify below #}
+ {% if attribute.is_unforgeable or
+ interface_name == 'Window' and attribute.idl_type == 'EventHandler' %}
+ {% if interface_name == 'Window' %}
+ v8::Handle<v8::Object> holder = info.Holder();
+ {% else %}{# perform lookup first #}
+ {# FIXME: can we remove this lookup? #}
v8::Handle<v8::Object> holder = info.This()->FindInstanceInPrototypeChain({{v8_class}}::domTemplate(info.GetIsolate(), worldType(info.GetIsolate())));
if (holder.IsEmpty())
return;
+ {% endif %}{# Window #}
{{cpp_class}}* imp = {{v8_class}}::toNative(holder);
- {% endif %}
- {% if attribute.cached_attribute_validation_method %}
+ {% elif attribute.cached_attribute_validation_method %}
v8::Handle<v8::String> propertyName = v8AtomicString(info.GetIsolate(), "{{attribute.name}}");
{{cpp_class}}* imp = {{v8_class}}::toNative(info.Holder());
if (!imp->{{attribute.cached_attribute_validation_method}}()) {
{% elif not (attribute.is_static or attribute.is_unforgeable) %}
{{cpp_class}}* imp = {{v8_class}}::toNative(info.Holder());
{% endif %}
+ {% if interface_name == 'Window' and attribute.idl_type == 'EventHandler' %}
+ if (!imp->document())
+ return;
+ {% endif %}
+ {# Local variables #}
{% if attribute.is_call_with_execution_context %}
- ExecutionContext* scriptContext = getExecutionContext();
+ ExecutionContext* scriptContext = currentExecutionContext(info.GetIsolate());
{% endif %}
- {# Special cases #}
{% if attribute.is_check_security_for_node or
attribute.is_getter_raises_exception %}
ExceptionState exceptionState(ExceptionState::GetterContext, "{{attribute.name}}", "{{interface_name}}", info.Holder(), info.GetIsolate());
{% endif %}
+ {% if attribute.is_nullable %}
+ bool isNull = false;
+ {% endif %}
+ {# FIXME: consider always using a local variable for value #}
+ {% if attribute.cached_attribute_validation_method or
+ attribute.is_getter_raises_exception or
+ attribute.is_nullable or
+ attribute.reflect_only or
+ attribute.idl_type == 'EventHandler' %}
+ {{attribute.cpp_type}} {{attribute.cpp_value}} = {{attribute.cpp_value_original}};
+ {% endif %}
+ {# Checks #}
+ {% if attribute.is_getter_raises_exception %}
+ if (UNLIKELY(exceptionState.throwIfNeeded()))
+ return;
+ {% endif %}
{% if attribute.is_check_security_for_node %}
- {# FIXME: consider using a local variable to not call getter twice #}
- if (!BindingSecurity::shouldAllowAccessToNode({{attribute.cpp_value}}, exceptionState)) {
+ {# FIXME: use a local variable to not call getter twice #}
+ if (!BindingSecurity::shouldAllowAccessToNode(info.GetIsolate(), {{attribute.cpp_value}}, exceptionState)) {
v8SetReturnValueNull(info);
exceptionState.throwIfNeeded();
return;
}
{% endif %}
- {% if attribute.is_getter_raises_exception %}
- {{attribute.cpp_type}} {{attribute.cpp_value}} = {{attribute.cpp_value_original}};
- if (UNLIKELY(exceptionState.throwIfNeeded()))
- return;
+ {% if attribute.reflect_only %}
+ {{release_only_check(attribute.reflect_only, attribute.reflect_missing,
+ attribute.reflect_invalid, attribute.reflect_empty)
+ | indent}}
{% endif %}
{% if attribute.is_nullable %}
- bool isNull = false;
- {{attribute.cpp_type}} {{attribute.cpp_value}} = {{attribute.cpp_value_original}};
if (isNull) {
v8SetReturnValueNull(info);
return;
}
- {% elif attribute.idl_type == 'EventHandler' or
- attribute.cached_attribute_validation_method %}
- {# FIXME: consider merging all these assign to local variable statements #}
- {{attribute.cpp_type}} {{attribute.cpp_value}} = {{attribute.cpp_value_original}};
{% endif %}
{% if attribute.cached_attribute_validation_method %}
setHiddenValue(info.GetIsolate(), info.Holder(), propertyName, {{attribute.cpp_value}}.v8Value());
{% endif %}
- {# End special cases #}
+ {# v8SetReturnValue #}
{% if attribute.is_keep_alive_for_gc %}
+ {# FIXME: merge local variable assignment with above #}
{{attribute.cpp_type}} result = {{attribute.cpp_value}};
- if (result && DOMDataStore::setReturnValueFromWrapper<{{attribute.v8_type}}>(info.GetReturnValue(), result.get()))
+ if (result && DOMDataStore::setReturnValueFromWrapper{{world_suffix}}<{{attribute.v8_type}}>(info.GetReturnValue(), result.get()))
return;
v8::Handle<v8::Value> wrapper = toV8(result.get(), info.Holder(), info.GetIsolate());
if (!wrapper.IsEmpty()) {
setHiddenValue(info.GetIsolate(), info.Holder(), "{{attribute.name}}", wrapper);
{{attribute.v8_set_return_value}};
}
+ {% elif world_suffix %}
+ {{attribute.v8_set_return_value_for_main_world}};
{% else %}
{{attribute.v8_set_return_value}};
{% endif %}
{% endfilter %}
{% endmacro %}
+{######################################}
+{% macro release_only_check(reflect_only_values, reflect_missing,
+ reflect_invalid, reflect_empty) %}
+{# Attribute is limited to only known values: check that the attribute value is
+ one of those. If not, set it to the empty string.
+ http://www.whatwg.org/specs/web-apps/current-work/#limited-to-only-known-values #}
+{# FIXME: rename resultValue to jsValue #}
+{% if reflect_empty %}
+if (resultValue.isNull()) {
+{% if reflect_missing %}
+ resultValue = "{{reflect_missing}}";
+{% else %}
+ ;
+{% endif %}
+} else if (resultValue.isEmpty()) {
+ resultValue = "{{reflect_empty}}";
+{% else %}
+if (resultValue.isEmpty()) {
+{# FIXME: should use [ReflectEmpty] instead; need to change IDL files #}
+{% if reflect_missing %}
+ resultValue = "{{reflect_missing}}";
+{% else %}
+ ;
+{% endif %}
+{% endif %}
+{% for value in reflect_only_values %}
+} else if (equalIgnoringCase(resultValue, "{{value}}")) {
+ resultValue = "{{value}}";
+{% endfor %}
+} else {
+ resultValue = "{{reflect_invalid}}";
+}
+{% endmacro %}
+
{##############################################################################}
{% macro attribute_getter_callback(attribute, world_suffix) %}
{
TRACE_EVENT_SET_SAMPLING_STATE("Blink", "DOMGetter");
{% if attribute.deprecate_as %}
- UseCounter::countDeprecation(activeExecutionContext(), UseCounter::{{attribute.deprecate_as}});
+ UseCounter::countDeprecation(activeExecutionContext(info.GetIsolate()), UseCounter::{{attribute.deprecate_as}});
{% endif %}
{% if attribute.measure_as %}
- UseCounter::count(activeExecutionContext(), UseCounter::{{attribute.measure_as}});
+ UseCounter::count(activeExecutionContext(info.GetIsolate()), UseCounter::{{attribute.measure_as}});
{% endif %}
{% if world_suffix in attribute.activity_logging_world_list_for_getter %}
V8PerContextData* contextData = V8PerContextData::from(info.GetIsolate()->GetCurrentContext());
{% if attribute.is_reflect and attribute.idl_type == 'DOMString' and
is_node %}
{% set cpp_class, v8_class = 'Element', 'V8Element' %}
- {# FIXME: Perl skips most of function, but this seems unnecessary #}
+ {# FIXME: Perl skips most of function, but this seems unnecessary;
+ we only need to skip the CallbackDeliveryScope #}
{% endif %}
{% if attribute.has_setter_exception_state %}
ExceptionState exceptionState(ExceptionState::SetterContext, "{{attribute.name}}", "{{interface_name}}", info.Holder(), info.GetIsolate());
return;
{% elif not attribute.is_static %}
{{cpp_class}}* imp = {{v8_class}}::toNative(info.Holder());
- {% endif %}
+ {% endif %}{# imp #}
{% if attribute.idl_type == 'EventHandler' and interface_name == 'Window' %}
if (!imp->document())
return;
{% if attribute.idl_type != 'EventHandler' %}
{{attribute.v8_value_to_local_cpp_value}};
{% elif not is_node %}{# EventHandler hack #}
- transferHiddenDependency(info.Holder(), {{attribute.event_handler_getter_expression}}, jsValue, {{v8_class}}::eventListenerCacheIndex, info.GetIsolate());
+ moveEventListenerToNewWrapper(info.Holder(), {{attribute.event_handler_getter_expression}}, jsValue, {{v8_class}}::eventListenerCacheIndex, info.GetIsolate());
{% endif %}
{% if attribute.enum_validation_expression %}
{# Setter ignores invalid enum values: http://www.w3.org/TR/WebIDL/#idl-enums #}
if (!({{attribute.enum_validation_expression}}))
return;
{% endif %}
- {% if attribute.is_reflect and
- not(attribute.idl_type == 'DOMString' and is_node) %}
+ {% if attribute.is_custom_element_callbacks or
+ (attribute.is_reflect and
+ not(attribute.idl_type == 'DOMString' and is_node)) %}
+ {# Skip on compact node DOMString getters #}
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
{% endif %}
- {% if attribute.is_call_with_execution_context %}
- ExecutionContext* scriptContext = getExecutionContext();
+ {% if attribute.is_call_with_execution_context or
+ attribute.is_setter_call_with_execution_context %}
+ ExecutionContext* scriptContext = currentExecutionContext(info.GetIsolate());
{% endif %}
{{attribute.cpp_setter}};
{% if attribute.is_setter_raises_exception %}
{% endif %}
TRACE_EVENT_SET_SAMPLING_STATE("Blink", "DOMSetter");
{% if attribute.deprecate_as %}
- UseCounter::countDeprecation(activeExecutionContext(), UseCounter::{{attribute.deprecate_as}});
+ UseCounter::countDeprecation(activeExecutionContext(info.GetIsolate()), UseCounter::{{attribute.deprecate_as}});
{% endif %}
{% if attribute.measure_as %}
- UseCounter::count(activeExecutionContext(), UseCounter::{{attribute.measure_as}});
+ UseCounter::count(activeExecutionContext(info.GetIsolate()), UseCounter::{{attribute.measure_as}});
{% endif %}
{% if world_suffix in attribute.activity_logging_world_list_for_setter %}
V8PerContextData* contextData = V8PerContextData::from(info.GetIsolate()->GetCurrentContext());
contextData->activityLogger()->log("{{interface_name}}.{{attribute.name}}", 1, &loggerArg[0], "Setter");
}
{% endif %}
- {% if attribute.is_reflect %}
+ {% if attribute.is_custom_element_callbacks or attribute.is_reflect %}
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
{% endif %}
{% if attribute.has_custom_setter %}