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

Unified Diff: mojo/public/tools/bindings/generators/mojom_cpp_generator.py

Issue 2864543002: Mojo code generator: makes the filters member methods of generator if necessary. (Closed)
Patch Set: Created 3 years, 7 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 | « no previous file | mojo/public/tools/bindings/generators/mojom_java_generator.py » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: mojo/public/tools/bindings/generators/mojom_cpp_generator.py
diff --git a/mojo/public/tools/bindings/generators/mojom_cpp_generator.py b/mojo/public/tools/bindings/generators/mojom_cpp_generator.py
index 38d222b136995a93b668e607594989d1f2771b41..f946812d153480e9ad9891c215cfca1b70f59ee0 100644
--- a/mojo/public/tools/bindings/generators/mojom_cpp_generator.py
+++ b/mojo/public/tools/bindings/generators/mojom_cpp_generator.py
@@ -32,15 +32,6 @@ _kind_to_cpp_literal_suffix = {
mojom.UINT64: "ULL",
}
-# TODO(rockot): Get rid of these globals. This requires some refactoring of the
-# generator library code so that filters can use the generator as context.
-_current_typemap = {}
-_for_blink = False
-# TODO(rockot, yzshen): The variant handling is kind of a hack currently. Make
-# it right.
-_variant = None
-_export_attribute = None
-
class _NameFormatter(object):
"""A formatter for the names of kinds or values."""
@@ -130,36 +121,9 @@ class _NameFormatter(object):
return []
-def ConstantValue(constant):
- return ExpressionToText(constant.value, kind=constant.kind)
-
-# TODO(yzshen): Revisit the default value feature. It was designed prior to
-# custom type mapping.
-def DefaultValue(field):
- if field.default:
- if mojom.IsStructKind(field.kind):
- assert field.default == "default"
- if not IsTypemappedKind(field.kind):
- return "%s::New()" % GetNameForKind(field.kind)
- return ExpressionToText(field.default, kind=field.kind)
- return ""
-
def NamespaceToArray(namespace):
return namespace.split(".") if namespace else []
-def GetNameForKind(kind, internal=False, flatten_nested_kind=False,
- add_same_module_namespaces=False):
- return _NameFormatter(kind, _variant).FormatForCpp(
- internal=internal, flatten_nested_kind=flatten_nested_kind,
- add_same_module_namespaces=add_same_module_namespaces)
-
-def GetQualifiedNameForKind(kind, internal=False, flatten_nested_kind=False,
- include_variant=True):
- return _NameFormatter(
- kind, _variant if include_variant else None).FormatForCpp(
- internal=internal, add_same_module_namespaces=True,
- flatten_nested_kind=flatten_nested_kind)
-
def GetWtfHashFnNameForEnum(enum):
return _NameFormatter(
@@ -167,59 +131,11 @@ def GetWtfHashFnNameForEnum(enum):
flatten_nested_kind=True) + "HashFn"
-def GetFullMojomNameForKind(kind):
- return _NameFormatter(kind, _variant).FormatForMojom()
-
-def IsTypemappedKind(kind):
- return hasattr(kind, "name") and \
- GetFullMojomNameForKind(kind) in _current_typemap
-
def IsNativeOnlyKind(kind):
return (mojom.IsStructKind(kind) or mojom.IsEnumKind(kind)) and \
kind.native_only
-def IsHashableKind(kind):
- """Check if the kind can be hashed.
-
- Args:
- kind: {Kind} The kind to check.
-
- Returns:
- {bool} True if a value of this kind can be hashed.
- """
- checked = set()
- def Check(kind):
- if kind.spec in checked:
- return True
- checked.add(kind.spec)
- if mojom.IsNullableKind(kind):
- return False
- elif mojom.IsStructKind(kind):
- if (IsTypemappedKind(kind) and
- not _current_typemap[GetFullMojomNameForKind(kind)]["hashable"]):
- return False
- return all(Check(field.kind) for field in kind.fields)
- elif mojom.IsEnumKind(kind):
- return not IsTypemappedKind(kind) or _current_typemap[
- GetFullMojomNameForKind(kind)]["hashable"]
- elif mojom.IsUnionKind(kind):
- return all(Check(field.kind) for field in kind.fields)
- elif mojom.IsAnyHandleKind(kind):
- return False
- elif mojom.IsAnyInterfaceKind(kind):
- return False
- # TODO(tibell): Arrays and maps could be made hashable. We just don't have a
- # use case yet.
- elif mojom.IsArrayKind(kind):
- return False
- elif mojom.IsMapKind(kind):
- return False
- else:
- return True
- return Check(kind)
-
-
def AllEnumValues(enum):
"""Return all enum values associated with an enum.
@@ -232,171 +148,9 @@ def AllEnumValues(enum):
return set(field.numeric_value for field in enum.fields)
-def GetNativeTypeName(typemapped_kind):
- return _current_typemap[GetFullMojomNameForKind(typemapped_kind)]["typename"]
-
def GetCppPodType(kind):
return _kind_to_cpp_type[kind]
-def FormatConstantDeclaration(constant, nested=False):
- if mojom.IsStringKind(constant.kind):
- if nested:
- return "const char %s[]" % constant.name
- return "%sextern const char %s[]" % \
- ((_export_attribute + " ") if _export_attribute else "", constant.name)
- return "constexpr %s %s = %s" % (GetCppPodType(constant.kind), constant.name,
- ConstantValue(constant))
-
-def GetCppWrapperType(kind, add_same_module_namespaces=False):
- def _AddOptional(type_name):
- pattern = "WTF::Optional<%s>" if _for_blink else "base::Optional<%s>"
- return pattern % type_name
-
- if IsTypemappedKind(kind):
- type_name = GetNativeTypeName(kind)
- if (mojom.IsNullableKind(kind) and
- not _current_typemap[GetFullMojomNameForKind(kind)][
- "nullable_is_same_type"]):
- type_name = _AddOptional(type_name)
- return type_name
- if mojom.IsEnumKind(kind):
- return GetNameForKind(
- kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
- return "%sPtr" % GetNameForKind(
- kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsArrayKind(kind):
- pattern = "WTF::Vector<%s>" if _for_blink else "std::vector<%s>"
- if mojom.IsNullableKind(kind):
- pattern = _AddOptional(pattern)
- return pattern % GetCppWrapperType(
- kind.kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsMapKind(kind):
- pattern = ("WTF::HashMap<%s, %s>" if _for_blink else
- "std::unordered_map<%s, %s>")
- if mojom.IsNullableKind(kind):
- pattern = _AddOptional(pattern)
- return pattern % (
- GetCppWrapperType(
- kind.key_kind,
- add_same_module_namespaces=add_same_module_namespaces),
- GetCppWrapperType(
- kind.value_kind,
- add_same_module_namespaces=add_same_module_namespaces))
- if mojom.IsInterfaceKind(kind):
- return "%sPtr" % GetNameForKind(
- kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsInterfaceRequestKind(kind):
- return "%sRequest" % GetNameForKind(
- kind.kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsAssociatedInterfaceKind(kind):
- return "%sAssociatedPtrInfo" % GetNameForKind(
- kind.kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsAssociatedInterfaceRequestKind(kind):
- return "%sAssociatedRequest" % GetNameForKind(
- kind.kind, add_same_module_namespaces=add_same_module_namespaces)
- if mojom.IsStringKind(kind):
- if _for_blink:
- return "WTF::String"
- type_name = "std::string"
- return _AddOptional(type_name) if mojom.IsNullableKind(kind) else type_name
- if mojom.IsGenericHandleKind(kind):
- return "mojo::ScopedHandle"
- if mojom.IsDataPipeConsumerKind(kind):
- return "mojo::ScopedDataPipeConsumerHandle"
- if mojom.IsDataPipeProducerKind(kind):
- return "mojo::ScopedDataPipeProducerHandle"
- if mojom.IsMessagePipeKind(kind):
- return "mojo::ScopedMessagePipeHandle"
- if mojom.IsSharedBufferKind(kind):
- return "mojo::ScopedSharedBufferHandle"
- if not kind in _kind_to_cpp_type:
- raise Exception("Unrecognized kind %s" % kind.spec)
- return _kind_to_cpp_type[kind]
-
-def IsMoveOnlyKind(kind):
- if IsTypemappedKind(kind):
- if mojom.IsEnumKind(kind):
- return False
- return _current_typemap[GetFullMojomNameForKind(kind)]["move_only"]
- if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
- return True
- if mojom.IsArrayKind(kind):
- return IsMoveOnlyKind(kind.kind)
- if mojom.IsMapKind(kind):
- return IsMoveOnlyKind(kind.value_kind)
- if mojom.IsAnyHandleOrInterfaceKind(kind):
- return True
- return False
-
-def IsCopyablePassByValue(kind):
- if not IsTypemappedKind(kind):
- return False
- return _current_typemap[GetFullMojomNameForKind(kind)][
- "copyable_pass_by_value"]
-
-def ShouldPassParamByValue(kind):
- return ((not mojom.IsReferenceKind(kind)) or IsMoveOnlyKind(kind) or
- IsCopyablePassByValue(kind))
-
-def GetCppWrapperParamType(kind):
- cpp_wrapper_type = GetCppWrapperType(kind)
- return (cpp_wrapper_type if ShouldPassParamByValue(kind)
- else "const %s&" % cpp_wrapper_type)
-
-def GetCppFieldType(kind):
- if mojom.IsStructKind(kind):
- return ("mojo::internal::Pointer<%s>" %
- GetNameForKind(kind, internal=True))
- if mojom.IsUnionKind(kind):
- return "%s" % GetNameForKind(kind, internal=True)
- if mojom.IsArrayKind(kind):
- return ("mojo::internal::Pointer<mojo::internal::Array_Data<%s>>" %
- GetCppFieldType(kind.kind))
- if mojom.IsMapKind(kind):
- return ("mojo::internal::Pointer<mojo::internal::Map_Data<%s, %s>>" %
- (GetCppFieldType(kind.key_kind), GetCppFieldType(kind.value_kind)))
- if mojom.IsInterfaceKind(kind):
- return "mojo::internal::Interface_Data"
- if mojom.IsInterfaceRequestKind(kind):
- return "mojo::internal::Handle_Data"
- if mojom.IsAssociatedInterfaceKind(kind):
- return "mojo::internal::AssociatedInterface_Data"
- if mojom.IsAssociatedInterfaceRequestKind(kind):
- return "mojo::internal::AssociatedEndpointHandle_Data"
- if mojom.IsEnumKind(kind):
- return "int32_t"
- if mojom.IsStringKind(kind):
- return "mojo::internal::Pointer<mojo::internal::String_Data>"
- if mojom.IsAnyHandleKind(kind):
- return "mojo::internal::Handle_Data"
- return _kind_to_cpp_type[kind]
-
-def GetCppUnionFieldType(kind):
- if mojom.IsUnionKind(kind):
- return ("mojo::internal::Pointer<%s>" % GetNameForKind(kind, internal=True))
- return GetCppFieldType(kind)
-
-def GetUnionGetterReturnType(kind):
- if mojom.IsReferenceKind(kind):
- return "%s&" % GetCppWrapperType(kind)
- return GetCppWrapperType(kind)
-
-def GetUnionTraitGetterReturnType(kind):
- """Get field type used in UnionTraits template specialization.
-
- The type may be qualified as UnionTraits specializations live outside the
- namespace where e.g. structs are defined.
-
- Args:
- kind: {Kind} The type of the field.
-
- Returns:
- {str} The C++ type to use for the field.
- """
- if mojom.IsReferenceKind(kind):
- return "%s&" % GetCppWrapperType(kind, add_same_module_namespaces=True)
- return GetCppWrapperType(kind, add_same_module_namespaces=True)
def GetCppDataViewType(kind, qualified=False):
def _GetName(input_kind):
@@ -435,49 +189,10 @@ def GetCppDataViewType(kind, qualified=False):
return "mojo::ScopedSharedBufferHandle"
return _kind_to_cpp_type[kind]
+
def GetUnmappedTypeForSerializer(kind):
return GetCppDataViewType(kind, qualified=True)
-def TranslateConstants(token, kind):
- if isinstance(token, mojom.NamedValue):
- return GetNameForKind(token, flatten_nested_kind=True)
-
- if isinstance(token, mojom.BuiltinValue):
- if token.value == "double.INFINITY":
- return "std::numeric_limits<double>::infinity()"
- if token.value == "float.INFINITY":
- return "std::numeric_limits<float>::infinity()"
- if token.value == "double.NEGATIVE_INFINITY":
- return "-std::numeric_limits<double>::infinity()"
- if token.value == "float.NEGATIVE_INFINITY":
- return "-std::numeric_limits<float>::infinity()"
- if token.value == "double.NAN":
- return "std::numeric_limits<double>::quiet_NaN()"
- if token.value == "float.NAN":
- return "std::numeric_limits<float>::quiet_NaN()"
-
- if (kind is not None and mojom.IsFloatKind(kind)):
- return token if token.isdigit() else token + "f";
-
- # Per C++11, 2.14.2, the type of an integer literal is the first of the
- # corresponding list in Table 6 in which its value can be represented. In this
- # case, the list for decimal constants with no suffix is:
- # int, long int, long long int
- # The standard considers a program ill-formed if it contains an integer
- # literal that cannot be represented by any of the allowed types.
- #
- # As it turns out, MSVC doesn't bother trying to fall back to long long int,
- # so the integral constant -2147483648 causes it grief: it decides to
- # represent 2147483648 as an unsigned integer, and then warns that the unary
- # minus operator doesn't make sense on unsigned types. Doh!
- if kind == mojom.INT32 and token == "-2147483648":
- return "(-%d - 1) /* %s */" % (
- 2**31 - 1, "Workaround for MSVC bug; see https://crbug.com/445618")
-
- return "%s%s" % (token, _kind_to_cpp_literal_suffix.get(kind, ""))
-
-def ExpressionToText(value, kind=None):
- return TranslateConstants(value, kind)
def RequiresContextForDataView(kind):
for field in kind.fields:
@@ -485,6 +200,7 @@ def RequiresContextForDataView(kind):
return True
return False
+
def ShouldInlineStruct(struct):
# TODO(darin): Base this on the size of the wrapper class.
if len(struct.fields) > 4:
@@ -494,11 +210,6 @@ def ShouldInlineStruct(struct):
return False
return True
-def ContainsMoveOnlyMembers(struct):
- for field in struct.fields:
- if IsMoveOnlyKind(field.kind):
- return True
- return False
def ShouldInlineUnion(union):
return not any(
@@ -528,134 +239,11 @@ class StructConstructor(object):
yield (field, field in self._params)
-def GetStructConstructors(struct):
- """Returns a list of constructors for a struct.
-
- Params:
- struct: {Struct} The struct to return constructors for.
-
- Returns:
- {[StructConstructor]} A list of StructConstructors that should be generated
- for |struct|.
- """
- if not mojom.IsStructKind(struct):
- raise TypeError
- # Types that are neither copyable nor movable can't be passed to a struct
- # constructor so only generate a default constructor.
- if any(IsTypemappedKind(field.kind) and _current_typemap[
- GetFullMojomNameForKind(field.kind)]["non_copyable_non_movable"]
- for field in struct.fields):
- return [StructConstructor(struct.fields, [])]
-
- param_counts = [0]
- for version in struct.versions:
- if param_counts[-1] != version.num_fields:
- param_counts.append(version.num_fields)
-
- ordinal_fields = sorted(struct.fields, key=lambda field: field.ordinal)
- return (StructConstructor(struct.fields, ordinal_fields[:param_count])
- for param_count in param_counts)
-
-
-def GetContainerValidateParamsCtorArgs(kind):
- if mojom.IsStringKind(kind):
- expected_num_elements = 0
- element_is_nullable = False
- key_validate_params = "nullptr"
- element_validate_params = "nullptr"
- enum_validate_func = "nullptr"
- elif mojom.IsMapKind(kind):
- expected_num_elements = 0
- element_is_nullable = False
- key_validate_params = GetNewContainerValidateParams(mojom.Array(
- kind=kind.key_kind))
- element_validate_params = GetNewContainerValidateParams(mojom.Array(
- kind=kind.value_kind))
- enum_validate_func = "nullptr"
- else: # mojom.IsArrayKind(kind)
- expected_num_elements = generator.ExpectedArraySize(kind) or 0
- element_is_nullable = mojom.IsNullableKind(kind.kind)
- key_validate_params = "nullptr"
- element_validate_params = GetNewContainerValidateParams(kind.kind)
- if mojom.IsEnumKind(kind.kind):
- enum_validate_func = ("%s::Validate" %
- GetQualifiedNameForKind(kind.kind, internal=True,
- flatten_nested_kind=True))
- else:
- enum_validate_func = "nullptr"
-
- if enum_validate_func == "nullptr":
- if key_validate_params == "nullptr":
- return "%d, %s, %s" % (expected_num_elements,
- "true" if element_is_nullable else "false",
- element_validate_params)
- else:
- return "%s, %s" % (key_validate_params, element_validate_params)
- else:
- return "%d, %s" % (expected_num_elements, enum_validate_func)
-
-def GetNewContainerValidateParams(kind):
- if (not mojom.IsArrayKind(kind) and not mojom.IsMapKind(kind) and
- not mojom.IsStringKind(kind)):
- return "nullptr"
-
- return "new mojo::internal::ContainerValidateParams(%s)" % (
- GetContainerValidateParamsCtorArgs(kind))
-
class Generator(generator.Generator):
+ def __init__(self, *args, **kwargs):
+ super(Generator, self).__init__(*args, **kwargs)
- cpp_filters = {
- "all_enum_values": AllEnumValues,
- "constant_value": ConstantValue,
- "contains_handles_or_interfaces": mojom.ContainsHandlesOrInterfaces,
- "contains_move_only_members": ContainsMoveOnlyMembers,
- "cpp_wrapper_param_type": GetCppWrapperParamType,
- "cpp_data_view_type": GetCppDataViewType,
- "cpp_field_type": GetCppFieldType,
- "cpp_union_field_type": GetCppUnionFieldType,
- "cpp_pod_type": GetCppPodType,
- "cpp_union_getter_return_type": GetUnionGetterReturnType,
- "cpp_union_trait_getter_return_type": GetUnionTraitGetterReturnType,
- "cpp_wrapper_type": GetCppWrapperType,
- "default_value": DefaultValue,
- "expression_to_text": ExpressionToText,
- "format_constant_declaration": FormatConstantDeclaration,
- "get_container_validate_params_ctor_args":
- GetContainerValidateParamsCtorArgs,
- "get_name_for_kind": GetNameForKind,
- "get_pad": pack.GetPad,
- "get_qualified_name_for_kind": GetQualifiedNameForKind,
- "has_callbacks": mojom.HasCallbacks,
- "has_sync_methods": mojom.HasSyncMethods,
- "requires_context_for_data_view": RequiresContextForDataView,
- "should_inline": ShouldInlineStruct,
- "should_inline_union": ShouldInlineUnion,
- "is_array_kind": mojom.IsArrayKind,
- "is_enum_kind": mojom.IsEnumKind,
- "is_integral_kind": mojom.IsIntegralKind,
- "is_native_only_kind": IsNativeOnlyKind,
- "is_any_handle_kind": mojom.IsAnyHandleKind,
- "is_any_interface_kind": mojom.IsAnyInterfaceKind,
- "is_any_handle_or_interface_kind": mojom.IsAnyHandleOrInterfaceKind,
- "is_associated_kind": mojom.IsAssociatedKind,
- "is_hashable": IsHashableKind,
- "is_map_kind": mojom.IsMapKind,
- "is_nullable_kind": mojom.IsNullableKind,
- "is_object_kind": mojom.IsObjectKind,
- "is_reference_kind": mojom.IsReferenceKind,
- "is_string_kind": mojom.IsStringKind,
- "is_struct_kind": mojom.IsStructKind,
- "is_typemapped_kind": IsTypemappedKind,
- "is_union_kind": mojom.IsUnionKind,
- "passes_associated_kinds": mojom.PassesAssociatedKinds,
- "struct_constructors": GetStructConstructors,
- "stylize_method": generator.StudlyCapsToCamel,
- "under_to_camel": generator.UnderToCamel,
- "unmapped_type_for_serializer": GetUnmappedTypeForSerializer,
- "wtf_hash_fn_name_for_enum": GetWtfHashFnNameForEnum,
- }
-
- def GetExtraTraitsHeaders(self):
+ def _GetExtraTraitsHeaders(self):
extra_headers = set()
for typemap in self._GetAllUsedTypemaps():
extra_headers.update(typemap.get("traits_headers", []))
@@ -684,12 +272,12 @@ class Generator(generator.Generator):
AddKind(kind.key_kind)
AddKind(kind.value_kind)
else:
- name = GetFullMojomNameForKind(kind)
+ name = self._GetFullMojomNameForKind(kind)
if name in seen_types:
return
seen_types.add(name)
- typemap = _current_typemap.get(name, None)
+ typemap = self.typemap.get(name, None)
if typemap:
used_typemaps.append(typemap)
if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
@@ -707,14 +295,14 @@ class Generator(generator.Generator):
return used_typemaps
- def GetExtraPublicHeaders(self):
+ def _GetExtraPublicHeaders(self):
all_enums = list(self.module.enums)
for struct in self.module.structs:
all_enums.extend(struct.enums)
for interface in self.module.interfaces:
all_enums.extend(interface.enums)
- types = set(GetFullMojomNameForKind(typename)
+ types = set(self._GetFullMojomNameForKind(typename)
for typename in
self.module.structs + all_enums + self.module.unions)
headers = set()
@@ -733,7 +321,7 @@ class Generator(generator.Generator):
for param in method.parameters + (method.response_parameters or []):
yield param.kind
- def GetJinjaExports(self):
+ def _GetJinjaExports(self):
structs = self.GetStructs()
interfaces = self.GetInterfaces()
all_enums = list(self.module.enums)
@@ -754,8 +342,8 @@ class Generator(generator.Generator):
"unions": self.GetUnions(),
"interfaces": interfaces,
"variant": self.variant,
- "extra_traits_headers": self.GetExtraTraitsHeaders(),
- "extra_public_headers": self.GetExtraPublicHeaders(),
+ "extra_traits_headers": self._GetExtraTraitsHeaders(),
+ "extra_public_headers": self._GetExtraPublicHeaders(),
"for_blink": self.for_blink,
"use_once_callback": self.use_once_callback,
"export_attribute": self.export_attribute,
@@ -766,53 +354,455 @@ class Generator(generator.Generator):
def GetTemplatePrefix():
return "cpp_templates"
- @classmethod
- def GetFilters(cls):
- return cls.cpp_filters
+ def GetFilters(self):
+ cpp_filters = {
+ "all_enum_values": AllEnumValues,
+ "constant_value": self._ConstantValue,
+ "contains_handles_or_interfaces": mojom.ContainsHandlesOrInterfaces,
+ "contains_move_only_members": self._ContainsMoveOnlyMembers,
+ "cpp_wrapper_param_type": self._GetCppWrapperParamType,
+ "cpp_data_view_type": GetCppDataViewType,
+ "cpp_field_type": self._GetCppFieldType,
+ "cpp_union_field_type": self._GetCppUnionFieldType,
+ "cpp_pod_type": GetCppPodType,
+ "cpp_union_getter_return_type": self._GetUnionGetterReturnType,
+ "cpp_union_trait_getter_return_type": self._GetUnionTraitGetterReturnType,
+ "cpp_wrapper_type": self._GetCppWrapperType,
+ "default_value": self._DefaultValue,
+ "expression_to_text": self._ExpressionToText,
+ "format_constant_declaration": self._FormatConstantDeclaration,
+ "get_container_validate_params_ctor_args":
+ self._GetContainerValidateParamsCtorArgs,
+ "get_name_for_kind": self._GetNameForKind,
+ "get_pad": pack.GetPad,
+ "get_qualified_name_for_kind": self._GetQualifiedNameForKind,
+ "has_callbacks": mojom.HasCallbacks,
+ "has_sync_methods": mojom.HasSyncMethods,
+ "requires_context_for_data_view": RequiresContextForDataView,
+ "should_inline": ShouldInlineStruct,
+ "should_inline_union": ShouldInlineUnion,
+ "is_array_kind": mojom.IsArrayKind,
+ "is_enum_kind": mojom.IsEnumKind,
+ "is_integral_kind": mojom.IsIntegralKind,
+ "is_native_only_kind": IsNativeOnlyKind,
+ "is_any_handle_kind": mojom.IsAnyHandleKind,
+ "is_any_interface_kind": mojom.IsAnyInterfaceKind,
+ "is_any_handle_or_interface_kind": mojom.IsAnyHandleOrInterfaceKind,
+ "is_associated_kind": mojom.IsAssociatedKind,
+ "is_hashable": self._IsHashableKind,
+ "is_map_kind": mojom.IsMapKind,
+ "is_nullable_kind": mojom.IsNullableKind,
+ "is_object_kind": mojom.IsObjectKind,
+ "is_reference_kind": mojom.IsReferenceKind,
+ "is_string_kind": mojom.IsStringKind,
+ "is_struct_kind": mojom.IsStructKind,
+ "is_typemapped_kind": self._IsTypemappedKind,
+ "is_union_kind": mojom.IsUnionKind,
+ "passes_associated_kinds": mojom.PassesAssociatedKinds,
+ "struct_constructors": self._GetStructConstructors,
+ "under_to_camel": generator.UnderToCamel,
+ "unmapped_type_for_serializer": GetUnmappedTypeForSerializer,
+ "wtf_hash_fn_name_for_enum": GetWtfHashFnNameForEnum,
+ }
+ return cpp_filters
@UseJinja("module.h.tmpl")
- def GenerateModuleHeader(self):
- return self.GetJinjaExports()
+ def _GenerateModuleHeader(self):
+ return self._GetJinjaExports()
@UseJinja("module.cc.tmpl")
- def GenerateModuleSource(self):
- return self.GetJinjaExports()
+ def _GenerateModuleSource(self):
+ return self._GetJinjaExports()
@UseJinja("module-shared.h.tmpl")
- def GenerateModuleSharedHeader(self):
- return self.GetJinjaExports()
+ def _GenerateModuleSharedHeader(self):
+ return self._GetJinjaExports()
@UseJinja("module-shared-internal.h.tmpl")
- def GenerateModuleSharedInternalHeader(self):
- return self.GetJinjaExports()
+ def _GenerateModuleSharedInternalHeader(self):
+ return self._GetJinjaExports()
@UseJinja("module-shared.cc.tmpl")
- def GenerateModuleSharedSource(self):
- return self.GetJinjaExports()
+ def _GenerateModuleSharedSource(self):
+ return self._GetJinjaExports()
def GenerateFiles(self, args):
if self.generate_non_variant_code:
- self.Write(self.GenerateModuleSharedHeader(),
+ self.Write(self._GenerateModuleSharedHeader(),
self.MatchMojomFilePath("%s-shared.h" % self.module.name))
self.Write(
- self.GenerateModuleSharedInternalHeader(),
+ self._GenerateModuleSharedInternalHeader(),
self.MatchMojomFilePath("%s-shared-internal.h" % self.module.name))
- self.Write(self.GenerateModuleSharedSource(),
+ self.Write(self._GenerateModuleSharedSource(),
self.MatchMojomFilePath("%s-shared.cc" % self.module.name))
else:
- global _current_typemap
- _current_typemap = self.typemap
- global _for_blink
- _for_blink = self.for_blink
- global _use_once_callback
- _use_once_callback = self.use_once_callback
- global _variant
- _variant = self.variant
- global _export_attribute
- _export_attribute = self.export_attribute
suffix = "-%s" % self.variant if self.variant else ""
- self.Write(self.GenerateModuleHeader(),
+ self.Write(self._GenerateModuleHeader(),
self.MatchMojomFilePath("%s%s.h" % (self.module.name, suffix)))
self.Write(
- self.GenerateModuleSource(),
+ self._GenerateModuleSource(),
self.MatchMojomFilePath("%s%s.cc" % (self.module.name, suffix)))
+
+ def _ConstantValue(self, constant):
+ return self._ExpressionToText(constant.value, kind=constant.kind)
+
+ # TODO(yzshen): Revisit the default value feature. It was designed prior to
+ # custom type mapping.
+ def _DefaultValue(self, field):
+ if field.default:
+ if mojom.IsStructKind(field.kind):
+ assert field.default == "default"
+ if not self._IsTypemappedKind(field.kind):
+ return "%s::New()" % self._GetNameForKind(field.kind)
+ return self._ExpressionToText(field.default, kind=field.kind)
+ return ""
+
+ def _GetNameForKind(self, kind, internal=False, flatten_nested_kind=False,
+ add_same_module_namespaces=False):
+ return _NameFormatter(kind, self.variant).FormatForCpp(
+ internal=internal, flatten_nested_kind=flatten_nested_kind,
+ add_same_module_namespaces=add_same_module_namespaces)
+
+ def _GetQualifiedNameForKind(self, kind, internal=False,
+ flatten_nested_kind=False, include_variant=True):
+ return _NameFormatter(
+ kind, self.variant if include_variant else None).FormatForCpp(
+ internal=internal, add_same_module_namespaces=True,
+ flatten_nested_kind=flatten_nested_kind)
+
+ def _GetFullMojomNameForKind(self, kind):
+ return _NameFormatter(kind, self.variant).FormatForMojom()
+
+ def _IsTypemappedKind(self, kind):
+ return hasattr(kind, "name") and \
+ self._GetFullMojomNameForKind(kind) in self.typemap
+
+ def _IsHashableKind(self, kind):
+ """Check if the kind can be hashed.
+
+ Args:
+ kind: {Kind} The kind to check.
+
+ Returns:
+ {bool} True if a value of this kind can be hashed.
+ """
+ checked = set()
+ def Check(kind):
+ if kind.spec in checked:
+ return True
+ checked.add(kind.spec)
+ if mojom.IsNullableKind(kind):
+ return False
+ elif mojom.IsStructKind(kind):
+ if (self._IsTypemappedKind(kind) and
+ not self.typemap[self._GetFullMojomNameForKind(kind)]["hashable"]):
+ return False
+ return all(Check(field.kind) for field in kind.fields)
+ elif mojom.IsEnumKind(kind):
+ return not self._IsTypemappedKind(kind) or self.typemap[
+ self._GetFullMojomNameForKind(kind)]["hashable"]
+ elif mojom.IsUnionKind(kind):
+ return all(Check(field.kind) for field in kind.fields)
+ elif mojom.IsAnyHandleKind(kind):
+ return False
+ elif mojom.IsAnyInterfaceKind(kind):
+ return False
+ # TODO(tibell): Arrays and maps could be made hashable. We just don't have
+ # a use case yet.
+ elif mojom.IsArrayKind(kind):
+ return False
+ elif mojom.IsMapKind(kind):
+ return False
+ else:
+ return True
+ return Check(kind)
+
+ def _GetNativeTypeName(self, typemapped_kind):
+ return self.typemap[self._GetFullMojomNameForKind(typemapped_kind)][
+ "typename"]
+
+ def _FormatConstantDeclaration(self, constant, nested=False):
+ if mojom.IsStringKind(constant.kind):
+ if nested:
+ return "const char %s[]" % constant.name
+ return "%sextern const char %s[]" % \
+ ((self.export_attribute + " ") if self.export_attribute else "",
+ constant.name)
+ return "constexpr %s %s = %s" % (
+ GetCppPodType(constant.kind), constant.name,
+ self._ConstantValue(constant))
+
+ def _GetCppWrapperType(self, kind, add_same_module_namespaces=False):
+ def _AddOptional(type_name):
+ pattern = "WTF::Optional<%s>" if self.for_blink else "base::Optional<%s>"
+ return pattern % type_name
+
+ if self._IsTypemappedKind(kind):
+ type_name = self._GetNativeTypeName(kind)
+ if (mojom.IsNullableKind(kind) and
+ not self.typemap[self._GetFullMojomNameForKind(kind)][
+ "nullable_is_same_type"]):
+ type_name = _AddOptional(type_name)
+ return type_name
+ if mojom.IsEnumKind(kind):
+ return self._GetNameForKind(
+ kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
+ return "%sPtr" % self._GetNameForKind(
+ kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsArrayKind(kind):
+ pattern = "WTF::Vector<%s>" if self.for_blink else "std::vector<%s>"
+ if mojom.IsNullableKind(kind):
+ pattern = _AddOptional(pattern)
+ return pattern % self._GetCppWrapperType(
+ kind.kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsMapKind(kind):
+ pattern = ("WTF::HashMap<%s, %s>" if self.for_blink else
+ "std::unordered_map<%s, %s>")
+ if mojom.IsNullableKind(kind):
+ pattern = _AddOptional(pattern)
+ return pattern % (
+ self._GetCppWrapperType(
+ kind.key_kind,
+ add_same_module_namespaces=add_same_module_namespaces),
+ self._GetCppWrapperType(
+ kind.value_kind,
+ add_same_module_namespaces=add_same_module_namespaces))
+ if mojom.IsInterfaceKind(kind):
+ return "%sPtr" % self._GetNameForKind(
+ kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsInterfaceRequestKind(kind):
+ return "%sRequest" % self._GetNameForKind(
+ kind.kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsAssociatedInterfaceKind(kind):
+ return "%sAssociatedPtrInfo" % self._GetNameForKind(
+ kind.kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsAssociatedInterfaceRequestKind(kind):
+ return "%sAssociatedRequest" % self._GetNameForKind(
+ kind.kind, add_same_module_namespaces=add_same_module_namespaces)
+ if mojom.IsStringKind(kind):
+ if self.for_blink:
+ return "WTF::String"
+ type_name = "std::string"
+ return (_AddOptional(type_name) if mojom.IsNullableKind(kind)
+ else type_name)
+ if mojom.IsGenericHandleKind(kind):
+ return "mojo::ScopedHandle"
+ if mojom.IsDataPipeConsumerKind(kind):
+ return "mojo::ScopedDataPipeConsumerHandle"
+ if mojom.IsDataPipeProducerKind(kind):
+ return "mojo::ScopedDataPipeProducerHandle"
+ if mojom.IsMessagePipeKind(kind):
+ return "mojo::ScopedMessagePipeHandle"
+ if mojom.IsSharedBufferKind(kind):
+ return "mojo::ScopedSharedBufferHandle"
+ if not kind in _kind_to_cpp_type:
+ raise Exception("Unrecognized kind %s" % kind.spec)
+ return _kind_to_cpp_type[kind]
+
+ def _IsMoveOnlyKind(self, kind):
+ if self._IsTypemappedKind(kind):
+ if mojom.IsEnumKind(kind):
+ return False
+ return self.typemap[self._GetFullMojomNameForKind(kind)]["move_only"]
+ if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
+ return True
+ if mojom.IsArrayKind(kind):
+ return self._IsMoveOnlyKind(kind.kind)
+ if mojom.IsMapKind(kind):
+ return self._IsMoveOnlyKind(kind.value_kind)
+ if mojom.IsAnyHandleOrInterfaceKind(kind):
+ return True
+ return False
+
+ def _IsCopyablePassByValue(self, kind):
+ if not self._IsTypemappedKind(kind):
+ return False
+ return self.typemap[self._GetFullMojomNameForKind(kind)][
+ "copyable_pass_by_value"]
+
+ def _ShouldPassParamByValue(self, kind):
+ return ((not mojom.IsReferenceKind(kind)) or self._IsMoveOnlyKind(kind) or
+ self._IsCopyablePassByValue(kind))
+
+ def _GetCppWrapperParamType(self, kind):
+ cpp_wrapper_type = self._GetCppWrapperType(kind)
+ return (cpp_wrapper_type if self._ShouldPassParamByValue(kind)
+ else "const %s&" % cpp_wrapper_type)
+
+ def _GetCppFieldType(self, kind):
+ if mojom.IsStructKind(kind):
+ return ("mojo::internal::Pointer<%s>" %
+ self._GetNameForKind(kind, internal=True))
+ if mojom.IsUnionKind(kind):
+ return "%s" % self._GetNameForKind(kind, internal=True)
+ if mojom.IsArrayKind(kind):
+ return ("mojo::internal::Pointer<mojo::internal::Array_Data<%s>>" %
+ self._GetCppFieldType(kind.kind))
+ if mojom.IsMapKind(kind):
+ return ("mojo::internal::Pointer<mojo::internal::Map_Data<%s, %s>>" %
+ (self._GetCppFieldType(kind.key_kind),
+ self._GetCppFieldType(kind.value_kind)))
+ if mojom.IsInterfaceKind(kind):
+ return "mojo::internal::Interface_Data"
+ if mojom.IsInterfaceRequestKind(kind):
+ return "mojo::internal::Handle_Data"
+ if mojom.IsAssociatedInterfaceKind(kind):
+ return "mojo::internal::AssociatedInterface_Data"
+ if mojom.IsAssociatedInterfaceRequestKind(kind):
+ return "mojo::internal::AssociatedEndpointHandle_Data"
+ if mojom.IsEnumKind(kind):
+ return "int32_t"
+ if mojom.IsStringKind(kind):
+ return "mojo::internal::Pointer<mojo::internal::String_Data>"
+ if mojom.IsAnyHandleKind(kind):
+ return "mojo::internal::Handle_Data"
+ return _kind_to_cpp_type[kind]
+
+ def _GetCppUnionFieldType(self, kind):
+ if mojom.IsUnionKind(kind):
+ return ("mojo::internal::Pointer<%s>" %
+ self._GetNameForKind(kind, internal=True))
+ return self._GetCppFieldType(kind)
+
+ def _GetUnionGetterReturnType(self, kind):
+ if mojom.IsReferenceKind(kind):
+ return "%s&" % self._GetCppWrapperType(kind)
+ return self._GetCppWrapperType(kind)
+
+ def _GetUnionTraitGetterReturnType(self, kind):
+ """Get field type used in UnionTraits template specialization.
+
+ The type may be qualified as UnionTraits specializations live outside the
+ namespace where e.g. structs are defined.
+
+ Args:
+ kind: {Kind} The type of the field.
+
+ Returns:
+ {str} The C++ type to use for the field.
+ """
+ if mojom.IsReferenceKind(kind):
+ return "%s&" % self._GetCppWrapperType(kind,
+ add_same_module_namespaces=True)
+ return self._GetCppWrapperType(kind, add_same_module_namespaces=True)
+
+ def _TranslateConstants(self, token, kind):
+ if isinstance(token, mojom.NamedValue):
+ return self._GetNameForKind(token, flatten_nested_kind=True)
+
+ if isinstance(token, mojom.BuiltinValue):
+ if token.value == "double.INFINITY":
+ return "std::numeric_limits<double>::infinity()"
+ if token.value == "float.INFINITY":
+ return "std::numeric_limits<float>::infinity()"
+ if token.value == "double.NEGATIVE_INFINITY":
+ return "-std::numeric_limits<double>::infinity()"
+ if token.value == "float.NEGATIVE_INFINITY":
+ return "-std::numeric_limits<float>::infinity()"
+ if token.value == "double.NAN":
+ return "std::numeric_limits<double>::quiet_NaN()"
+ if token.value == "float.NAN":
+ return "std::numeric_limits<float>::quiet_NaN()"
+
+ if (kind is not None and mojom.IsFloatKind(kind)):
+ return token if token.isdigit() else token + "f";
+
+ # Per C++11, 2.14.2, the type of an integer literal is the first of the
+ # corresponding list in Table 6 in which its value can be represented. In
+ # this case, the list for decimal constants with no suffix is:
+ # int, long int, long long int
+ # The standard considers a program ill-formed if it contains an integer
+ # literal that cannot be represented by any of the allowed types.
+ #
+ # As it turns out, MSVC doesn't bother trying to fall back to long long int,
+ # so the integral constant -2147483648 causes it grief: it decides to
+ # represent 2147483648 as an unsigned integer, and then warns that the unary
+ # minus operator doesn't make sense on unsigned types. Doh!
+ if kind == mojom.INT32 and token == "-2147483648":
+ return "(-%d - 1) /* %s */" % (
+ 2**31 - 1, "Workaround for MSVC bug; see https://crbug.com/445618")
+
+ return "%s%s" % (token, _kind_to_cpp_literal_suffix.get(kind, ""))
+
+ def _ExpressionToText(self, value, kind=None):
+ return self._TranslateConstants(value, kind)
+
+ def _ContainsMoveOnlyMembers(self, struct):
+ for field in struct.fields:
+ if self._IsMoveOnlyKind(field.kind):
+ return True
+ return False
+
+ def _GetStructConstructors(self, struct):
+ """Returns a list of constructors for a struct.
+
+ Params:
+ struct: {Struct} The struct to return constructors for.
+
+ Returns:
+ {[StructConstructor]} A list of StructConstructors that should be
+ generated for |struct|.
+ """
+ if not mojom.IsStructKind(struct):
+ raise TypeError
+ # Types that are neither copyable nor movable can't be passed to a struct
+ # constructor so only generate a default constructor.
+ if any(self._IsTypemappedKind(field.kind) and self.typemap[
+ self._GetFullMojomNameForKind(field.kind)]["non_copyable_non_movable"]
+ for field in struct.fields):
+ return [StructConstructor(struct.fields, [])]
+
+ param_counts = [0]
+ for version in struct.versions:
+ if param_counts[-1] != version.num_fields:
+ param_counts.append(version.num_fields)
+
+ ordinal_fields = sorted(struct.fields, key=lambda field: field.ordinal)
+ return (StructConstructor(struct.fields, ordinal_fields[:param_count])
+ for param_count in param_counts)
+
+ def _GetContainerValidateParamsCtorArgs(self, kind):
+ if mojom.IsStringKind(kind):
+ expected_num_elements = 0
+ element_is_nullable = False
+ key_validate_params = "nullptr"
+ element_validate_params = "nullptr"
+ enum_validate_func = "nullptr"
+ elif mojom.IsMapKind(kind):
+ expected_num_elements = 0
+ element_is_nullable = False
+ key_validate_params = self._GetNewContainerValidateParams(mojom.Array(
+ kind=kind.key_kind))
+ element_validate_params = self._GetNewContainerValidateParams(mojom.Array(
+ kind=kind.value_kind))
+ enum_validate_func = "nullptr"
+ else: # mojom.IsArrayKind(kind)
+ expected_num_elements = generator.ExpectedArraySize(kind) or 0
+ element_is_nullable = mojom.IsNullableKind(kind.kind)
+ key_validate_params = "nullptr"
+ element_validate_params = self._GetNewContainerValidateParams(kind.kind)
+ if mojom.IsEnumKind(kind.kind):
+ enum_validate_func = ("%s::Validate" %
+ self._GetQualifiedNameForKind(kind.kind, internal=True,
+ flatten_nested_kind=True))
+ else:
+ enum_validate_func = "nullptr"
+
+ if enum_validate_func == "nullptr":
+ if key_validate_params == "nullptr":
+ return "%d, %s, %s" % (expected_num_elements,
+ "true" if element_is_nullable else "false",
+ element_validate_params)
+ else:
+ return "%s, %s" % (key_validate_params, element_validate_params)
+ else:
+ return "%d, %s" % (expected_num_elements, enum_validate_func)
+
+ def _GetNewContainerValidateParams(self, kind):
+ if (not mojom.IsArrayKind(kind) and not mojom.IsMapKind(kind) and
+ not mojom.IsStringKind(kind)):
+ return "nullptr"
+
+ return "new mojo::internal::ContainerValidateParams(%s)" % (
+ self._GetContainerValidateParamsCtorArgs(kind))
« no previous file with comments | « no previous file | mojo/public/tools/bindings/generators/mojom_java_generator.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698