Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1622)

Unified Diff: bindings/scripts/v8_utilities.py

Issue 1660113002: Updated to Chrome 45 (2454) moved from SVN to git. Base URL: https://github.com/dart-lang/webcore.git@roll_45
Patch Set: Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « bindings/scripts/v8_union.py ('k') | bindings/templates/copyright_block.txt » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: bindings/scripts/v8_utilities.py
diff --git a/bindings/scripts/v8_utilities.py b/bindings/scripts/v8_utilities.py
index e6ee9c9c9f3dd6bf808889c9d8e5df441f4a5dd0..1cd44abbe378c6d69e80cb8f24d0d6a28e0f9958 100644
--- a/bindings/scripts/v8_utilities.py
+++ b/bindings/scripts/v8_utilities.py
@@ -28,8 +28,6 @@
"""Functions shared by various parts of the code generator.
-Extends IdlTypeBase type with |enum_validation_expression| property.
-
Design doc: http://www.chromium.org/developers/design-documents/idl-compiler
"""
@@ -37,8 +35,8 @@ import re
from idl_types import IdlTypeBase
import idl_types
+from idl_definitions import Exposure, IdlInterface
from v8_globals import includes
-import v8_types
ACRONYMS = [
'CSSOM', # must come *before* CSS to match full acronym
@@ -118,15 +116,6 @@ def uncapitalize(name):
# C++
################################################################################
-def enum_validation_expression(idl_type):
- # FIXME: Add IdlEnumType, move property to derived type, and remove this check
- if not idl_type.is_enum:
- return None
- return ' || '.join(['string == "%s"' % enum_value
- for enum_value in idl_type.enum_values])
-IdlTypeBase.enum_validation_expression = property(enum_validation_expression)
-
-
def scoped_name(interface, definition, base_name):
if 'ImplementedInPrivateScript' in definition.extended_attributes:
return '%s::PrivateScript::%s' % (v8_class_name(interface), base_name)
@@ -142,7 +131,14 @@ def scoped_name(interface, definition, base_name):
def v8_class_name(interface):
- return v8_types.v8_type(interface.name)
+ return 'V8' + interface.name
+
+
+def v8_class_name_or_partial(interface):
+ class_name = v8_class_name(interface)
+ if interface.is_partial:
+ return ''.join([class_name, 'Partial'])
+ return class_name
################################################################################
@@ -193,6 +189,7 @@ CALL_WITH_ARGUMENTS = {
'ActiveWindow': 'callingDOMWindow(info.GetIsolate())',
'FirstWindow': 'enteredDOMWindow(info.GetIsolate())',
'Document': 'document',
+ 'ThisValue': 'ScriptValue(scriptState, info.This())',
}
# List because key order matters, as we want arguments in deterministic order
CALL_WITH_VALUES = [
@@ -202,6 +199,7 @@ CALL_WITH_VALUES = [
'ActiveWindow',
'FirstWindow',
'Document',
+ 'ThisValue',
]
@@ -227,6 +225,12 @@ def conditional_string(definition_or_member):
return 'ENABLE(%s)' % extended_attributes['Conditional']
+# [Constructor], [NamedConstructor]
+def is_constructor_attribute(member):
+ # TODO(yukishiino): replace this with [Constructor] and [NamedConstructor] extended attribute
+ return member.idl_type.name.endswith('Constructor')
+
+
# [DeprecateAs]
def deprecate_as(member):
extended_attributes = member.extended_attributes
@@ -238,6 +242,7 @@ def deprecate_as(member):
# [Exposed]
EXPOSED_EXECUTION_CONTEXT_METHOD = {
+ 'CompositorWorker': 'isCompositorWorkerGlobalScope',
'DedicatedWorker': 'isDedicatedWorkerGlobalScope',
'ServiceWorker': 'isServiceWorkerGlobalScope',
'SharedWorker': 'isSharedWorkerGlobalScope',
@@ -246,36 +251,88 @@ EXPOSED_EXECUTION_CONTEXT_METHOD = {
}
-def exposed(definition_or_member, interface):
- exposure_set = extended_attribute_value_as_list(definition_or_member, 'Exposed')
- if not exposure_set:
- return None
-
- interface_exposure_set = expanded_exposure_set_for_interface(interface)
+EXPOSED_WORKERS = set([
+ 'CompositorWorker',
+ 'DedicatedWorker',
+ 'SharedWorker',
+ 'ServiceWorker',
+])
+
+
+class ExposureSet:
+ """An ExposureSet is a collection of Exposure instructions."""
+ def __init__(self, exposures=None):
+ self.exposures = set(exposures) if exposures else set()
+
+ def issubset(self, other):
+ """Returns true if |self|'s exposure set is a subset of
+ |other|'s exposure set. This function doesn't care about
+ RuntimeEnabled."""
+ self_set = self._extended(set(e.exposed for e in self.exposures))
+ other_set = self._extended(set(e.exposed for e in other.exposures))
+ return self_set.issubset(other_set)
+
+ @staticmethod
+ def _extended(target):
+ if EXPOSED_WORKERS.issubset(target):
+ return target | set(['Worker'])
+ elif 'Worker' in target:
+ return target | EXPOSED_WORKERS
+ return target
+
+ def add(self, exposure):
+ self.exposures.add(exposure)
+
+ def __len__(self):
+ return len(self.exposures)
+
+ def __iter__(self):
+ return self.exposures.__iter__()
+
+ @staticmethod
+ def _code(exposure):
+ exposed = ('context->%s()' %
+ EXPOSED_EXECUTION_CONTEXT_METHOD[exposure.exposed])
+ if exposure.runtime_enabled is not None:
+ runtime_enabled = ('RuntimeEnabledFeatures::%sEnabled()' %
+ uncapitalize(exposure.runtime_enabled))
+ return '({0} && {1})'.format(exposed, runtime_enabled)
+ return exposed
+
+ def code(self):
+ if len(self.exposures) == 0:
+ return None
+ # We use sorted here to deflake output.
+ return ' || '.join(sorted(self._code(e) for e in self.exposures))
+
+
+def exposed(member, interface):
+ """Returns a C++ code that checks if a method/attribute/etc is exposed.
+
+ When the Exposed attribute contains RuntimeEnabledFeatures (i.e.
+ Exposed(Arguments) form is given), the code contains check for them as
+ well.
+
+ EXAMPLE: [Exposed=Window, RuntimeEnabledFeature=Feature1]
+ => context->isDocument()
+
+ EXAMPLE: [Exposed(Window Feature1, Window Feature2)]
+ => context->isDocument() && RuntimeEnabledFeatures::feature1Enabled() ||
+ context->isDocument() && RuntimeEnabledFeatures::feature2Enabled()
+ """
+ exposure_set = ExposureSet(
+ extended_attribute_value_as_list(member, 'Exposed'))
+ interface_exposure_set = ExposureSet(
+ extended_attribute_value_as_list(interface, 'Exposed'))
+ for e in exposure_set:
+ if e.exposed not in EXPOSED_EXECUTION_CONTEXT_METHOD:
+ raise ValueError('Invalid execution context: %s' % e.exposed)
# Methods must not be exposed to a broader scope than their interface.
- if not set(exposure_set).issubset(interface_exposure_set):
+ if not exposure_set.issubset(interface_exposure_set):
raise ValueError('Interface members\' exposure sets must be a subset of the interface\'s.')
- exposure_checks = []
- for environment in exposure_set:
- # Methods must be exposed on one of the scopes known to Blink.
- if environment not in EXPOSED_EXECUTION_CONTEXT_METHOD:
- raise ValueError('Values for the [Exposed] annotation must reflect to a valid exposure scope.')
-
- exposure_checks.append('context->%s()' % EXPOSED_EXECUTION_CONTEXT_METHOD[environment])
-
- return ' || '.join(exposure_checks)
-
-
-def expanded_exposure_set_for_interface(interface):
- exposure_set = extended_attribute_value_as_list(interface, 'Exposed')
-
- # "Worker" is an aggregation for the different kinds of workers.
- if 'Worker' in exposure_set:
- exposure_set.extend(('DedicatedWorker', 'SharedWorker', 'ServiceWorker'))
-
- return sorted(set(exposure_set))
+ return exposure_set.code()
# [GarbageCollected], [WillBeGarbageCollected]
@@ -296,22 +353,30 @@ def cpp_name(definition_or_member):
return extended_attributes['ImplementedAs']
-# [MeasureAs]
-def measure_as(definition_or_member):
- extended_attributes = definition_or_member.extended_attributes
- if 'MeasureAs' not in extended_attributes:
- return None
- includes.add('core/frame/UseCounter.h')
- return extended_attributes['MeasureAs']
+def cpp_name_from_interfaces_info(name, interfaces_info):
+ return interfaces_info.get(name, {}).get('implemented_as') or name
+
+def cpp_name_or_partial(interface):
+ cpp_class_name = cpp_name(interface)
+ if interface.is_partial:
+ return ''.join([cpp_class_name, 'Partial'])
+ return cpp_class_name
-# [PerContextEnabled]
-def per_context_enabled_function_name(definition_or_member):
+
+# [MeasureAs]
+def measure_as(definition_or_member, interface):
extended_attributes = definition_or_member.extended_attributes
- if 'PerContextEnabled' not in extended_attributes:
- return None
- feature_name = extended_attributes['PerContextEnabled']
- return 'ContextFeatures::%sEnabled' % uncapitalize(feature_name)
+ if 'MeasureAs' in extended_attributes:
+ includes.add('core/frame/UseCounter.h')
+ return lambda suffix: extended_attributes['MeasureAs']
+ if 'Measure' in extended_attributes:
+ includes.add('core/frame/UseCounter.h')
+ measure_as_name = capitalize(definition_or_member.name)
+ if interface is not None:
+ measure_as_name = '%s_%s' % (capitalize(interface.name), measure_as_name)
+ return lambda suffix: 'V8%s_%s' % (measure_as_name, suffix)
+ return None
# [RuntimeEnabled]
@@ -329,9 +394,200 @@ def runtime_enabled_function_name(definition_or_member):
return 'RuntimeEnabledFeatures::%sEnabled' % uncapitalize(feature_name)
+# [Unforgeable]
+def is_unforgeable(interface, member):
+ return (('Unforgeable' in interface.extended_attributes or
+ 'Unforgeable' in member.extended_attributes) and
+ not member.is_static)
+
+
+# [TypeChecking=Interface] / [LegacyInterfaceTypeChecking]
+def is_legacy_interface_type_checking(interface, member):
+ if not ('TypeChecking' in interface.extended_attributes or
+ 'TypeChecking' in member.extended_attributes):
+ return True
+ if 'LegacyInterfaceTypeChecking' in member.extended_attributes:
+ return True
+ return False
+
+
+# [Unforgeable], [Global], [PrimaryGlobal] and [DoNotExposeJSAccessors]
+def on_instance(interface, member):
+ """Returns True if the interface's member needs to be defined on every
+ instance object.
+
+ The following members must be defiend on an instance object.
+ - [Unforgeable] members
+ - regular members of [Global] or [PrimaryGlobal] interfaces
+ - members on which [DoNotExposeJSAccessors] is specified
+ """
+ # TODO(yukishiino): Implement this function following the spec.
+ return not on_prototype(interface, member)
+
+
+# [ExposeJSAccessors]
+def on_prototype(interface, member):
+ """Returns True if the interface's member needs to be defined on the
+ prototype object.
+
+ Most members are defined on the prototype object. Exceptions are as
+ follows.
+ - constant members
+ - static members (optional)
+ - [Unforgeable] members
+ - members of [Global] or [PrimaryGlobal] interfaces
+ - named properties of [Global] or [PrimaryGlobal] interfaces
+ However, if [ExposeJSAccessors] is specified, the member is defined on the
+ prototype object.
+ """
+ # TODO(yukishiino): Implement this function following the spec.
+
+ if ('ExposeJSAccessors' in interface.extended_attributes and
+ 'DoNotExposeJSAccessors' in interface.extended_attributes):
+ raise Exception('Both of ExposeJSAccessors and DoNotExposeJSAccessors are specified at a time in an interface: ' + interface.name)
+ if ('ExposeJSAccessors' in member.extended_attributes and
+ 'DoNotExposeJSAccessors' in member.extended_attributes):
+ raise Exception('Both of ExposeJSAccessors and DoNotExposeJSAccessors are specified at a time on a member: ' + member.name + ' in an interface: ' + interface.name)
+
+ # Note that ExposeJSAccessors and DoNotExposeJSAccessors are more powerful
+ # than 'static', [Unforgeable] and [OverrideBuiltins].
+ if 'ExposeJSAccessors' in member.extended_attributes:
+ return True
+ if 'DoNotExposeJSAccessors' in member.extended_attributes:
+ return False
+
+ # These members must not be placed on prototype chains.
+ if (is_constructor_attribute(member) or
+ member.is_static or
+ is_unforgeable(interface, member) or
+ 'OverrideBuiltins' in interface.extended_attributes):
+ return False
+
+ # TODO(yukishiino): We should handle [Global] and [PrimaryGlobal] instead of
+ # Window.
+ if (interface.name == 'Window'):
+ return member.idl_type.name == 'EventHandler'
+
+ if 'ExposeJSAccessors' in interface.extended_attributes:
+ return True
+ if 'DoNotExposeJSAccessors' in interface.extended_attributes:
+ return False
+
+ return True
+
+
+# static, const
+def on_interface(interface, member):
+ """Returns True if the interface's member needs to be defined on the
+ interface object.
+
+ The following members must be defiend on an interface object.
+ - constant members
+ - static members
+ """
+ # TODO(yukishiino): Implement this function following the spec.
+ return False
+
+
+################################################################################
+# Indexed properties
+# http://heycam.github.io/webidl/#idl-indexed-properties
+################################################################################
+
+def indexed_property_getter(interface):
+ try:
+ # Find indexed property getter, if present; has form:
+ # getter TYPE [OPTIONAL_IDENTIFIER](unsigned long ARG1)
+ return next(
+ method
+ for method in interface.operations
+ if ('getter' in method.specials and
+ len(method.arguments) == 1 and
+ str(method.arguments[0].idl_type) == 'unsigned long'))
+ except StopIteration:
+ return None
+
+
+def indexed_property_setter(interface):
+ try:
+ # Find indexed property setter, if present; has form:
+ # setter RETURN_TYPE [OPTIONAL_IDENTIFIER](unsigned long ARG1, ARG_TYPE ARG2)
+ return next(
+ method
+ for method in interface.operations
+ if ('setter' in method.specials and
+ len(method.arguments) == 2 and
+ str(method.arguments[0].idl_type) == 'unsigned long'))
+ except StopIteration:
+ return None
+
+
+def indexed_property_deleter(interface):
+ try:
+ # Find indexed property deleter, if present; has form:
+ # deleter TYPE [OPTIONAL_IDENTIFIER](unsigned long ARG)
+ return next(
+ method
+ for method in interface.operations
+ if ('deleter' in method.specials and
+ len(method.arguments) == 1 and
+ str(method.arguments[0].idl_type) == 'unsigned long'))
+ except StopIteration:
+ return None
+
+
################################################################################
-# Dart Specific extended attributes
+# Named properties
+# http://heycam.github.io/webidl/#idl-named-properties
################################################################################
-def dart_custom_method(extended_attributes):
- return ('DartCustom' in extended_attributes and
- extended_attribute_value_contains(extended_attributes['DartCustom'], 'New'))
+
+def named_property_getter(interface):
+ try:
+ # Find named property getter, if present; has form:
+ # getter TYPE [OPTIONAL_IDENTIFIER](DOMString ARG1)
+ getter = next(
+ method
+ for method in interface.operations
+ if ('getter' in method.specials and
+ len(method.arguments) == 1 and
+ str(method.arguments[0].idl_type) == 'DOMString'))
+ getter.name = getter.name or 'anonymousNamedGetter'
+ return getter
+ except StopIteration:
+ return None
+
+
+def named_property_setter(interface):
+ try:
+ # Find named property setter, if present; has form:
+ # setter RETURN_TYPE [OPTIONAL_IDENTIFIER](DOMString ARG1, ARG_TYPE ARG2)
+ return next(
+ method
+ for method in interface.operations
+ if ('setter' in method.specials and
+ len(method.arguments) == 2 and
+ str(method.arguments[0].idl_type) == 'DOMString'))
+ except StopIteration:
+ return None
+
+
+def named_property_deleter(interface):
+ try:
+ # Find named property deleter, if present; has form:
+ # deleter TYPE [OPTIONAL_IDENTIFIER](DOMString ARG)
+ return next(
+ method
+ for method in interface.operations
+ if ('deleter' in method.specials and
+ len(method.arguments) == 1 and
+ str(method.arguments[0].idl_type) == 'DOMString'))
+ except StopIteration:
+ return None
+
+
+IdlInterface.indexed_property_getter = property(indexed_property_getter)
+IdlInterface.indexed_property_setter = property(indexed_property_setter)
+IdlInterface.indexed_property_deleter = property(indexed_property_deleter)
+IdlInterface.named_property_getter = property(named_property_getter)
+IdlInterface.named_property_setter = property(named_property_setter)
+IdlInterface.named_property_deleter = property(named_property_deleter)
« no previous file with comments | « bindings/scripts/v8_union.py ('k') | bindings/templates/copyright_block.txt » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698