1 // Copyright 2015 the V8 project authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef V8_FAST_ACCESSOR_ASSEMBLER_H_ 6 #define V8_FAST_ACCESSOR_ASSEMBLER_H_ 7 8 #include <stdint.h> 9 #include <memory> 10 #include <vector> 11 12 #include "include/v8-experimental.h" 13 #include "src/base/macros.h" 14 #include "src/zone/zone.h" 15 16 namespace v8 { 17 namespace internal { 18 19 class Code; 20 class CodeStubAssembler; 21 class Isolate; 22 template <typename T> 23 class MaybeHandle; 24 25 namespace compiler { 26 class Node; 27 class CodeAssemblerLabel; 28 class CodeAssemblerState; 29 class CodeAssemblerVariable; 30 } 31 32 // This interface "exports" an aggregated subset of RawMachineAssembler, for 33 // use by the API to implement Fast Dom Accessors. 34 // 35 // This interface is made for this single purpose only and does not attempt 36 // to implement a general purpose solution. If you need one, please look at 37 // RawMachineAssembler instead. 38 // 39 // The life cycle of a FastAccessorAssembler has two phases: 40 // - After creating the instance, you can call an arbitrary sequence of 41 // builder functions to build the desired function. 42 // - When done, you can Build() the accessor and query for the build results. 43 // 44 // You cannot call any result getters before Build() was called & successful; 45 // and you cannot call any builder functions after Build() was called. 46 class FastAccessorAssembler { 47 public: 48 typedef v8::experimental::FastAccessorBuilder::ValueId ValueId; 49 typedef v8::experimental::FastAccessorBuilder::LabelId LabelId; 50 typedef v8::FunctionCallback FunctionCallback; 51 52 explicit FastAccessorAssembler(Isolate* isolate); 53 ~FastAccessorAssembler(); 54 55 // Builder / assembler functions: 56 ValueId IntegerConstant(int int_constant); 57 ValueId GetReceiver(); 58 ValueId LoadInternalField(ValueId value_id, int field_no); 59 60 // Loads internal field and assumes the object is indeed a valid API object 61 // with the proper internal fields present. 62 // The intended use is to call this on an object whose structure has already 63 // been checked previously, e.g. the accessor's receiver, which is map-checked 64 // before the fast accessor is called on it. Using this on an arbitrary object 65 // will result in unsafe memory accesses. 66 ValueId LoadInternalFieldUnchecked(ValueId value_id, int field_no); 67 68 ValueId LoadValue(ValueId value_id, int offset); 69 ValueId LoadObject(ValueId value_id, int offset); 70 71 // Converts a machine integer to a SMI. 72 ValueId ToSmi(ValueId value_id); 73 74 // Builder / assembler functions for control flow. 75 void ReturnValue(ValueId value_id); 76 void CheckFlagSetOrReturnNull(ValueId value_id, int mask); 77 void CheckNotZeroOrReturnNull(ValueId value_id); 78 LabelId MakeLabel(); 79 void SetLabel(LabelId label_id); 80 void Goto(LabelId label_id); 81 void CheckNotZeroOrJump(ValueId value_id, LabelId label_id); 82 83 // C++ callback. 84 ValueId Call(FunctionCallback callback, ValueId arg); 85 86 // Assemble the code. 87 MaybeHandle<Code> Build(); 88 89 private: 90 ValueId FromRaw(compiler::Node* node); 91 LabelId FromRaw(compiler::CodeAssemblerLabel* label); 92 compiler::Node* FromId(ValueId value) const; 93 compiler::CodeAssemblerLabel* FromId(LabelId value) const; 94 95 void CheckIsJSObjectOrJump(ValueId value, LabelId label_id); 96 97 void Clear(); zone()98 Zone* zone() { return &zone_; } isolate()99 Isolate* isolate() const { return isolate_; } 100 101 Zone zone_; 102 Isolate* isolate_; 103 std::unique_ptr<compiler::CodeAssemblerState> assembler_state_; 104 std::unique_ptr<CodeStubAssembler> assembler_; 105 106 // To prevent exposing the RMA internals to the outside world, we'll map 107 // Node + Label pointers integers wrapped in ValueId and LabelId instances. 108 // These vectors maintain this mapping. 109 std::vector<compiler::Node*> nodes_; 110 std::vector<compiler::CodeAssemblerLabel*> labels_; 111 112 // Remember the current state for easy error checking. (We prefer to be 113 // strict as this class will be exposed at the API.) 114 enum { kBuilding, kBuilt, kError } state_; 115 116 DISALLOW_COPY_AND_ASSIGN(FastAccessorAssembler); 117 }; 118 119 } // namespace internal 120 } // namespace v8 121 122 #endif // V8_FAST_ACCESSOR_ASSEMBLER_H_ 123