[JITLink][AArch32] Revisit descriptions for Call and Jump24 relocation types (NFC)
[llvm-project.git] / lldb / examples / python / memory.py
blob985deb89d1ab9778bc2dc6e0aa61131b7376197f
1 #!/usr/bin/env python
3 # ----------------------------------------------------------------------
4 # Be sure to add the python path that points to the LLDB shared library.
6 # # To use this in the embedded python interpreter using "lldb" just
7 # import it with the full path using the "command script import"
8 # command
9 # (lldb) command script import /path/to/cmdtemplate.py
10 # ----------------------------------------------------------------------
12 import platform
13 import os
14 import re
15 import sys
16 import subprocess
18 try:
19 # Just try for LLDB in case PYTHONPATH is already correctly setup
20 import lldb
21 except ImportError:
22 lldb_python_dirs = list()
23 # lldb is not in the PYTHONPATH, try some defaults for the current platform
24 platform_system = platform.system()
25 if platform_system == "Darwin":
26 # On Darwin, try the currently selected Xcode directory
27 xcode_dir = subprocess.check_output("xcode-select --print-path", shell=True)
28 if xcode_dir:
29 lldb_python_dirs.append(
30 os.path.realpath(
31 xcode_dir + "/../SharedFrameworks/LLDB.framework/Resources/Python"
34 lldb_python_dirs.append(
35 xcode_dir + "/Library/PrivateFrameworks/LLDB.framework/Resources/Python"
37 lldb_python_dirs.append(
38 "/System/Library/PrivateFrameworks/LLDB.framework/Resources/Python"
40 success = False
41 for lldb_python_dir in lldb_python_dirs:
42 if os.path.exists(lldb_python_dir):
43 if not (sys.path.__contains__(lldb_python_dir)):
44 sys.path.append(lldb_python_dir)
45 try:
46 import lldb
47 except ImportError:
48 pass
49 else:
50 print('imported lldb from: "%s"' % (lldb_python_dir))
51 success = True
52 break
53 if not success:
54 print(
55 "error: couldn't locate the 'lldb' module, please set PYTHONPATH correctly"
57 sys.exit(1)
59 import optparse
60 import shlex
61 import string
62 import struct
63 import time
66 def append_data_callback(option, opt_str, value, parser):
67 if opt_str == "--uint8":
68 int8 = int(value, 0)
69 parser.values.data += struct.pack("1B", int8)
70 if opt_str == "--uint16":
71 int16 = int(value, 0)
72 parser.values.data += struct.pack("1H", int16)
73 if opt_str == "--uint32":
74 int32 = int(value, 0)
75 parser.values.data += struct.pack("1I", int32)
76 if opt_str == "--uint64":
77 int64 = int(value, 0)
78 parser.values.data += struct.pack("1Q", int64)
79 if opt_str == "--int8":
80 int8 = int(value, 0)
81 parser.values.data += struct.pack("1b", int8)
82 if opt_str == "--int16":
83 int16 = int(value, 0)
84 parser.values.data += struct.pack("1h", int16)
85 if opt_str == "--int32":
86 int32 = int(value, 0)
87 parser.values.data += struct.pack("1i", int32)
88 if opt_str == "--int64":
89 int64 = int(value, 0)
90 parser.values.data += struct.pack("1q", int64)
93 def create_memfind_options():
94 usage = "usage: %prog [options] STARTADDR [ENDADDR]"
95 description = """This command can find data in a specified address range.
96 Options are used to specify the data that is to be looked for and the options
97 can be specified multiple times to look for longer streams of data.
98 """
99 parser = optparse.OptionParser(description=description, prog="memfind", usage=usage)
100 parser.add_option(
101 "-s",
102 "--size",
103 type="int",
104 metavar="BYTESIZE",
105 dest="size",
106 help="Specify the byte size to search.",
107 default=0,
109 parser.add_option(
110 "--int8",
111 action="callback",
112 callback=append_data_callback,
113 type="string",
114 metavar="INT",
115 dest="data",
116 help="Specify a 8 bit signed integer value to search for in memory.",
117 default="",
119 parser.add_option(
120 "--int16",
121 action="callback",
122 callback=append_data_callback,
123 type="string",
124 metavar="INT",
125 dest="data",
126 help="Specify a 16 bit signed integer value to search for in memory.",
127 default="",
129 parser.add_option(
130 "--int32",
131 action="callback",
132 callback=append_data_callback,
133 type="string",
134 metavar="INT",
135 dest="data",
136 help="Specify a 32 bit signed integer value to search for in memory.",
137 default="",
139 parser.add_option(
140 "--int64",
141 action="callback",
142 callback=append_data_callback,
143 type="string",
144 metavar="INT",
145 dest="data",
146 help="Specify a 64 bit signed integer value to search for in memory.",
147 default="",
149 parser.add_option(
150 "--uint8",
151 action="callback",
152 callback=append_data_callback,
153 type="string",
154 metavar="INT",
155 dest="data",
156 help="Specify a 8 bit unsigned integer value to search for in memory.",
157 default="",
159 parser.add_option(
160 "--uint16",
161 action="callback",
162 callback=append_data_callback,
163 type="string",
164 metavar="INT",
165 dest="data",
166 help="Specify a 16 bit unsigned integer value to search for in memory.",
167 default="",
169 parser.add_option(
170 "--uint32",
171 action="callback",
172 callback=append_data_callback,
173 type="string",
174 metavar="INT",
175 dest="data",
176 help="Specify a 32 bit unsigned integer value to search for in memory.",
177 default="",
179 parser.add_option(
180 "--uint64",
181 action="callback",
182 callback=append_data_callback,
183 type="string",
184 metavar="INT",
185 dest="data",
186 help="Specify a 64 bit unsigned integer value to search for in memory.",
187 default="",
189 return parser
192 def memfind_command(debugger, command, result, dict):
193 # Use the Shell Lexer to properly parse up command options just like a
194 # shell would
195 command_args = shlex.split(command)
196 parser = create_memfind_options()
197 (options, args) = parser.parse_args(command_args)
198 # try:
199 # (options, args) = parser.parse_args(command_args)
200 # except:
201 # # if you don't handle exceptions, passing an incorrect argument to the OptionParser will cause LLDB to exit
202 # # (courtesy of OptParse dealing with argument errors by throwing SystemExit)
203 # result.SetStatus (lldb.eReturnStatusFailed)
204 # print >>result, "error: option parsing failed" # returning a string is the same as returning an error whose description is the string
205 # return
206 memfind(debugger.GetSelectedTarget(), options, args, result)
209 def print_error(str, show_usage, result):
210 print(str, file=result)
211 if show_usage:
212 print(create_memfind_options().format_help(), file=result)
215 def memfind(target, options, args, result):
216 num_args = len(args)
217 start_addr = 0
218 if num_args == 1:
219 if options.size > 0:
220 print_error(
221 "error: --size must be specified if there is no ENDADDR argument",
222 True,
223 result,
225 return
226 start_addr = int(args[0], 0)
227 elif num_args == 2:
228 if options.size != 0:
229 print_error(
230 "error: --size can't be specified with an ENDADDR argument",
231 True,
232 result,
234 return
235 start_addr = int(args[0], 0)
236 end_addr = int(args[1], 0)
237 if start_addr >= end_addr:
238 print_error(
239 "error: inavlid memory range [%#x - %#x)" % (start_addr, end_addr),
240 True,
241 result,
243 return
244 options.size = end_addr - start_addr
245 else:
246 print_error("error: memfind takes 1 or 2 arguments", True, result)
247 return
249 if not options.data:
250 print("error: no data specified to search for", file=result)
251 return
253 if not target:
254 print("error: invalid target", file=result)
255 return
256 process = target.process
257 if not process:
258 print("error: invalid process", file=result)
259 return
261 error = lldb.SBError()
262 bytes = process.ReadMemory(start_addr, options.size, error)
263 if error.Success():
264 num_matches = 0
265 print(
266 "Searching memory range [%#x - %#x) for" % (start_addr, end_addr),
267 end=" ",
268 file=result,
270 for byte in options.data:
271 print("%2.2x" % ord(byte), end=" ", file=result)
272 print(file=result)
274 match_index = string.find(bytes, options.data)
275 while match_index != -1:
276 num_matches = num_matches + 1
277 print(
278 "%#x: %#x + %u" % (start_addr + match_index, start_addr, match_index),
279 file=result,
281 match_index = string.find(bytes, options.data, match_index + 1)
283 if num_matches == 0:
284 print("error: no matches found", file=result)
285 else:
286 print("error: %s" % (error.GetCString()), file=result)
289 if __name__ == "__main__":
290 print(
291 "error: this script is designed to be used within the embedded script interpreter in LLDB"
295 def __lldb_init_module(debugger, internal_dict):
296 memfind_command.__doc__ = create_memfind_options().format_help()
297 debugger.HandleCommand("command script add -o -f memory.memfind_command memfind")
298 print('"memfind" command installed, use the "--help" option for detailed help')