Index: Source/bindings/scripts/v8_utilities.py |
diff --git a/Source/bindings/scripts/v8_utilities.py b/Source/bindings/scripts/v8_utilities.py |
new file mode 100644 |
index 0000000000000000000000000000000000000000..f00a798ee6130d9acfbe6c289d8033bcfe669d1a |
--- /dev/null |
+++ b/Source/bindings/scripts/v8_utilities.py |
@@ -0,0 +1,243 @@ |
+# Copyright (C) 2013 Google Inc. All rights reserved. |
+# |
+# Redistribution and use in source and binary forms, with or without |
+# modification, are permitted provided that the following conditions are |
+# met: |
+# |
+# * Redistributions of source code must retain the above copyright |
+# notice, this list of conditions and the following disclaimer. |
+# * Redistributions in binary form must reproduce the above |
+# copyright notice, this list of conditions and the following disclaimer |
+# in the documentation and/or other materials provided with the |
+# distribution. |
+# * Neither the name of Google Inc. nor the names of its |
+# contributors may be used to endorse or promote products derived from |
+# this software without specific prior written permission. |
+# |
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
+# 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
+# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
+# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
+# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
+# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
+# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
+# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
+# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
+# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
+# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
+ |
+ |
+import re |
+ |
+ACRONYMS = ['CSS', 'HTML', 'IME', 'JS', 'SVG', 'URL', 'XML', 'XSLT'] |
+ |
+ |
+def generate_conditional_string(definition_or_member): |
+ if 'Conditional' not in definition_or_member.extended_attributes: |
+ return '' |
+ conditional = definition_or_member.extended_attributes['Conditional'] |
+ for operator in ['&', '|']: |
+ if operator in conditional: |
+ conditions = sorted(conditional.split(operator)) |
+ operator_separator = ' {0}{0} '.format(operator) |
+ return operator_separator.join(['ENABLE(%s)' % expression for expression in conditions]) |
+ return 'ENABLE(%s)' % conditional |
+ |
+ |
+def implemented_as_cpp_name(definition_or_member): |
+ """Return ImplementedAs name, falling back on name attribute. |
+ |
+ For interfaces (definitions), this is used as the class name. |
+ For attributes and operations (members), this is used as the method name. |
+ For attributes, this is also used in the getter and setter. |
+ """ |
+ return definition_or_member.extended_attributes.get('ImplementedAs', definition_or_member.name) |
+ |
+ |
+def runtime_enable_function_name(definition_or_member): |
+ """Return the name of the RuntimeEnabledFeatures function. |
+ |
+ The returned function checks if a method/attribute is enabled. |
+ If a parameter is given (e.g. 'EnabledAtRuntime=FeatureName'), return: |
+ RuntimeEnabledFeatures::{featureName}Enabled |
+ Otherwise return: |
+ RuntimeEnabledFeatures::{methodName}Enabled |
+ """ |
+ name = definition_or_member.extended_attributes.get('EnabledAtRuntime') or definition_or_member.name |
+ return 'RuntimeEnabledFeatures::%sEnabled' % uncapitalize(name) |
+ |
+ |
+def uncapitalize(name): |
+ """Uncapitalize first letter or initial acronym (* with some exceptions). |
+ |
+ E.g., 'SetURL' becomes 'setURL', but 'URLFoo' becomes 'urlFoo'. |
+ Used in method names; exceptions differ from capitalize(). |
+ """ |
+ for acronym in ACRONYMS: |
+ if name.startswith(acronym): |
+ name.replace(acronym, acronym.lower()) |
+ break |
+ else: |
+ name = name[0].lower() + name[1:] |
+ |
+ # For HTML5 FileSystem API Flags attributes. |
+ # (create is widely used to instantiate an object and must be avoided.) |
+ if name == 'create': |
+ return 'isCreate' |
+ if name == 'exclusive': |
+ return 'isExclusive' |
+ return name |
+ |
+ |
+################################################################################ |
+# WIP |
+################################################################################ |
+ |
+ACTIVITY_LOGGING_INCLUDES = [ |
+ 'bindings/v8/V8Binding.h', |
+ 'bindings/v8/V8DOMActivityLogger.h', |
+ 'wtf/Vector.h', |
+] |
+ |
+ |
+def capitalize(name): |
+ """Capitalize first letter or initial acronym (* with some exceptions). |
+ |
+ Used in setter names. |
+ """ |
+ name = name[0].upper() + name[1:] |
+ # xmlEncoding becomes XMLEncoding, but xmlllang becomes Xmllang. |
+ if name.startswith('CssText') or re.match('Xml[a-z]', name): |
+ return name |
+ for acronym in ACRONYMS: |
+ if name.startswith(acronym.capitalize()): |
+ name.replace(acronym.capitalize(), acronym) |
+ break |
+ return name |
+ |
+ |
+def strip_suffix(text, suffix): |
+ if suffix and text.endswith(suffix): |
+ return text[:-len(suffix)] |
+ return text |
+ |
+ |
+def extended_attribute_contains(values_str, keyword): |
+ return values_str and keyword in re.split('[|&]', values_str) |
+ |
+ |
+def get_raises_exception(function): |
+ return 'RaisesException' in function.extended_attributes |
+ |
+ |
+def get_function_mandatory_parameters(function, count_variadic=False): |
+ allow_non_optional = True |
+ for parameter in function.arguments: |
+ if parameter.is_optional or parameter.is_variadic: |
+ allow_non_optional = False |
+ else: |
+ if not allow_non_optional: |
+ raise Exception() |
+ mandatory_parameters = 0 |
+ for parameter in function.arguments: |
+ if parameter.is_optional: |
+ break |
+ if parameter.is_variadic and not count_variadic: |
+ break |
+ mandatory_parameters += 1 |
+# print '[]', function.name, mandatory_parameters |
+ return mandatory_parameters |
+ |
+ |
+def get_feature_observation_parameter(interface_or_attribute_or_function): |
+ includes = [] |
+ measure_as = 'MeasureAs' in interface_or_attribute_or_function.extended_attributes |
+ if measure_as: |
+ includes.append('core/page/UseCounter.h') |
+ parameter = { |
+ 'measure_as': interface_or_attribute_or_function.extended_attributes.get('MeasureAs'), |
+ } |
+ return parameter, includes |
+ |
+ |
+def get_deprecation_notification_parameter(interface_or_attribute_or_function): |
+ includes = [] |
+# print '[[]]', interface_or_attribute_or_function.extended_attributes |
+ deprecate_as = 'DeprecateAs' in interface_or_attribute_or_function.extended_attributes |
+ if deprecate_as: |
+ includes.append('core/page/PageConsole.h') |
+ includes.append('core/page/UseCounter.h') |
+ parameter = { |
+ 'deprecate_as': interface_or_attribute_or_function.extended_attributes.get('DeprecateAs'), |
+ } |
+ return parameter, includes |
+ |
+ |
+def has_activity_logging(for_main_world_suffix, extended_attributes, access): |
+ if access not in ['Method', 'Setter', 'Getter']: |
+ raise Exception('Unrecognized activity logging access type') |
+ if 'ActivityLog' not in extended_attributes: |
+ return False |
+ activity_log = extended_attributes['ActivityLog'] |
+ log_only_isolated_worlds = activity_log.endswith('ForIsolatedWorlds') |
+ if log_only_isolated_worlds and for_main_world_suffix == 'ForMainWorld': |
+ return False |
+ return ( |
+ activity_log.startswith('Access') or |
+ (access in ['Getter', 'Setter'] and activity_log.startswith(access))) |
+ |
+ |
+def get_custom_element_invocation_scope_parameter(interface_or_attribute_or_function): |
+# print '[[]]', interface_or_attribute_or_function.extended_attributes |
+ includes = [] |
+ custom_element_invocation_scope = 'DeliverCustomElementCallbacks' in interface_or_attribute_or_function.extended_attributes or 'Reflect' in interface_or_attribute_or_function.extended_attributes |
+ if custom_element_invocation_scope: |
+ includes.append('core/dom/CustomElementCallbackDispatcher.h') |
+ parameter = { |
+ 'custom_element_invocation_scope': custom_element_invocation_scope, |
+ } |
+ return parameter, includes |
+ |
+ |
+def get_call_with_parameter(call_with, return_void=False, function=None): |
+ """ |
+ @return arguments, template_parameter, includes |
+ """ |
+ if not call_with: |
+ return [], {}, [] |
+ |
+ if return_void: |
+ script_state_return_value = '' |
+ else: |
+ script_state_return_value = ' v8Undefined()' |
+ |
+ script_state = extended_attribute_contains(call_with, 'ScriptState') |
+ script_execution_context = extended_attribute_contains(call_with, 'ScriptExecutionContext') |
+ script_arguments = extended_attribute_contains(call_with, 'ScriptArguments') |
+ active_window = extended_attribute_contains(call_with, 'ActiveWindow') |
+ first_window = extended_attribute_contains(call_with, 'FirstWindow') |
+ |
+ call_with_arguments = [] |
+ if script_state: |
+ call_with_arguments.append('&state') |
+ if script_execution_context: |
+ call_with_arguments.append('scriptContext') |
+ if function and script_arguments: |
+ call_with_arguments.append('scriptArguments.release()') |
+ includes = ['bindings/v8/ScriptCallStackFactory.h', |
+ 'core/inspector/ScriptArguments.h'] |
+ else: |
+ includes = [] |
+ if active_window: |
+ call_with_arguments.append('activeDOMWindow()') |
+ if first_window: |
+ call_with_arguments.append('firstDOMWindow()') |
+ |
+ template_parameter = { |
+ 'script_state_return_value': script_state_return_value, |
+ 'script_state': script_state, |
+ 'script_execution_context': script_execution_context, |
+ 'function': function, |
+ 'number_of_function_parameters': len(function.arguments) if function else 0, |
+ } |
+ return call_with_arguments, template_parameter, includes |