• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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_WASM_RESULT_H_
6 #define V8_WASM_RESULT_H_
7 
8 #include "src/base/smart-pointers.h"
9 
10 #include "src/globals.h"
11 
12 namespace v8 {
13 namespace internal {
14 
15 class Isolate;
16 
17 namespace wasm {
18 
19 // Error codes for programmatic checking of the decoder's verification.
20 enum ErrorCode {
21   kSuccess,
22   kError,                 // TODO(titzer): remove me
23   kOutOfMemory,           // decoder ran out of memory
24   kEndOfCode,             // end of code reached prematurely
25   kInvalidOpcode,         // found invalid opcode
26   kUnreachableCode,       // found unreachable code
27   kImproperContinue,      // improperly nested continue
28   kImproperBreak,         // improperly nested break
29   kReturnCount,           // return count mismatch
30   kTypeError,             // type mismatch
31   kInvalidLocalIndex,     // invalid local
32   kInvalidGlobalIndex,    // invalid global
33   kInvalidFunctionIndex,  // invalid function
34   kInvalidMemType         // invalid memory type
35 };
36 
37 // The overall result of decoding a function or a module.
38 template <typename T>
39 struct Result {
ResultResult40   Result()
41       : val(nullptr), error_code(kSuccess), start(nullptr), error_pc(nullptr) {
42     error_msg.Reset(nullptr);
43   }
44 
45   T val;
46   ErrorCode error_code;
47   const byte* start;
48   const byte* error_pc;
49   const byte* error_pt;
50   base::SmartArrayPointer<char> error_msg;
51 
okResult52   bool ok() const { return error_code == kSuccess; }
failedResult53   bool failed() const { return error_code != kSuccess; }
54 
55   template <typename V>
CopyFromResult56   void CopyFrom(Result<V>& that) {
57     error_code = that.error_code;
58     start = that.start;
59     error_pc = that.error_pc;
60     error_pt = that.error_pt;
61     error_msg = that.error_msg;
62   }
63 };
64 
65 template <typename T>
66 std::ostream& operator<<(std::ostream& os, const Result<T>& result) {
67   os << "Result = ";
68   if (result.ok()) {
69     if (result.val != nullptr) {
70       os << *result.val;
71     } else {
72       os << "success (no value)";
73     }
74   } else if (result.error_msg.get() != nullptr) {
75     ptrdiff_t offset = result.error_pc - result.start;
76     if (offset < 0) {
77       os << result.error_msg.get() << " @" << offset;
78     } else {
79       os << result.error_msg.get() << " @+" << offset;
80     }
81   } else {
82     os << result.error_code;
83   }
84   os << std::endl;
85   return os;
86 }
87 
88 std::ostream& operator<<(std::ostream& os, const ErrorCode& error_code);
89 
90 // A helper for generating error messages that bubble up to JS exceptions.
91 class ErrorThrower {
92  public:
ErrorThrower(Isolate * isolate,const char * context)93   ErrorThrower(Isolate* isolate, const char* context)
94       : isolate_(isolate), context_(context), error_(false) {}
95 
96   void Error(const char* fmt, ...);
97 
98   template <typename T>
Failed(const char * error,Result<T> & result)99   void Failed(const char* error, Result<T>& result) {
100     std::ostringstream str;
101     str << error << result;
102     return Error(str.str().c_str());
103   }
104 
error()105   bool error() const { return error_; }
106 
107  private:
108   Isolate* isolate_;
109   const char* context_;
110   bool error_;
111 };
112 }  // namespace wasm
113 }  // namespace internal
114 }  // namespace v8
115 
116 #endif
117