Commit 92614bc0 authored by Yuki Shiino's avatar Yuki Shiino Committed by Commit Bot

bind-gen: Clean up IDLNullable and NativeValutTraits<IDLNullable<T>>

Issue 798467: It's not yet clear what ImplType should be, but we
technically don't need both of ImplType and ResultType.  We can
implement IDLNullabe without ResultType.

At this moment, ImplType looks implementation helper used only by
IDLXxx and NativeValueTraits.  ImplType doesn't look a public API.

Issue 798470: It's reasonable that NullValue() is defined iff
type T can represent IDL null value.  We can tell whether
base::Optional is necessary or not by looking at existence of
NullValue().

Issue 798471: This patch requires NullValue() only in
NativeValueTraits and not in IDLXxx.  IDLXxx is a simple tag
type just like the original design.

Bug: 798467, 798470, 798471
Change-Id: I08e3cf54f3059ec308b4b455045c0bc1cfd5967b
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2002551
Commit-Queue: Yuki Shiino <yukishiino@chromium.org>
Reviewed-by: default avatarHitoshi Yoshida <peria@chromium.org>
Cr-Commit-Position: refs/heads/master@{#732345}
parent 8142143b
......@@ -8,12 +8,13 @@
#include <type_traits>
#include "base/optional.h"
#include "base/template_util.h"
#include "base/time/time.h"
#include "third_party/blink/renderer/bindings/core/v8/idl_types_base.h"
#include "third_party/blink/renderer/bindings/core/v8/native_value_traits.h"
#include "third_party/blink/renderer/bindings/core/v8/v8_string_resource.h"
#include "third_party/blink/renderer/platform/heap/handle.h"
#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h"
#include "third_party/blink/renderer/platform/wtf/forward.h"
#include "third_party/blink/renderer/platform/wtf/vector.h"
namespace blink {
......@@ -22,6 +23,9 @@ class EventListener;
class ScriptPromise;
class ScriptValue;
// The type names below are named as "IDL" prefix + Web IDL type name.
// https://heycam.github.io/webidl/#dfn-type-name
// Boolean
struct IDLBoolean final : public IDLBaseHelper<bool> {};
......@@ -144,6 +148,10 @@ struct IDLSequence final : public IDLBase {
using ImplType = VectorOf<typename NativeValueTraits<T>::ImplType>;
};
// Frozen array types
template <typename T>
using IDLArray = IDLSequence<T>;
// Record
template <typename Key, typename Value>
struct IDLRecord final : public IDLBase {
......@@ -156,45 +164,25 @@ struct IDLRecord final : public IDLBase {
VectorOfPairs<String, typename NativeValueTraits<Value>::ImplType>;
};
// Nullable (T?).
// https://heycam.github.io/webidl/#idl-nullable-type
// Types without a built-in notion of nullability are mapped to
// base::Optional<T>.
template <typename InnerType, typename = void>
// Nullable
template <typename InnerType, typename SFINAEHelper = void>
struct IDLNullable final : public IDLBase {
private:
using InnerTraits = NativeValueTraits<InnerType>;
using InnerResultType =
decltype(InnerTraits::NativeValue(std::declval<v8::Isolate*>(),
v8::Local<v8::Value>(),
std::declval<ExceptionState&>()));
public:
using ResultType = base::Optional<std::decay_t<InnerResultType>>;
using ImplType = ResultType;
static inline ResultType NullValue() { return base::nullopt; }
using ImplType =
base::Optional<typename NativeValueTraits<InnerType>::ImplType>;
};
template <typename InnerType>
struct IDLNullable<InnerType,
decltype(void(NativeValueTraits<InnerType>::NullValue()))>
struct IDLNullable<
InnerType,
base::void_t<decltype(NativeValueTraits<InnerType>::NullValue)>>
final : public IDLBase {
private:
using InnerTraits = NativeValueTraits<InnerType>;
using InnerResultType =
decltype(InnerTraits::NativeValue(std::declval<v8::Isolate*>(),
v8::Local<v8::Value>(),
std::declval<ExceptionState&>()));
public:
using ResultType = InnerResultType;
using ImplType = typename InnerTraits::ImplType;
static inline ResultType NullValue() { return InnerTraits::NullValue(); }
using ImplType = typename NativeValueTraits<InnerType>::ImplType;
};
// EventHandler types
struct IDLEventHandler : public IDLBaseHelper<EventListener*> {};
struct IDLOnBeforeUnloadEventHandler : public IDLBaseHelper<EventListener*> {};
struct IDLOnErrorEventHandler : public IDLBaseHelper<EventListener*> {};
struct IDLEventHandler final : public IDLBaseHelper<EventListener> {};
struct IDLOnBeforeUnloadEventHandler final
: public IDLBaseHelper<EventListener> {};
struct IDLOnErrorEventHandler final : public IDLBaseHelper<EventListener> {};
} // namespace blink
......
......@@ -7,7 +7,7 @@
namespace blink {
// This is the base type for all WebIDL types, such as the ones defined in
// This is the base type for all Web IDL types, such as the ones defined in
// idl_types.h. It is defined in a separate location to avoid circular header
// inclusions when one only needs to check if a type inherits from IDLBase.
struct IDLBase {
......@@ -18,7 +18,7 @@ struct IDLBase {
// can inherit from IDLBaseHelper to avoid having to set ImplType on its own.
//
// Example:
// struct MyType<double> final : public IDLBaseHelper<double> {};
// struct IDLDouble final : public IDLBaseHelper<double> {};
template <typename T>
struct IDLBaseHelper : public IDLBase {
using ImplType = T;
......
......@@ -5,6 +5,7 @@
#include "third_party/blink/renderer/bindings/core/v8/idl_types.h"
#include <type_traits>
#include "third_party/blink/renderer/bindings/core/v8/native_value_traits_impl.h"
#include "third_party/blink/renderer/bindings/core/v8/string_or_string_sequence.h"
#include "third_party/blink/renderer/bindings/core/v8/v8_element.h"
......@@ -142,14 +143,14 @@ static_assert(
static_assert(std::is_base_of<IDLBase, IDLNullable<IDLDouble>>::value,
"IDLNullable should have IDLBase as a base class");
static_assert(std::is_same<IDLNullable<IDLDouble>::ResultType,
static_assert(std::is_same<IDLNullable<IDLDouble>::ImplType,
base::Optional<double>>::value,
"double? corresponds to base::Optional<double>");
static_assert(std::is_same<IDLNullable<Element>::ResultType, Element*>::value,
static_assert(std::is_same<IDLNullable<Element>::ImplType, Element>::value,
"Element? doesn't require a base::Optional<> wrapper");
static_assert(std::is_same<IDLNullable<IDLString>::ResultType, String>::value,
static_assert(std::is_same<IDLNullable<IDLString>::ImplType, String>::value,
"DOMString? doesn't require a base::Optional<> wrapper");
static_assert(std::is_same<IDLNullable<StringOrStringSequence>::ResultType,
static_assert(std::is_same<IDLNullable<StringOrStringSequence>::ImplType,
StringOrStringSequence>::value,
"(union type)? doesn't require a base::Optional<> wrapper");
......
......@@ -893,6 +893,8 @@ struct NativeValueTraits<
<< "is not yet implemented.";
return nullptr;
}
static constexpr T* NullValue() { return nullptr; }
};
// Dictionary
......@@ -907,6 +909,8 @@ struct NativeValueTraits<
ExceptionState& exception_state) {
return T::Create(isolate, value, exception_state);
}
static constexpr T* NullValue() { return nullptr; }
};
// Interface
......@@ -937,24 +941,49 @@ struct NativeValueTraits<
};
// Nullable
//
// Types without a built-in notion of nullability are mapped to
// base::Optional<T>.
template <typename InnerType>
struct NativeValueTraits<IDLNullable<InnerType>>
: public NativeValueTraitsBase<IDLNullable<InnerType>> {
// https://heycam.github.io/webidl/#es-nullable-type
static typename IDLNullable<InnerType>::ResultType NativeValue(
v8::Isolate* isolate,
v8::Local<v8::Value> v8_value,
ExceptionState& exception_state) {
if (v8_value->IsNullOrUndefined())
return IDLNullable<InnerType>::NullValue();
return NativeValueTraits<InnerType>::NativeValue(isolate, v8_value,
using ImplType =
base::Optional<typename NativeValueTraits<InnerType>::ImplType>;
static ImplType NativeValue(v8::Isolate* isolate,
v8::Local<v8::Value> value,
ExceptionState& exception_state) {
if (value->IsNullOrUndefined())
return base::nullopt;
return NativeValueTraits<InnerType>::NativeValue(isolate, value,
exception_state);
}
};
template <typename InnerType>
struct NativeValueTraits<
IDLNullable<InnerType>,
base::void_t<decltype(NativeValueTraits<InnerType>::NullValue)>>
: public NativeValueTraitsBase<IDLNullable<InnerType>> {
// https://heycam.github.io/webidl/#es-nullable-type
using ImplType = typename NativeValueTraits<InnerType>::ImplType;
static decltype(auto) NativeValue(v8::Isolate* isolate,
v8::Local<v8::Value> value,
ExceptionState& exception_state) {
if (value->IsNullOrUndefined())
return NativeValueTraits<InnerType>::NullValue();
return NativeValueTraits<InnerType>::NativeValue(isolate, value,
exception_state);
}
};
// IDLNullable<IDLNullable<T>> must not be used.
template <typename T>
struct NativeValueTraits<IDLNullable<IDLNullable<T>>>;
// EventHandler
template <>
struct NativeValueTraits<IDLEventHandler>
struct CORE_EXPORT NativeValueTraits<IDLEventHandler>
: public NativeValueTraitsBase<IDLEventHandler> {
static EventListener* NativeValue(v8::Isolate* isolate,
v8::Local<v8::Value> value,
......@@ -962,7 +991,7 @@ struct NativeValueTraits<IDLEventHandler>
};
template <>
struct NativeValueTraits<IDLOnBeforeUnloadEventHandler>
struct CORE_EXPORT NativeValueTraits<IDLOnBeforeUnloadEventHandler>
: public NativeValueTraitsBase<IDLOnBeforeUnloadEventHandler> {
static EventListener* NativeValue(v8::Isolate* isolate,
v8::Local<v8::Value> value,
......@@ -970,13 +999,22 @@ struct NativeValueTraits<IDLOnBeforeUnloadEventHandler>
};
template <>
struct NativeValueTraits<IDLOnErrorEventHandler>
struct CORE_EXPORT NativeValueTraits<IDLOnErrorEventHandler>
: public NativeValueTraitsBase<IDLOnErrorEventHandler> {
static EventListener* NativeValue(v8::Isolate* isolate,
v8::Local<v8::Value> value,
ExceptionState& exception_state);
};
// EventHandler and its family are nullable, so IDLNullable<IDLEventHandler>
// must not be used.
template <>
struct NativeValueTraits<IDLNullable<IDLEventHandler>>;
template <>
struct NativeValueTraits<IDLNullable<IDLOnBeforeUnloadEventHandler>>;
template <>
struct NativeValueTraits<IDLNullable<IDLOnErrorEventHandler>>;
} // namespace blink
#endif // THIRD_PARTY_BLINK_RENDERER_BINDINGS_CORE_V8_NATIVE_VALUE_TRAITS_IMPL_H_
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment