1 //===-- OptionGroupWatchpoint.cpp -----------------------------------------===//
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 #include "lldb/Interpreter/OptionGroupWatchpoint.h"
10 
11 #include "lldb/Host/OptionParser.h"
12 #include "lldb/Interpreter/OptionArgParser.h"
13 #include "lldb/lldb-enumerations.h"
14 
15 using namespace lldb;
16 using namespace lldb_private;
17 
18 static constexpr OptionEnumValueElement g_watch_type[] = {
19     {
20         OptionGroupWatchpoint::eWatchRead,
21         "read",
22         "Watch for read",
23     },
24     {
25         OptionGroupWatchpoint::eWatchWrite,
26         "write",
27         "Watch for write",
28     },
29     {
30         OptionGroupWatchpoint::eWatchReadWrite,
31         "read_write",
32         "Watch for read/write",
33     },
34 };
35 
36 static constexpr OptionEnumValueElement g_watch_size[] = {
37     {
38         1,
39         "1",
40         "Watch for byte size of 1",
41     },
42     {
43         2,
44         "2",
45         "Watch for byte size of 2",
46     },
47     {
48         4,
49         "4",
50         "Watch for byte size of 4",
51     },
52     {
53         8,
54         "8",
55         "Watch for byte size of 8",
56     },
57 };
58 
59 static constexpr OptionDefinition g_option_table[] = {
60     {LLDB_OPT_SET_1, false, "watch", 'w', OptionParser::eRequiredArgument,
61      nullptr, OptionEnumValues(g_watch_type), 0, eArgTypeWatchType,
62      "Specify the type of watching to perform."},
63     {LLDB_OPT_SET_1, false, "size", 's', OptionParser::eRequiredArgument,
64      nullptr, OptionEnumValues(g_watch_size), 0, eArgTypeByteSize,
65      "Number of bytes to use to watch a region."}};
66 
67 bool OptionGroupWatchpoint::IsWatchSizeSupported(uint32_t watch_size) {
68   for (const auto& size : g_watch_size) {
69     if (0  == size.value)
70       break;
71     if (watch_size == size.value)
72       return true;
73   }
74   return false;
75 }
76 
77 OptionGroupWatchpoint::OptionGroupWatchpoint() : OptionGroup() {}
78 
79 OptionGroupWatchpoint::~OptionGroupWatchpoint() {}
80 
81 Status
82 OptionGroupWatchpoint::SetOptionValue(uint32_t option_idx,
83                                       llvm::StringRef option_arg,
84                                       ExecutionContext *execution_context) {
85   Status error;
86   const int short_option = g_option_table[option_idx].short_option;
87   switch (short_option) {
88   case 'w': {
89     WatchType tmp_watch_type;
90     tmp_watch_type = (WatchType)OptionArgParser::ToOptionEnum(
91         option_arg, g_option_table[option_idx].enum_values, 0, error);
92     if (error.Success()) {
93       watch_type = tmp_watch_type;
94       watch_type_specified = true;
95     }
96     break;
97   }
98   case 's':
99     watch_size = (uint32_t)OptionArgParser::ToOptionEnum(
100         option_arg, g_option_table[option_idx].enum_values, 0, error);
101     break;
102 
103   default:
104     llvm_unreachable("Unimplemented option");
105   }
106 
107   return error;
108 }
109 
110 void OptionGroupWatchpoint::OptionParsingStarting(
111     ExecutionContext *execution_context) {
112   watch_type_specified = false;
113   watch_type = eWatchInvalid;
114   watch_size = 0;
115 }
116 
117 llvm::ArrayRef<OptionDefinition> OptionGroupWatchpoint::GetDefinitions() {
118   return llvm::makeArrayRef(g_option_table);
119 }
120