1 /* 2 * Copyright (c) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef PANDA_RUNTIME_INTERPRETER_INSTRUCTION_HANDLER_STATE_H_ 17 #define PANDA_RUNTIME_INTERPRETER_INSTRUCTION_HANDLER_STATE_H_ 18 19 #include "runtime/interpreter/state.h" 20 #include "runtime/jit/profiling_data.h" 21 22 namespace panda::interpreter { 23 24 class InstructionHandlerState { 25 public: InstructionHandlerState(ManagedThread * thread,const uint8_t * pc,Frame * frame)26 ALWAYS_INLINE InstructionHandlerState(ManagedThread *thread, const uint8_t *pc, Frame *frame) 27 : state_(thread, pc, frame) 28 { 29 instructions_ = GetFrame()->GetInstruction(); 30 } 31 ~InstructionHandlerState() = default; 32 DEFAULT_MOVE_SEMANTIC(InstructionHandlerState); 33 DEFAULT_COPY_SEMANTIC(InstructionHandlerState); 34 UpdateInstructionHandlerState(const uint8_t * pc,Frame * frame)35 ALWAYS_INLINE void UpdateInstructionHandlerState(const uint8_t *pc, Frame *frame) 36 { 37 state_.UpdateState(pc, frame); 38 instructions_ = GetFrame()->GetInstruction(); 39 } 40 GetThread()41 ALWAYS_INLINE ManagedThread *GetThread() const 42 { 43 return state_.GetThread(); 44 } 45 SetThread(ManagedThread * thread)46 ALWAYS_INLINE void SetThread(ManagedThread *thread) 47 { 48 state_.SetThread(thread); 49 } 50 SetInst(BytecodeInstruction inst)51 ALWAYS_INLINE void SetInst(BytecodeInstruction inst) 52 { 53 state_.SetInst(inst); 54 } 55 GetFrame()56 ALWAYS_INLINE Frame *GetFrame() const 57 { 58 return state_.GetFrame(); 59 } 60 SetFrame(Frame * frame)61 ALWAYS_INLINE void SetFrame(Frame *frame) 62 { 63 state_.SetFrame(frame); 64 } 65 GetDispatchTable()66 ALWAYS_INLINE const void *const *GetDispatchTable() const 67 { 68 return state_.GetDispatchTable(); 69 } 70 SetDispatchTable(const void * const * dispatch_table)71 ALWAYS_INLINE void SetDispatchTable(const void *const *dispatch_table) 72 { 73 return state_.SetDispatchTable(dispatch_table); 74 } 75 SaveState()76 ALWAYS_INLINE void SaveState() 77 { 78 state_.SaveState(); 79 } 80 RestoreState()81 ALWAYS_INLINE void RestoreState() 82 { 83 state_.RestoreState(); 84 } 85 GetOpcodeExtension()86 ALWAYS_INLINE uint16_t GetOpcodeExtension() const 87 { 88 return opcode_extension_; 89 } 90 SetOpcodeExtension(uint16_t opcode_extension)91 ALWAYS_INLINE void SetOpcodeExtension(uint16_t opcode_extension) 92 { 93 opcode_extension_ = opcode_extension; 94 } 95 GetPrimaryOpcode()96 ALWAYS_INLINE uint8_t GetPrimaryOpcode() const 97 { 98 return static_cast<unsigned>(GetInst().GetOpcode()) & 0xff; 99 } 100 GetSecondaryOpcode()101 ALWAYS_INLINE uint8_t GetSecondaryOpcode() const 102 { 103 return (static_cast<unsigned>(GetInst().GetOpcode()) >> 8) & 0xff; 104 } 105 IsPrimaryOpcodeValid()106 ALWAYS_INLINE bool IsPrimaryOpcodeValid() const 107 { 108 return GetInst().IsPrimaryOpcodeValid(); 109 } 110 GetInst()111 ALWAYS_INLINE BytecodeInstruction GetInst() const 112 { 113 return state_.GetInst(); 114 } 115 GetAcc()116 ALWAYS_INLINE const AccVRegister &GetAcc() const 117 { 118 return state_.GetAcc(); 119 } 120 GetAcc()121 ALWAYS_INLINE AccVRegister &GetAcc() 122 { 123 return state_.GetAcc(); 124 } 125 GetFakeInstBuf()126 ALWAYS_INLINE auto &GetFakeInstBuf() 127 { 128 return fake_inst_buf_; 129 } 130 GetBytecodeOffset()131 ALWAYS_INLINE uint32_t GetBytecodeOffset() const 132 { 133 return GetInst().GetAddress() - instructions_; 134 } 135 136 private: 137 static constexpr size_t FAKE_INST_BUF_SIZE = 4; 138 139 State state_; 140 std::array<uint8_t, FAKE_INST_BUF_SIZE> fake_inst_buf_; 141 uint16_t opcode_extension_ {0}; 142 const uint8_t *instructions_ {nullptr}; 143 }; 144 145 } // namespace panda::interpreter 146 147 #endif // PANDA_RUNTIME_INTERPRETER_INSTRUCTION_HANDLER_STATE_H_ 148