• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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_TRAP_HANDLER_TRAP_HANDLER_INTERNAL_H_
6 #define V8_TRAP_HANDLER_TRAP_HANDLER_INTERNAL_H_
7 
8 // This file should not be included (even transitively) by files outside of
9 // src/trap-handler.
10 
11 #include "src/trap-handler/trap-handler.h"
12 
13 #include <atomic>
14 
15 namespace v8 {
16 namespace internal {
17 namespace trap_handler {
18 
19 // This describes a chunk of code that the signal handler will be able to handle
20 // faults in. {base} points to the beginning of the chunk, and {size} is the
21 // number of bytes in the code chunk. The remainder of the struct is a list of
22 // protected memory access instructions and an offset to a landing pad to handle
23 // faults on that instruction.
24 struct CodeProtectionInfo {
25   Address base;
26   size_t size;
27   size_t num_protected_instructions;
28   ProtectedInstructionData instructions[1];
29 };
30 
31 class MetadataLock {
32   static std::atomic_flag spinlock_;
33 
34  public:
35   MetadataLock();
36   ~MetadataLock();
37 
38   // We'd normally use DISALLOW_COPY_AND_ASSIGN, but we're avoiding a dependency
39   // on base/macros.h
40   MetadataLock(const MetadataLock&) = delete;
41   void operator=(const MetadataLock&) = delete;
42 };
43 
44 #if V8_TRAP_HANDLER_SUPPORTED
45 void HandleSignal(int signum, siginfo_t* info, void* context);
46 #endif
47 
48 // To enable constant time registration of handler data, we keep a free list of
49 // entries in the gCodeObjects table. Each entry contains a {next_free} field,
50 // which can be used to figure out where the next entry should be inserted.
51 // In order to avoid having to initialize all the links to start with, we use
52 // 0 to indicate that this is a fresh, never-used list entry and that therefore
53 // the next entry is known to be free. If {next_entry} is greater than zero,
54 // then {next_entry - 1} is the index that we should insert into next.
55 struct CodeProtectionInfoListEntry {
56   CodeProtectionInfo* code_info;
57   size_t next_free;
58 };
59 
60 extern size_t gNumCodeObjects;
61 extern CodeProtectionInfoListEntry* gCodeObjects;
62 
63 extern std::atomic_size_t gRecoveredTrapCount;
64 
65 // Searches the fault location table for an entry matching fault_addr. If found,
66 // returns true and sets landing_pad to the address of a fragment of code that
67 // can recover from this fault. Otherwise, returns false and leaves offset
68 // unchanged.
69 bool TryFindLandingPad(uintptr_t fault_addr, uintptr_t* landing_pad);
70 
71 #if V8_TRAP_HANDLER_SUPPORTED
72 // When using the default signal handler, we save the old one to restore in case
73 // V8 chooses not to handle the signal.
74 extern struct sigaction g_old_handler;
75 extern bool g_is_default_signal_handler_registered;
76 #endif
77 
78 }  // namespace trap_handler
79 }  // namespace internal
80 }  // namespace v8
81 
82 #endif  // V8_TRAP_HANDLER_TRAP_HANDLER_INTERNAL_H_
83