1 | //===-- BreakpointName.h ----------------------------------------*- C++ -*-===// |
2 | // |
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
4 | // See https://llvm.org/LICENSE.txt for license information. |
5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
6 | // |
7 | //===----------------------------------------------------------------------===// |
8 | |
9 | #ifndef LLDB_BREAKPOINT_BREAKPOINTNAME_H |
10 | #define LLDB_BREAKPOINT_BREAKPOINTNAME_H |
11 | |
12 | #include <memory> |
13 | #include <string> |
14 | #include <unordered_set> |
15 | #include <vector> |
16 | |
17 | #include "lldb/Breakpoint/BreakpointID.h" |
18 | #include "lldb/Breakpoint/BreakpointLocationCollection.h" |
19 | #include "lldb/Breakpoint/BreakpointLocationList.h" |
20 | #include "lldb/Breakpoint/BreakpointOptions.h" |
21 | #include "lldb/Breakpoint/Stoppoint.h" |
22 | #include "lldb/Core/SearchFilter.h" |
23 | #include "lldb/Utility/Event.h" |
24 | #include "lldb/Utility/Flags.h" |
25 | #include "lldb/Utility/StringList.h" |
26 | #include "lldb/Utility/StructuredData.h" |
27 | |
28 | namespace lldb_private { |
29 | |
30 | class BreakpointName { |
31 | public: |
32 | class Permissions |
33 | { |
34 | public: |
35 | |
36 | enum PermissionKinds { listPerm = 0, disablePerm = 1, |
37 | deletePerm = 2, allPerms = 3 }; |
38 | |
39 | Permissions(bool in_list, bool in_disable, bool in_delete) |
40 | { |
41 | m_permissions[listPerm] = in_list; |
42 | m_permissions[disablePerm] = in_disable; |
43 | m_permissions[deletePerm] = in_delete; |
44 | m_set_mask.Set(permissions_mask[allPerms]); |
45 | } |
46 | |
47 | Permissions(const Permissions &rhs) |
48 | { |
49 | m_permissions[listPerm] = rhs.m_permissions[listPerm]; |
50 | m_permissions[disablePerm] = rhs.m_permissions[disablePerm]; |
51 | m_permissions[deletePerm] = rhs.m_permissions[deletePerm]; |
52 | m_set_mask = rhs.m_set_mask; |
53 | } |
54 | |
55 | Permissions() |
56 | { |
57 | m_permissions[listPerm] = true; |
58 | m_permissions[disablePerm] = true; |
59 | m_permissions[deletePerm] = true; |
60 | m_set_mask.Clear(); |
61 | } |
62 | |
63 | const Permissions &operator= (const Permissions &rhs) |
64 | { |
65 | if (this != &rhs) { |
66 | m_permissions[listPerm] = rhs.m_permissions[listPerm]; |
67 | m_permissions[disablePerm] = rhs.m_permissions[disablePerm]; |
68 | m_permissions[deletePerm] = rhs.m_permissions[deletePerm]; |
69 | m_set_mask = rhs.m_set_mask; |
70 | } |
71 | return *this; |
72 | } |
73 | |
74 | void Clear() { |
75 | *this = Permissions(); |
76 | } |
77 | |
78 | // Merge the permissions from incoming into this set of permissions. Only |
79 | // merge set permissions, and most restrictive permission wins. |
80 | void MergeInto(const Permissions &incoming) |
81 | { |
82 | MergePermission(incoming, permission: listPerm); |
83 | MergePermission(incoming, permission: disablePerm); |
84 | MergePermission(incoming, permission: deletePerm); |
85 | } |
86 | |
87 | bool GetAllowList() const { return GetPermission(permission: listPerm); } |
88 | bool SetAllowList(bool value) { return SetPermission(permission: listPerm, value); } |
89 | |
90 | bool GetAllowDelete() const { return GetPermission(permission: deletePerm); } |
91 | bool SetAllowDelete(bool value) { return SetPermission(permission: deletePerm, value); } |
92 | |
93 | bool GetAllowDisable() const { return GetPermission(permission: disablePerm); } |
94 | bool SetAllowDisable(bool value) { return SetPermission(permission: disablePerm, |
95 | value); } |
96 | |
97 | bool GetPermission(enum PermissionKinds permission) const |
98 | { |
99 | return m_permissions[permission]; |
100 | } |
101 | |
102 | bool GetDescription(Stream *s, lldb::DescriptionLevel level); |
103 | |
104 | bool IsSet(enum PermissionKinds permission) const |
105 | { |
106 | return m_set_mask.Test(bit: permissions_mask[permission]); |
107 | } |
108 | |
109 | bool AnySet() { |
110 | return m_set_mask.AnySet(mask: permissions_mask[allPerms]); |
111 | } |
112 | |
113 | private: |
114 | static const Flags::ValueType permissions_mask[allPerms + 1]; |
115 | |
116 | bool m_permissions[allPerms]; |
117 | Flags m_set_mask; |
118 | |
119 | bool SetPermission(enum PermissionKinds permission, bool value) |
120 | { |
121 | bool old_value = m_permissions[permission]; |
122 | m_permissions[permission] = value; |
123 | m_set_mask.Set(permissions_mask[permission]); |
124 | return old_value; |
125 | } |
126 | |
127 | // If either side disallows the permission, the resultant disallows it. |
128 | void MergePermission(const Permissions &incoming, |
129 | enum PermissionKinds permission) |
130 | { |
131 | if (incoming.IsSet(permission)) |
132 | { |
133 | SetPermission(permission, value: !(m_permissions[permission] | |
134 | incoming.m_permissions[permission])); |
135 | } |
136 | } |
137 | }; |
138 | |
139 | BreakpointName(ConstString name, const char *help = nullptr) : |
140 | m_name(name), m_options(false) |
141 | { |
142 | SetHelp(help); |
143 | } |
144 | |
145 | BreakpointName(const BreakpointName &rhs) : |
146 | m_name(rhs.m_name), m_options(rhs.m_options), |
147 | m_permissions(rhs.m_permissions), m_help(rhs.m_help) |
148 | {} |
149 | |
150 | ConstString GetName() const { return m_name; } |
151 | BreakpointOptions &GetOptions() { return m_options; } |
152 | const BreakpointOptions &GetOptions() const { return m_options; } |
153 | |
154 | void SetOptions(const BreakpointOptions &options) { |
155 | m_options = options; |
156 | } |
157 | |
158 | Permissions &GetPermissions() { return m_permissions; } |
159 | const Permissions &GetPermissions() const { return m_permissions; } |
160 | void SetPermissions(const Permissions &permissions) { |
161 | m_permissions = permissions; |
162 | } |
163 | |
164 | bool GetPermission(Permissions::PermissionKinds permission) const |
165 | { |
166 | return m_permissions.GetPermission(permission); |
167 | } |
168 | |
169 | void SetHelp(const char *description) |
170 | { |
171 | if (description) |
172 | m_help.assign(s: description); |
173 | else |
174 | m_help.clear(); |
175 | } |
176 | |
177 | const char *GetHelp() |
178 | { |
179 | return m_help.c_str(); |
180 | } |
181 | |
182 | // Returns true if any options were set in the name |
183 | bool GetDescription(Stream *s, lldb::DescriptionLevel level); |
184 | |
185 | void ConfigureBreakpoint(lldb::BreakpointSP bp_sp); |
186 | |
187 | private: |
188 | ConstString m_name; |
189 | BreakpointOptions m_options; |
190 | Permissions m_permissions; |
191 | std::string m_help; |
192 | }; |
193 | |
194 | } // namespace lldb_private |
195 | |
196 | #endif // LLDB_BREAKPOINT_BREAKPOINTNAME_H |
197 | |