Пример #1
0
def TranslateConstants(token, kind):
    if isinstance(token, mojom.NamedValue):
        # Both variable and enum constants are constructed like:
        # Namespace::Struct::CONSTANT_NAME
        # For enums, CONSTANT_NAME is ENUM_NAME_ENUM_VALUE.
        name = []
        if token.imported_from:
            name.extend(NamespaceToArray(token.namespace))
        if token.parent_kind:
            name.append(token.parent_kind.name)
        if isinstance(token, mojom.EnumValue):
            name.append(
                "%s_%s" %
                (generator.CamelCaseToAllCaps(token.enum.name), token.name))
        else:
            name.append(token.name)
        return "::".join(name)

    if isinstance(token, mojom.BuiltinValue):
        if token.value == "double.INFINITY" or token.value == "float.INFINITY":
            return "INFINITY"
        if token.value == "double.NEGATIVE_INFINITY" or \
           token.value == "float.NEGATIVE_INFINITY":
            return "-INFINITY"
        if token.value == "double.NAN" or token.value == "float.NAN":
            return "NAN"

    if (kind is not None and mojom.IsFloatKind(kind)):
        return token if token.isdigit() else token + "f"

    return '%s%s' % (token, _kind_to_cpp_literal_suffix.get(kind, ''))
Пример #2
0
def TranslateConstants(token, kind):
    if isinstance(token, mojom.NamedValue):
        return _NameFormatter(token, _variant).FormatForCpp()

    if isinstance(token, mojom.BuiltinValue):
        if token.value == "double.INFINITY" or token.value == "float.INFINITY":
            return "INFINITY"
        if token.value == "double.NEGATIVE_INFINITY" or \
           token.value == "float.NEGATIVE_INFINITY":
            return "-INFINITY"
        if token.value == "double.NAN" or token.value == "float.NAN":
            return "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, ""))
Пример #3
0
    def AddKind(kind):
      if (mojom.IsIntegralKind(kind) or mojom.IsStringKind(kind) or
          mojom.IsDoubleKind(kind) or mojom.IsFloatKind(kind) or
          mojom.IsAnyHandleKind(kind) or
          mojom.IsInterfaceKind(kind) or
          mojom.IsInterfaceRequestKind(kind) or
          mojom.IsAssociatedKind(kind) or
          mojom.IsPendingRemoteKind(kind) or
          mojom.IsPendingReceiverKind(kind)):
        pass
      elif mojom.IsArrayKind(kind):
        AddKind(kind.kind)
      elif mojom.IsMapKind(kind):
        AddKind(kind.key_kind)
        AddKind(kind.value_kind)
      else:
        name = self._GetFullMojomNameForKind(kind)
        if name in seen_types:
          return
        seen_types.add(name)

        typemap = self.typemap.get(name, None)
        if typemap:
          used_typemaps.append(typemap)
        if mojom.IsStructKind(kind) or mojom.IsUnionKind(kind):
          for field in kind.fields:
            AddKind(field.kind)
Пример #4
0
 def AddKind(kind):
     if (mojom.IsIntegralKind(kind) or mojom.IsStringKind(kind)
             or mojom.IsDoubleKind(kind) or mojom.IsFloatKind(kind)):
         pass
     elif (mojom.IsAnyHandleKind(kind)):
         self.needs_mojolpm_proto = True
     elif mojom.IsArrayKind(kind):
         AddKind(kind.kind)
     elif mojom.IsMapKind(kind):
         AddKind(kind.key_kind)
         AddKind(kind.value_kind)
     elif (mojom.IsStructKind(kind) or mojom.IsUnionKind(kind)
           or mojom.IsEnumKind(kind) or mojom.IsInterfaceKind(kind)):
         name = self._GetFullMojomNameForKind(kind)
         if name in seen_types:
             return
         seen_types.add(name)
         if kind.module in all_imports:
             seen_imports.add(kind.module)
     elif (mojom.IsInterfaceRequestKind(kind)
           or mojom.IsAssociatedInterfaceKind(kind)
           or mojom.IsAssociatedInterfaceRequestKind(kind)
           or mojom.IsPendingRemoteKind(kind)
           or mojom.IsPendingReceiverKind(kind)
           or mojom.IsPendingAssociatedRemoteKind(kind)
           or mojom.IsPendingAssociatedReceiverKind(kind)):
         AddKind(kind.kind)
Пример #5
0
 def _IsStringableKind(self, kind):
     # Indicates whether a kind of suitable to stringify and use as an Object
     # property name. This is checked for map key types to allow most kinds of
     # mojom maps to be represented as either a Map or an Object.
     return (mojom.IsIntegralKind(kind) or mojom.IsFloatKind(kind)
             or mojom.IsDoubleKind(kind) or mojom.IsStringKind(kind)
             or mojom.IsEnumKind(kind))
Пример #6
0
 def IsBasicKind(kind):
     return (mojom.IsIntegralKind(kind) or mojom.IsStringKind(kind)
             or mojom.IsDoubleKind(kind) or mojom.IsFloatKind(kind)
             or mojom.IsAnyHandleKind(kind)
             or mojom.IsInterfaceKind(kind)
             or mojom.IsInterfaceRequestKind(kind)
             or mojom.IsAssociatedKind(kind))
Пример #7
0
    def _WriteInputParamForTracing(self, kind, mojo_prefix, parameter_name,
                                   value):
        """Generates lines of C++ to log parameter |parameter_name| into TracedValue
    |value|.

    Args:
      kind: {Kind} The kind of the parameter (corresponds to its C++ type).
      mojo_prefix: {string} The prefix of the auto-generated parameter.
      parameter_name: {string} The mojom parameter name to be logged
        (auto-generated C++ parameter name is |mojo_prefix+parameter_name|).
      value: {string} The C++ TracedValue* variable name to be logged into.

    Yields:
      {string} C++ lines of code that trace |parameter_name| into |value|.
    """
        cpp_parameter_name = mojo_prefix + parameter_name
        value_name_cppname = (value, parameter_name, cpp_parameter_name)
        # TODO(crbug.com/1103623): Support more involved types.
        if mojom.IsEnumKind(kind):
            # TODO(crbug.com/1103623): Pretty-print enums.
            yield '%s->SetInteger("%s", static_cast<int>(%s));' % value_name_cppname
            return
        if mojom.IsStringKind(kind):
            if self.for_blink:
                # WTF::String is nullable on its own.
                yield '%s->SetString("%s", %s.Utf8());' % value_name_cppname
                return
            if mojom.IsNullableKind(kind):
                # base::Optional<std::string>
                yield 'if (%s.has_value()) {' % cpp_parameter_name
                yield '  %s->SetString("%s", %s.value());' % value_name_cppname
                yield '} else {'
                yield '  %s->SetString("%s", "base::nullopt");' % (
                    value, parameter_name)
                yield '}'
                return
            else:
                yield '%s->SetString("%s", %s);' % value_name_cppname
                return
        if kind == mojom.BOOL:
            yield '%s->SetBoolean("%s", %s);' % value_name_cppname
            return
        # TODO(crbug.com/1103623): Make TracedValue support int64_t, then move to
        # mojom.IsIntegralKind.
        if kind in [
                mojom.INT8, mojom.UINT8, mojom.INT16, mojom.UINT16, mojom.INT32
        ]:
            # Parameter is representable as 32bit int.
            yield '%s->SetInteger("%s", %s);' % value_name_cppname
            return
        if kind in [mojom.UINT32, mojom.INT64, mojom.UINT64]:
            yield '%s->SetString("%s", std::to_string(%s));' % value_name_cppname
            return
        if mojom.IsFloatKind(kind) or mojom.IsDoubleKind(kind):
            yield '%s->SetDouble("%s", %s);' % value_name_cppname
            return
        yield '%s->SetString("%s", "<value of type %s>");' % (
            value, parameter_name, self._GetCppWrapperParamType(kind))
Пример #8
0
 def _IsStringableKind(self, kind):
     # Indicates whether a kind of suitable to stringify and use as an Object
     # property name. This is checked for map key types to allow most kinds of
     # mojom maps to be represented as either a Map or an Object.
     if kind == mojom.INT64 or kind == mojom.UINT64:
         # JS BigInts are not stringable and cannot be used as Object property
         # names.
         return False
     return (mojom.IsIntegralKind(kind) or mojom.IsFloatKind(kind)
             or mojom.IsDoubleKind(kind) or mojom.IsStringKind(kind)
             or mojom.IsEnumKind(kind))
Пример #9
0
def TranslateConstants(token, kind):
    if isinstance(token, mojom.NamedValue):
        # Both variable and enum constants are constructed like:
        # Namespace::Struct::CONSTANT_NAME
        # For enums, CONSTANT_NAME is ENUM_NAME_ENUM_VALUE.
        name = []
        if token.imported_from:
            name.extend(NamespaceToArray(token.namespace))
        if token.parent_kind:
            name.append(token.parent_kind.name)
        if isinstance(token, mojom.EnumValue):
            name.append(
                "%s_%s" %
                (generator.CamelCaseToAllCaps(token.enum.name), token.name))
        else:
            name.append(token.name)
        return "::".join(name)

    if isinstance(token, mojom.BuiltinValue):
        if token.value == "double.INFINITY" or token.value == "float.INFINITY":
            return "INFINITY"
        if token.value == "double.NEGATIVE_INFINITY" or \
           token.value == "float.NEGATIVE_INFINITY":
            return "-INFINITY"
        if token.value == "double.NAN" or token.value == "float.NAN":
            return "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, ""))
Пример #10
0
    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"

        return "%s%s" % (token, _kind_to_cpp_literal_suffix.get(kind, ""))
Пример #11
0
def _WriteInputParamForTracingImpl(generator, kind, cpp_parameter_name,
                                   output_context):
  """Generates lines of C++ to log a parameter into TracedValue
  |output_context.value|. Use |output_context.name| if |output_context| is of
  inhereted type from _OutputContext.

  Args:
    kind: {Kind} The kind of the parameter (corresponds to its C++ type).
    cpp_parameter_name: {string} The actual C++ variable name corresponding to
      the mojom parameter |parameter_name|. Can be a valid C++ expression
      (e.g., dereferenced variable |"(*var)"|).
    output_context: {_OutputContext} Represents the TracedValue* variable to be
      written into. Possibly also holds the mojo parameter name corresponding to
      |cpp_parameter_name|.

  Yields:
    {string} C++ lines of code that trace a |cpp_parameter_name| into
      |output_context.value|.
  """

  def _WrapIfNullable(inner_lines):
    """Check if kind is nullable if so yield code to check whether it has
    value.

    Args:
      inner_lines: {function} Function taking single argument and returning
        iterable. If kind is nullable, yield from this method with
        |cpp_parameter_name+'.value()'| otherwise yield with the parameter
        |cpp_parameter_name|.

    Args from the surrounding method:
      kind
      cpp_parameter_name
      output_context.AddSingleValue
    """
    if mojom.IsNullableKind(kind):
      yield 'if (%s.has_value()) {' % cpp_parameter_name
      for line in inner_lines(cpp_parameter_name + '.value()'):
        yield '  ' + line
      yield '} else {'
      yield '  ' + output_context.AddSingleValue('String', '"base::nullopt"')
      yield '}'
    else:
      # |yield from| is introduced in Python3.3.
      for line in inner_lines(cpp_parameter_name):
        yield line

  # TODO(crbug.com/1103623): Support more involved types.
  if mojom.IsEnumKind(kind):
    if generator._IsTypemappedKind(kind) or IsNativeOnlyKind(kind):
      yield output_context.AddSingleValue(
          'Integer', 'static_cast<int>(%s)' % cpp_parameter_name)
    else:
      yield output_context.AddSingleValue(
          'String', 'base::trace_event::ValueToString(%s)' % cpp_parameter_name)
    return
  if mojom.IsStringKind(kind):
    if generator.for_blink:
      # WTF::String is nullable on its own.
      yield output_context.AddSingleValue('String',
                                          '%s.Utf8()' % cpp_parameter_name)
      return
    # The type might be base::Optional<std::string> or std::string.
    for line in _WrapIfNullable(lambda cpp_parameter_name: [
        output_context.AddSingleValue('String', cpp_parameter_name)
    ]):
      yield line
    return
  if kind == mojom.BOOL:
    yield output_context.AddSingleValue('Boolean', cpp_parameter_name)
    return
  # TODO(crbug.com/1103623): Make TracedValue support int64_t, then move to
  # mojom.IsIntegralKind.
  if kind in [mojom.INT8, mojom.UINT8, mojom.INT16, mojom.UINT16, mojom.INT32]:
    # Parameter is representable as 32bit int.
    yield output_context.AddSingleValue('Integer', cpp_parameter_name)
    return
  if kind in [mojom.UINT32, mojom.INT64, mojom.UINT64]:
    yield output_context.AddSingleValue(
        'String', 'base::NumberToString(%s)' % cpp_parameter_name)
    return
  if mojom.IsFloatKind(kind) or mojom.IsDoubleKind(kind):
    yield output_context.AddSingleValue('Double', cpp_parameter_name)
    return
  if (mojom.IsStructKind(kind) and not generator._IsTypemappedKind(kind)
      and not IsNativeOnlyKind(kind)):
    yield 'if (%s.is_null()) {' % cpp_parameter_name
    yield '  ' + output_context.AddSingleValue('String', '"nullptr"')
    yield '} else {'
    yield '  ' + output_context.BeginContainer('Dictionary')
    yield '  ' + output_context.AsValueInto(cpp_parameter_name)
    yield '  ' + output_context.EndContainer('Dictionary')
    yield '}'
    return

  if mojom.IsArrayKind(kind):
    iterator_name = 'item'
    loop_body = _WriteInputParamForTracingImpl(generator=generator,
                                               kind=kind.kind,
                                               cpp_parameter_name=iterator_name,
                                               output_context=_ArrayItem(
                                                   output_context.value))
    loop_generator = lambda cpp_parameter_name: output_context.TraceContainer(
        container_type='Array',
        iterator_name=iterator_name,
        container_name=cpp_parameter_name,
        loop_body=loop_body)
    # Array might be a nullable kind.
    for line in _WrapIfNullable(loop_generator):
      yield line
    return

  def _TraceEventToString(cpp_parameter_name=cpp_parameter_name, kind=kind):
    return 'base::trace_event::ValueToString(%s, "<value of type %s>")' % (
        cpp_parameter_name, generator._GetCppWrapperParamType(kind))

  if mojom.IsMapKind(kind):
    iterator_name = 'item'
    if generator.for_blink:
      # WTF::HashMap<,>
      key_access = '.key'
      value_access = '.value'
    else:
      # base::flat_map<,>
      key_access = '.first'
      value_access = '.second'
    loop_body = _WriteInputParamForTracingImpl(
        generator=generator,
        kind=kind.value_kind,
        cpp_parameter_name=iterator_name + value_access,
        output_context=_DictionaryItemWithCopiedKey(
            value=output_context.value,
            name=_TraceEventToString(cpp_parameter_name=iterator_name +
                                     key_access,
                                     kind=kind.key_kind)))
    loop_generator = lambda cpp_parameter_name: output_context.TraceContainer(
        container_type="Dictionary",
        iterator_name=iterator_name,
        container_name=cpp_parameter_name,
        loop_body=loop_body)
    # Dictionary might be a nullable kind.
    for line in _WrapIfNullable(loop_generator):
      yield line
    return
  if (mojom.IsInterfaceRequestKind(kind)
      or mojom.IsAssociatedInterfaceRequestKind(kind)):
    yield output_context.AddSingleValue('Boolean',
                                        cpp_parameter_name + '.is_pending()')
    return
  if (mojom.IsAnyHandleOrInterfaceKind(kind)
      and not mojom.IsInterfaceKind(kind)):
    yield output_context.AddSingleValue('Boolean',
                                        cpp_parameter_name + '.is_valid()')
    return
  """ The case |mojom.IsInterfaceKind(kind)| is not covered.
  |mojom.IsInterfaceKind(kind) == True| for the following types:
  |mojo::InterfacePtrInfo|, |mojo::InterfacePtr|.
    There is |mojo::InterfacePtrInfo::is_valid|,
      but not |mojo::InterfacePtrInfo::is_bound|.
    There is |mojo::InterfacePtr::is_bound|,
      but not |mojo::InterfacePtr::is_valid|.

  Both |mojo::InterfacePtrInfo| and |mojo::InterfacePtr| are deprecated.
  """
  yield output_context.AddSingleValue('String', _TraceEventToString())
Пример #12
0
def TranslateConstants(token, kind):
    if isinstance(token, mojom.NamedValue):
        # Both variable and enum constants are constructed like:
        # Namespace::Struct::CONSTANT_NAME
        # For enums, CONSTANT_NAME is ENUM_NAME_ENUM_VALUE.
        name = []
        if token.imported_from:
            name.extend(NamespaceToArray(token.namespace))
        if token.parent_kind:
            name.append(token.parent_kind.name)
        if IsEnumToken(token):
            name.extend([token.enum.name, token.name])
        else:
            name.append(token.name)

        ret = "::".join(name)

        # Explicitly disallow cases where we are translating an enum token for a
        # non-enum (but defined) kind.
        if IsEnumToken(
                token) and kind is not None and not mojom.IsEnumKind(kind):
            raise Exception(
                "Assignment of enum value '%s' to type %s is disallowed" %
                (ret, _kind_to_cpp_type.get(kind, "<unknown>")))

        # Explicitly disallow a non-enum token for an enum kind, we need an explicit
        # cast.
        if not IsEnumToken(token) and mojom.IsEnumKind(kind):
            raise Exception(
                "Assignment of non-enum value '%s' to enum-type %s is disallowed"
                % (ret, GetNameForKind(kind)))

        return ret

    if isinstance(token, mojom.BuiltinValue):
        if token.value == "double.INFINITY" or token.value == "float.INFINITY":
            return "INFINITY"
        if token.value == "double.NEGATIVE_INFINITY" or \
           token.value == "float.NEGATIVE_INFINITY":
            return "-INFINITY"
        if token.value == "double.NAN" or token.value == "float.NAN":
            return "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")

    ret = "%s%s" % (token, _kind_to_cpp_literal_suffix.get(kind, ""))

    # Literal tokens may not be assigned to enum variable.  By definition, the
    # only valid tokens for the RHS of an assignment to an enum named values
    # (specifically, members of the enumeration).
    if mojom.IsEnumKind(kind):
        raise Exception(
            "Assignment of literal '%s' to enum-type %s is disallowed" %
            (ret, GetNameForKind(kind)))

    return ret
Пример #13
0
 def _IsObjCNumberKind(self, kind):
     return (mojom.IsIntegralKind(kind) or mojom.IsDoubleKind(kind)
             or mojom.IsFloatKind(kind))