LCOV - code coverage report
Current view: top level - src/wasm - wasm-interpreter.h (source / functions) Hit Total Coverage
Test: app.info Lines: 1 1 100.0 %
Date: 2019-04-17 Functions: 0 0 -

          Line data    Source code
       1             : // Copyright 2016 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_WASM_WASM_INTERPRETER_H_
       6             : #define V8_WASM_WASM_INTERPRETER_H_
       7             : 
       8             : #include "src/wasm/wasm-opcodes.h"
       9             : #include "src/wasm/wasm-value.h"
      10             : #include "src/zone/zone-containers.h"
      11             : 
      12             : namespace v8 {
      13             : 
      14             : namespace internal {
      15             : class WasmInstanceObject;
      16             : 
      17             : namespace wasm {
      18             : 
      19             : // Forward declarations.
      20             : struct ModuleWireBytes;
      21             : struct WasmFunction;
      22             : struct WasmModule;
      23             : class WasmInterpreterInternals;
      24             : 
      25             : using pc_t = size_t;
      26             : using sp_t = size_t;
      27             : using pcdiff_t = int32_t;
      28             : using spdiff_t = uint32_t;
      29             : 
      30             : constexpr pc_t kInvalidPc = 0x80000000;
      31             : 
      32             : struct ControlTransferEntry {
      33             :   // Distance from the instruction to the label to jump to (forward, but can be
      34             :   // negative).
      35             :   pcdiff_t pc_diff;
      36             :   // Delta by which to decrease the stack height.
      37             :   spdiff_t sp_diff;
      38             :   // Arity of the block we jump to.
      39             :   uint32_t target_arity;
      40             : };
      41             : 
      42             : using ControlTransferMap = ZoneMap<pc_t, ControlTransferEntry>;
      43             : 
      44             : // Representation of frames within the interpreter.
      45             : //
      46             : // Layout of a frame:
      47             : // -----------------
      48             : // stack slot #N  ‾\.
      49             : // ...             |  stack entries: GetStackHeight(); GetStackValue()
      50             : // stack slot #0  _/·
      51             : // local #L       ‾\.
      52             : // ...             |  locals: GetLocalCount(); GetLocalValue()
      53             : // local #P+1      |
      54             : // param #P        |   ‾\.
      55             : // ...             |    | parameters: GetParameterCount(); GetLocalValue()
      56             : // param #0       _/·  _/·
      57             : // -----------------
      58             : //
      59             : class V8_EXPORT_PRIVATE InterpretedFrame {
      60             :  public:
      61             :   const WasmFunction* function() const;
      62             :   int pc() const;
      63             : 
      64             :   int GetParameterCount() const;
      65             :   int GetLocalCount() const;
      66             :   int GetStackHeight() const;
      67             :   WasmValue GetLocalValue(int index) const;
      68             :   WasmValue GetStackValue(int index) const;
      69             : 
      70             :  private:
      71             :   friend class WasmInterpreter;
      72             :   // Don't instante InterpretedFrames; they will be allocated as
      73             :   // InterpretedFrameImpl in the interpreter implementation.
      74             :   InterpretedFrame() = delete;
      75             :   DISALLOW_COPY_AND_ASSIGN(InterpretedFrame);
      76             : };
      77             : 
      78             : // Deleter struct to delete the underlying InterpretedFrameImpl without
      79             : // violating language specifications.
      80             : struct V8_EXPORT_PRIVATE InterpretedFrameDeleter {
      81             :   void operator()(InterpretedFrame* ptr);
      82             : };
      83             : 
      84             : // An interpreter capable of executing WebAssembly.
      85             : class V8_EXPORT_PRIVATE WasmInterpreter {
      86             :  public:
      87             :   // State machine for a Thread:
      88             :   //    +----------------------------------------------------------+
      89             :   //    |                    +--------Run()/Step()---------+       |
      90             :   //    V                    V                             |       |
      91             :   // STOPPED ---Run()-->  RUNNING  ------Pause()-----+-> PAUSED <--+
      92             :   //    ^                 | | | |                   /              |
      93             :   //    +--- Exception ---+ | | +--- Breakpoint ---+       RaiseException() <--+
      94             :   //                        | |                                                |
      95             :   //                        | +---------- Trap --------------> TRAPPED --------+
      96             :   //                        +----------- Finish -------------> FINISHED
      97             :   enum State { STOPPED, RUNNING, PAUSED, FINISHED, TRAPPED };
      98             : 
      99             :   // Tells a thread to pause after certain instructions.
     100             :   enum BreakFlag : uint8_t {
     101             :     None = 0,
     102             :     AfterReturn = 1 << 0,
     103             :     AfterCall = 1 << 1
     104             :   };
     105             : 
     106             :   using FramePtr = std::unique_ptr<InterpretedFrame, InterpretedFrameDeleter>;
     107             : 
     108             :   // Representation of a thread in the interpreter.
     109             :   class V8_EXPORT_PRIVATE Thread {
     110             :     // Don't instante Threads; they will be allocated as ThreadImpl in the
     111             :     // interpreter implementation.
     112             :     Thread() = delete;
     113             : 
     114             :    public:
     115             :     enum ExceptionHandlingResult { HANDLED, UNWOUND };
     116             : 
     117             :     // Execution control.
     118             :     State state();
     119             :     void InitFrame(const WasmFunction* function, WasmValue* args);
     120             :     // Pass -1 as num_steps to run till completion, pause or breakpoint.
     121             :     State Run(int num_steps = -1);
     122        3116 :     State Step() { return Run(1); }
     123             :     void Pause();
     124             :     void Reset();
     125             : 
     126             :     // Raise an exception in the current activation and unwind the stack
     127             :     // accordingly. Return whether the exception was handled inside wasm:
     128             :     //  - HANDLED: Activation at handler position and in {PAUSED} state.
     129             :     //  - UNWOUND: Frames unwound, exception pending, and in {STOPPED} state.
     130             :     ExceptionHandlingResult RaiseException(Isolate*, Handle<Object> exception);
     131             : 
     132             :     // Stack inspection and modification.
     133             :     pc_t GetBreakpointPc();
     134             :     // TODO(clemensh): Make this uint32_t.
     135             :     int GetFrameCount();
     136             :     // The InterpretedFrame is only valid as long as the Thread is paused.
     137             :     FramePtr GetFrame(int index);
     138             :     WasmValue GetReturnValue(int index = 0);
     139             :     TrapReason GetTrapReason();
     140             : 
     141             :     // Returns true if the thread executed an instruction which may produce
     142             :     // nondeterministic results, e.g. float div, float sqrt, and float mul,
     143             :     // where the sign bit of a NaN is nondeterministic.
     144             :     bool PossibleNondeterminism();
     145             : 
     146             :     // Returns the number of calls / function frames executed on this thread.
     147             :     uint64_t NumInterpretedCalls();
     148             : 
     149             :     // Thread-specific breakpoints.
     150             :     // TODO(wasm): Implement this once we support multiple threads.
     151             :     // bool SetBreakpoint(const WasmFunction* function, int pc, bool enabled);
     152             :     // bool GetBreakpoint(const WasmFunction* function, int pc);
     153             : 
     154             :     void AddBreakFlags(uint8_t flags);
     155             :     void ClearBreakFlags();
     156             : 
     157             :     // Each thread can have multiple activations, each represented by a portion
     158             :     // of the stack frames of this thread. StartActivation returns the id
     159             :     // (counting from 0 up) of the started activation.
     160             :     // Activations must be properly stacked, i.e. if FinishActivation is called,
     161             :     // the given id must the the latest activation on the stack.
     162             :     uint32_t NumActivations();
     163             :     uint32_t StartActivation();
     164             :     void FinishActivation(uint32_t activation_id);
     165             :     // Return the frame base of the given activation, i.e. the number of frames
     166             :     // when this activation was started.
     167             :     uint32_t ActivationFrameBase(uint32_t activation_id);
     168             :   };
     169             : 
     170             :   WasmInterpreter(Isolate* isolate, const WasmModule* module,
     171             :                   const ModuleWireBytes& wire_bytes,
     172             :                   Handle<WasmInstanceObject> instance);
     173             :   ~WasmInterpreter();
     174             : 
     175             :   //==========================================================================
     176             :   // Execution controls.
     177             :   //==========================================================================
     178             :   void Run();
     179             :   void Pause();
     180             : 
     181             :   // Set a breakpoint at {pc} in {function} to be {enabled}. Returns the
     182             :   // previous state of the breakpoint at {pc}.
     183             :   bool SetBreakpoint(const WasmFunction* function, pc_t pc, bool enabled);
     184             : 
     185             :   // Gets the current state of the breakpoint at {function}.
     186             :   bool GetBreakpoint(const WasmFunction* function, pc_t pc);
     187             : 
     188             :   // Enable or disable tracing for {function}. Return the previous state.
     189             :   bool SetTracing(const WasmFunction* function, bool enabled);
     190             : 
     191             :   //==========================================================================
     192             :   // Thread iteration and inspection.
     193             :   //==========================================================================
     194             :   int GetThreadCount();
     195             :   Thread* GetThread(int id);
     196             : 
     197             :   //==========================================================================
     198             :   // Testing functionality.
     199             :   //==========================================================================
     200             :   // Manually adds a function to this interpreter. The func_index of the
     201             :   // function must match the current number of functions.
     202             :   void AddFunctionForTesting(const WasmFunction* function);
     203             :   // Manually adds code to the interpreter for the given function.
     204             :   void SetFunctionCodeForTesting(const WasmFunction* function,
     205             :                                  const byte* start, const byte* end);
     206             : 
     207             :   // Computes the control transfers for the given bytecode. Used internally in
     208             :   // the interpreter, but exposed for testing.
     209             :   static ControlTransferMap ComputeControlTransfersForTesting(
     210             :       Zone* zone, const WasmModule* module, const byte* start, const byte* end);
     211             : 
     212             :  private:
     213             :   Zone zone_;
     214             :   WasmInterpreterInternals* internals_;
     215             : };
     216             : 
     217             : }  // namespace wasm
     218             : }  // namespace internal
     219             : }  // namespace v8
     220             : 
     221             : #endif  // V8_WASM_WASM_INTERPRETER_H_

Generated by: LCOV version 1.10