diff options
author | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2018-08-28 15:28:34 +0200 |
---|---|---|
committer | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2018-08-28 13:54:51 +0000 |
commit | 2a19c63448c84c1805fb1a585c3651318bb86ca7 (patch) | |
tree | eb17888e8531aa6ee5e85721bd553b832a7e5156 /chromium/v8/src/compiler/code-assembler.h | |
parent | b014812705fc80bff0a5c120dfcef88f349816dc (diff) | |
download | qtwebengine-chromium-2a19c63448c84c1805fb1a585c3651318bb86ca7.tar.gz |
BASELINE: Update Chromium to 69.0.3497.70
Change-Id: I2b7b56e4e7a8b26656930def0d4575dc32b900a0
Reviewed-by: Allan Sandfeld Jensen <allan.jensen@qt.io>
Diffstat (limited to 'chromium/v8/src/compiler/code-assembler.h')
-rw-r--r-- | chromium/v8/src/compiler/code-assembler.h | 216 |
1 files changed, 160 insertions, 56 deletions
diff --git a/chromium/v8/src/compiler/code-assembler.h b/chromium/v8/src/compiler/code-assembler.h index 0e4f8ea5c81..6419140a745 100644 --- a/chromium/v8/src/compiler/code-assembler.h +++ b/chromium/v8/src/compiler/code-assembler.h @@ -35,6 +35,7 @@ class JSRegExpStringIterator; class JSWeakCollection; class JSWeakMap; class JSWeakSet; +class MaybeObject; class PromiseCapability; class PromiseFulfillReactionJobTask; class PromiseReaction; @@ -57,7 +58,9 @@ struct WordT : IntegralT { : MachineRepresentation::kWord64; }; -struct RawPtrT : WordT {}; +struct RawPtrT : WordT { + static constexpr MachineType kMachineType = MachineType::Pointer(); +}; template <class To> struct RawPtr : RawPtrT {}; @@ -275,7 +278,8 @@ HEAP_OBJECT_TEMPLATE_TYPE_LIST(OBJECT_TYPE_TEMPLATE_CASE) #undef OBJECT_TYPE_STRUCT_CASE #undef OBJECT_TYPE_TEMPLATE_CASE -Smi* CheckObjectType(Object* value, Smi* type, String* location); +Smi* CheckObjectType(Isolate* isolate, Object* value, Smi* type, + String* location); namespace compiler { @@ -361,6 +365,16 @@ struct types_have_common_values<UnionT<T1, T2>, UnionT<U1, U2>> { types_have_common_values<T2, U2>::value; }; +template <class T> +struct types_have_common_values<T, MaybeObject> { + static const bool value = types_have_common_values<T, Object>::value; +}; + +template <class T> +struct types_have_common_values<MaybeObject, T> { + static const bool value = types_have_common_values<Object, T>::value; +}; + // TNode<T> is an SSA value with the static type tag T, which is one of the // following: // - a subclass of internal::Object represents a tagged type @@ -434,7 +448,6 @@ class SloppyTNode : public TNode<T> { V(IntPtrLessThanOrEqual, BoolT, WordT, WordT) \ V(IntPtrGreaterThan, BoolT, WordT, WordT) \ V(IntPtrGreaterThanOrEqual, BoolT, WordT, WordT) \ - V(IntPtrEqual, BoolT, WordT, WordT) \ V(Uint32LessThan, BoolT, Word32T, Word32T) \ V(Uint32LessThanOrEqual, BoolT, Word32T, Word32T) \ V(Uint32GreaterThan, BoolT, Word32T, Word32T) \ @@ -442,13 +455,7 @@ class SloppyTNode : public TNode<T> { V(UintPtrLessThan, BoolT, WordT, WordT) \ V(UintPtrLessThanOrEqual, BoolT, WordT, WordT) \ V(UintPtrGreaterThan, BoolT, WordT, WordT) \ - V(UintPtrGreaterThanOrEqual, BoolT, WordT, WordT) \ - V(WordEqual, BoolT, WordT, WordT) \ - V(WordNotEqual, BoolT, WordT, WordT) \ - V(Word32Equal, BoolT, Word32T, Word32T) \ - V(Word32NotEqual, BoolT, Word32T, Word32T) \ - V(Word64Equal, BoolT, Word64T, Word64T) \ - V(Word64NotEqual, BoolT, Word64T, Word64T) + V(UintPtrGreaterThanOrEqual, BoolT, WordT, WordT) #define CODE_ASSEMBLER_BINARY_OP_LIST(V) \ CODE_ASSEMBLER_COMPARE_BINARY_OP_LIST(V) \ @@ -468,6 +475,7 @@ class SloppyTNode : public TNode<T> { V(Int32Add, Word32T, Word32T, Word32T) \ V(Int32AddWithOverflow, PAIR_TYPE(Int32T, BoolT), Int32T, Int32T) \ V(Int32Sub, Word32T, Word32T, Word32T) \ + V(Int32SubWithOverflow, PAIR_TYPE(Int32T, BoolT), Int32T, Int32T) \ V(Int32Mul, Word32T, Word32T, Word32T) \ V(Int32MulWithOverflow, PAIR_TYPE(Int32T, BoolT), Int32T, Int32T) \ V(Int32Div, Int32T, Int32T, Int32T) \ @@ -517,6 +525,8 @@ TNode<Float64T> Float64Add(TNode<Float64T> a, TNode<Float64T> b); V(ChangeInt32ToInt64, Int64T, Int32T) \ V(ChangeUint32ToFloat64, Float64T, Word32T) \ V(ChangeUint32ToUint64, Uint64T, Word32T) \ + V(BitcastInt32ToFloat32, Float32T, Word32T) \ + V(BitcastFloat32ToInt32, Word32T, Float32T) \ V(RoundFloat64ToInt32, Int32T, Float64T) \ V(RoundInt32ToFloat32, Int32T, Float32T) \ V(Float64SilenceNaN, Float64T, Float64T) \ @@ -557,7 +567,8 @@ class V8_EXPORT_PRIVATE CodeAssembler { explicit CodeAssembler(CodeAssemblerState* state) : state_(state) {} ~CodeAssembler(); - static Handle<Code> GenerateCode(CodeAssemblerState* state); + static Handle<Code> GenerateCode(CodeAssemblerState* state, + const AssemblerOptions& options); bool Is64() const; bool IsFloat64RoundUpSupported() const; @@ -592,6 +603,10 @@ class V8_EXPORT_PRIVATE CodeAssembler { template <class A> operator TNode<A>() { + static_assert( + !std::is_same<A, MaybeObject>::value, + "Can't cast to MaybeObject, use explicit conversion functions. "); + static_assert(types_have_common_values<A, PreviousType>::value, "Incompatible types: this cast can never succeed."); static_assert(std::is_convertible<TNode<A>, TNode<Object>>::value, @@ -603,12 +618,17 @@ class V8_EXPORT_PRIVATE CodeAssembler { "Unnecessary CAST: types are convertible."); #ifdef DEBUG if (FLAG_debug_code) { + if (std::is_same<PreviousType, MaybeObject>::value) { + code_assembler_->GenerateCheckMaybeObjectIsObject(node_, location_); + } Node* function = code_assembler_->ExternalConstant( ExternalReference::check_object_type()); - code_assembler_->CallCFunction3( - MachineType::AnyTagged(), MachineType::AnyTagged(), - MachineType::TaggedSigned(), MachineType::AnyTagged(), function, - node_, + Node* const isolate_ptr = code_assembler_->ExternalConstant( + ExternalReference::isolate_address(code_assembler_->isolate())); + code_assembler_->CallCFunction4( + MachineType::AnyTagged(), MachineType::Pointer(), + MachineType::AnyTagged(), MachineType::TaggedSigned(), + MachineType::AnyTagged(), function, isolate_ptr, node_, code_assembler_->SmiConstant( static_cast<int>(ObjectTypeOf<A>::value)), code_assembler_->StringConstant(location_)); @@ -668,9 +688,8 @@ class V8_EXPORT_PRIVATE CodeAssembler { #define CAST(x) Cast(x, "") #endif -#ifdef V8_EMBEDDED_BUILTINS - TNode<HeapObject> LookupConstant(Handle<HeapObject> object); - TNode<ExternalReference> LookupExternalReference(ExternalReference reference); +#ifdef DEBUG + void GenerateCheckMaybeObjectIsObject(Node* node, const char* location); #endif // Constants. @@ -702,6 +721,9 @@ class V8_EXPORT_PRIVATE CodeAssembler { TNode<BoolT> Int32FalseConstant() { return ReinterpretCast<BoolT>(Int32Constant(0)); } + TNode<BoolT> BoolConstant(bool value) { + return value ? Int32TrueConstant() : Int32FalseConstant(); + } bool ToInt32Constant(Node* node, int32_t& out_value); bool ToInt64Constant(Node* node, int64_t& out_value); @@ -720,6 +742,8 @@ class V8_EXPORT_PRIVATE CodeAssembler { return UncheckedCast<UintPtrT>(x); } + static constexpr int kTargetParameterIndex = -1; + Node* Parameter(int value); TNode<Context> GetJSContextParameter(); @@ -731,6 +755,8 @@ class V8_EXPORT_PRIVATE CodeAssembler { void ReturnIf(Node* condition, Node* value); + void ReturnRaw(Node* value); + void DebugAbort(Node* message); void DebugBreak(); void Unreachable(); @@ -753,9 +779,6 @@ class V8_EXPORT_PRIVATE CodeAssembler { Node* LoadFramePointer(); Node* LoadParentFramePointer(); - // Access to the roots pointer. - TNode<IntPtrT> LoadRootsPointer(); - // Access to the stack pointer Node* LoadStackPointer(); @@ -858,6 +881,18 @@ class V8_EXPORT_PRIVATE CodeAssembler { ReinterpretCast<WordT>(right)); } + TNode<BoolT> IntPtrEqual(SloppyTNode<WordT> left, SloppyTNode<WordT> right); + TNode<BoolT> WordEqual(SloppyTNode<WordT> left, SloppyTNode<WordT> right); + TNode<BoolT> WordNotEqual(SloppyTNode<WordT> left, SloppyTNode<WordT> right); + TNode<BoolT> Word32Equal(SloppyTNode<Word32T> left, + SloppyTNode<Word32T> right); + TNode<BoolT> Word32NotEqual(SloppyTNode<Word32T> left, + SloppyTNode<Word32T> right); + TNode<BoolT> Word64Equal(SloppyTNode<Word64T> left, + SloppyTNode<Word64T> right); + TNode<BoolT> Word64NotEqual(SloppyTNode<Word64T> left, + SloppyTNode<Word64T> right); + TNode<Int32T> Int32Add(TNode<Int32T> left, TNode<Int32T> right) { return Signed( Int32Add(static_cast<Node*>(left), static_cast<Node*>(right))); @@ -954,66 +989,88 @@ class V8_EXPORT_PRIVATE CodeAssembler { // Calls template <class... TArgs> - TNode<Object> CallRuntimeImpl(Runtime::FunctionId function, - SloppyTNode<Object> context, TArgs... args); - template <class... TArgs> TNode<Object> CallRuntime(Runtime::FunctionId function, SloppyTNode<Object> context, TArgs... args) { return CallRuntimeImpl(function, context, - implicit_cast<SloppyTNode<Object>>(args)...); + {implicit_cast<SloppyTNode<Object>>(args)...}); } template <class... TArgs> - TNode<Object> TailCallRuntimeImpl(Runtime::FunctionId function, - SloppyTNode<Object> context, TArgs... args); + TNode<Object> CallRuntimeWithCEntry(Runtime::FunctionId function, + TNode<Code> centry, + SloppyTNode<Object> context, + TArgs... args) { + return CallRuntimeWithCEntryImpl(function, centry, context, {args...}); + } + template <class... TArgs> - TNode<Object> TailCallRuntime(Runtime::FunctionId function, - SloppyTNode<Object> context, TArgs... args) { - return TailCallRuntimeImpl(function, context, - implicit_cast<SloppyTNode<Object>>(args)...); + void TailCallRuntime(Runtime::FunctionId function, + SloppyTNode<Object> context, TArgs... args) { + int argc = static_cast<int>(sizeof...(args)); + TNode<Int32T> arity = Int32Constant(argc); + return TailCallRuntimeImpl(function, arity, context, + {implicit_cast<SloppyTNode<Object>>(args)...}); + } + + template <class... TArgs> + void TailCallRuntime(Runtime::FunctionId function, TNode<Int32T> arity, + SloppyTNode<Object> context, TArgs... args) { + return TailCallRuntimeImpl(function, arity, context, + {implicit_cast<SloppyTNode<Object>>(args)...}); + } + + template <class... TArgs> + void TailCallRuntimeWithCEntry(Runtime::FunctionId function, + TNode<Code> centry, TNode<Object> context, + TArgs... args) { + int argc = sizeof...(args); + TNode<Int32T> arity = Int32Constant(argc); + return TailCallRuntimeWithCEntryImpl( + function, arity, centry, context, + {implicit_cast<SloppyTNode<Object>>(args)...}); } // // If context passed to CallStub is nullptr, it won't be passed to the stub. // - template <class... TArgs> - Node* CallStub(Callable const& callable, Node* context, TArgs... args) { - Node* target = HeapConstant(callable.code()); - return CallStub(callable.descriptor(), target, context, - implicit_cast<Node*>(args)...); + template <class T = Object, class... TArgs> + TNode<T> CallStub(Callable const& callable, SloppyTNode<Object> context, + TArgs... args) { + TNode<Code> target = HeapConstant(callable.code()); + return CallStub<T>(callable.descriptor(), target, context, args...); } - template <class... TArgs> - Node* CallStub(const CallInterfaceDescriptor& descriptor, Node* target, - Node* context, TArgs... args) { - return CallStubR(descriptor, 1, target, context, - implicit_cast<Node*>(args)...); + template <class T = Object, class... TArgs> + TNode<T> CallStub(const CallInterfaceDescriptor& descriptor, + SloppyTNode<Code> target, SloppyTNode<Object> context, + TArgs... args) { + return UncheckedCast<T>(CallStubR(descriptor, 1, target, context, args...)); } template <class... TArgs> Node* CallStubR(const CallInterfaceDescriptor& descriptor, size_t result_size, - Node* target, Node* context, TArgs... args); + SloppyTNode<Code> target, SloppyTNode<Object> context, + TArgs... args) { + return CallStubRImpl(descriptor, result_size, target, context, {args...}); + } Node* CallStubN(const CallInterfaceDescriptor& descriptor, size_t result_size, - int input_count, Node* const* inputs, - bool pass_context = true); + int input_count, Node* const* inputs); template <class... TArgs> - Node* TailCallStub(Callable const& callable, Node* context, TArgs... args) { - Node* target = HeapConstant(callable.code()); + void TailCallStub(Callable const& callable, SloppyTNode<Object> context, + TArgs... args) { + TNode<Code> target = HeapConstant(callable.code()); return TailCallStub(callable.descriptor(), target, context, args...); } template <class... TArgs> - Node* TailCallStub(const CallInterfaceDescriptor& descriptor, Node* target, - Node* context, TArgs... args) { - return TailCallStubImpl(descriptor, target, context, - implicit_cast<Node*>(args)...); + void TailCallStub(const CallInterfaceDescriptor& descriptor, + SloppyTNode<Code> target, SloppyTNode<Object> context, + TArgs... args) { + return TailCallStubImpl(descriptor, target, context, {args...}); } - template <class... TArgs> - Node* TailCallStubImpl(const CallInterfaceDescriptor& descriptor, - Node* target, Node* context, TArgs... args); template <class... TArgs> Node* TailCallBytecodeDispatch(const CallInterfaceDescriptor& descriptor, @@ -1021,8 +1078,23 @@ class V8_EXPORT_PRIVATE CodeAssembler { template <class... TArgs> Node* TailCallStubThenBytecodeDispatch( - const CallInterfaceDescriptor& descriptor, Node* context, Node* target, - TArgs... args); + const CallInterfaceDescriptor& descriptor, Node* target, Node* context, + TArgs... args) { + return TailCallStubThenBytecodeDispatchImpl(descriptor, target, context, + {args...}); + } + + // Tailcalls to the given code object with JSCall linkage. The JS arguments + // (including receiver) are supposed to be already on the stack. + // This is a building block for implementing trampoline stubs that are + // installed instead of code objects with JSCall linkage. + // Note that no arguments adaption is going on here - all the JavaScript + // arguments are left on the stack unmodified. Therefore, this tail call can + // only be used after arguments adaptation has been performed already. + TNode<Object> TailCallJSCode(TNode<Code> code, TNode<Context> context, + TNode<JSFunction> function, + TNode<Object> new_target, + TNode<Int32T> arg_count); template <class... TArgs> Node* CallJS(Callable const& callable, Node* context, Node* function, @@ -1131,7 +1203,39 @@ class V8_EXPORT_PRIVATE CodeAssembler { bool Word32ShiftIsSafe() const; PoisoningMitigationLevel poisoning_level() const; + bool IsJSFunctionCall() const; + private: + TNode<Object> CallRuntimeImpl(Runtime::FunctionId function, + TNode<Object> context, + std::initializer_list<TNode<Object>> args); + + TNode<Object> CallRuntimeWithCEntryImpl( + Runtime::FunctionId function, TNode<Code> centry, TNode<Object> context, + std::initializer_list<TNode<Object>> args); + + void TailCallRuntimeImpl(Runtime::FunctionId function, TNode<Int32T> arity, + TNode<Object> context, + std::initializer_list<TNode<Object>> args); + + void TailCallRuntimeWithCEntryImpl(Runtime::FunctionId function, + TNode<Int32T> arity, TNode<Code> centry, + TNode<Object> context, + std::initializer_list<TNode<Object>> args); + + void TailCallStubImpl(const CallInterfaceDescriptor& descriptor, + TNode<Code> target, TNode<Object> context, + std::initializer_list<Node*> args); + + Node* TailCallStubThenBytecodeDispatchImpl( + const CallInterfaceDescriptor& descriptor, Node* target, Node* context, + std::initializer_list<Node*> args); + + Node* CallStubRImpl(const CallInterfaceDescriptor& descriptor, + size_t result_size, SloppyTNode<Code> target, + SloppyTNode<Object> context, + std::initializer_list<Node*> args); + // These two don't have definitions and are here only for catching use cases // where the cast is not necessary. TNode<Int32T> Signed(TNode<Int32T> x); @@ -1276,7 +1380,7 @@ class V8_EXPORT_PRIVATE CodeAssemblerState { CodeAssemblerState(Isolate* isolate, Zone* zone, const CallInterfaceDescriptor& descriptor, Code::Kind kind, const char* name, PoisoningMitigationLevel poisoning_level, - size_t result_size = 1, uint32_t stub_key = 0, + uint32_t stub_key = 0, int32_t builtin_index = Builtins::kNoBuiltinId); // Create with JSCall linkage. |