Commit Graph

374 Commits

Author SHA1 Message Date
Omar Sandoval
906fa90202 python: add execscript()
On many occasions, I've wanted to build and iterate on a script while
exploring in an interactive session. This has involved various
workarounds, like copy-and-paste of the work-in-progress script into the
REPL, using importlib.reload(), or adding code.interact() at the end of
the script. These workflows aren't very convenient.

Add execscript(), which runs a script as if it was run from the REPL,
adding all defined functions and variables to the global scope so that
iterating on the script further is easy.
2019-06-28 12:48:45 -07:00
Omar Sandoval
808a03a3df cli: use argparse.REMAINDER for script arguments
This makes it possible to pass options to a script using drgn:

  $ cat test.py
  #!/usr/bin/drgn -k

  import sys

  print(sys.argv)
  $ sudo ./test.py --foo --bar
  ['./test.py', '--foo', '--bar']

Before, drgn would try to parse the additional arguments and fail.
2019-06-11 15:28:12 -07:00
Omar Sandoval
ca9e641fcb
Merge pull request #2 from naota/fix-for_each_cpu
helpers: fix for_each_cpu to use new attributes
2019-06-05 15:15:43 -07:00
Naohiro Aota
1691d5c02b helpers: fix for_each_cpu to use new attributes
for_each_cpu is using old attributes "sizeof" and "size". Fix them to
use new ones.

Before patch:
>>> for x in for_each_online_cpu(prog): print(x)
...
Traceback (most recent call last):
  File "<console>", line 1, in <module>
  File "/home/naota/drgn/drgn/helpers/linux/cpumask.py", line 29, in for_each_cpu
    word_bits = 8 * bits.type_.type.sizeof()
AttributeError: '_drgn.Type' object has no attribute 'sizeof'

After patch:
>>> for x in for_each_online_cpu(prog): print(x)
...
0
1
2
3
4
5
6
7
2019-06-05 09:59:07 +09:00
Omar Sandoval
95a8d992db docs: remove extra comma in add_memory_segment() signature 2019-05-31 17:17:00 -07:00
Omar Sandoval
f55158c74c libdrgn: add PAGE_{SHIFT,SIZE,MASK} symbols from vmcoreinfo
Since we currently don't parse DWARF macro information, there's no easy
way to get the value PAGE_SIZE and friends in drgn. However, vmcoreinfo
contains the value of PAGE_SIZE, so let's add a special symbol finder
that returns that.
2019-05-29 00:02:48 -07:00
Omar Sandoval
1614b1e6f6 libdrgn: add better vmcoreinfo fallback
Currently, if we don't get vmcoreinfo from /proc/kcore, and we can't get
it from /sys/kernel/vmcoreinfo, then we manually determine the kernel
release and KASLR offset. This has a couple of issues:

1. We look for vmlinux to determine the KASLR offset, which may not be
   in a standard location.
2. We might want to start using other information from vmcoreinfo which
   can't be determined as easily.

Instead, we can get the virtual address of vmcoreinfo from
/proc/kallsyms and read it directly from there.
2019-05-28 15:54:49 -07:00
Omar Sandoval
8e45a305fb libdrgn: fix file/memory leak in proc_kallsyms_symbol_addr() 2019-05-28 15:01:35 -07:00
Omar Sandoval
c337123fa2 Merge pull request #1 from sdimitro/vmlinux_path_ubuntu
libdrgn: add /usr/lib/debug/boot in the vmlinux_paths
2019-05-27 17:45:32 -07:00
Serapheim Dimitropoulos
2396cdca47 libdrgn: add /usr/lib/debug/boot in the vmlinux_paths
Ubuntu-based distros tend to put vmlinux with debug info
under /usr/lib/debug/boot/vmlinux-<version>.
2019-05-27 17:43:10 -07:00
Omar Sandoval
eeac241c65 libdrgn: make all kernel module iterator errors non-fatal when loading default symbols
kernel_module_iterator_next() can also fail in
open_loaded_kernel_modules(), so handle it in the same way that we
currently handle kernel_module_iterator_init().
2019-05-26 14:58:02 -07:00
Omar Sandoval
68f7b87d6a libdrgn: ignore physical core dump segments with address -1
/proc/kcore contains segments which don't have a valid physical address,
which it indicates with a p_paddr of -1. Skip those segments, otherwise
we got an overflow error from the memory reader.
2019-05-26 14:49:48 -07:00
Omar Sandoval
c0bc72b0ea libdrgn: use splay tree for memory reader
The current array-based memory reader has a bug in the following
scenario:

    prog.add_memory_segment(0xffff0000, 128, ...)
    # This should replace a subset of the first segment.
    prog.add_memory_segment(0xffff0020, 32, ...)
    # This moves the first segment back to the front of the array.
    prog.read(0xffff0000, 32)
    # This finds the first segment instead of the second segment.
    prog.read(0xffff0032, 32)

Fix it by using the newly-added splay tree. This also splits up the
virtual and physical memory segments into separate trees.
2019-05-24 17:48:08 -07:00
Omar Sandoval
10fb398338 libdrgn: add splay tree implementation
This will be used to track memory segments instead of the array we
currently use. The API is based on the hash table API; it can support
alternative implementations in the future, like red-black trees.
2019-05-24 17:48:08 -07:00
Omar Sandoval
dcddaa2cc1 libdrgn: revamp hash table API
This makes several improvements to the hash table API.

The first two changes make things more general in order to be consistent
with the upcoming binary search tree API:

- Items are renamed to entries.
- Positions are renamed to iterators.
- hash_table_empty() is added.

One change makes the definition API more convenient:

- It is no longer necessary to pass the types into
  DEFINE_HASH_{MAP,SET}_FUNCTIONS().

A few changes take some good ideas from the C++ STL:

- hash_table_insert() now fails on duplicates instead of overwriting.
- hash_table_delete_iterator() returns the next iterator.
- hash_table_next() returns an iterator instead of modifying it.

One change reduces memory usage:

- The lower-level DEFINE_HASH_TABLE() is cleaned up and exposed as an
  alternative to DEFINE_HASH_MAP() and DEFINE_HASH_SET(). This allows us
  to get rid of the duplicated key where a hash map value already embeds
  the key (the DWARF index file table) and gets rid of the need to make
  a dummy hash set entry to do a search (the pointer and array type
  caches).
2019-05-24 17:48:05 -07:00
Omar Sandoval
0026eeae66 libdrgn: find kernel module name in kernels < v4.13
If we can't find the module name in .modinfo, fall back to
.gnu.linkonce.this_module.
2019-05-14 15:39:16 -07:00
Omar Sandoval
e4b8af7807 libdrgn/python: fix uninitialized variable in Program.load_debug_info()
path_converter() reads arg->allow_none, so make sure we zero the array
of path arguments.
2019-05-14 14:28:03 -07:00
Omar Sandoval
39876ccbac libdrgn: find kernel module debuginfo on Debian
Debian's linux-image*-dbg packages name the ELF files without the extra
.debug suffix that Fedora includes.
2019-05-14 12:42:56 -07:00
Omar Sandoval
ac27f2c1ec libdrgn: only load debug information from loaded kernel modules
Currently, we load debug information for every kernel module that we
find under /lib/modules/$(uname -r)/kernel. This has a few issues:

1. Distribution kernels have lots of modules (~3000 for Fedora and
   Debian).
   a) This can exceed the default soft limit on the number of open file
      descriptors.
   b) The mmap'd debug information can trip the overcommit heuristics
      and cause OOM kills.
   c) It can take a long time to parse all of the debug information.
2. Not all modules are under the "kernel" directory; some distros also
   have an "extra" directory.
3. The user is not made aware of loaded kernel modules that don't have
   debug information available.

So, instead of walking /lib/modules, walk the list of loaded kernel
modules and look up their debugging information.
2019-05-14 11:55:39 -07:00
Omar Sandoval
efaec41ca2 libdrgn: add string_builder_append_error() 2019-05-14 11:49:52 -07:00
Omar Sandoval
e21ed988fb libdrgn: add drgn_error_from_string_builder()
And use that instead of exposing drgn_error_create_nodup().
2019-05-14 10:16:01 -07:00
Omar Sandoval
b0f10d3b58 libdrgn: pass enum drgn_error_code to error constructors 2019-05-14 10:13:05 -07:00
Omar Sandoval
f08d4c9a08 libdrgn: make string_builder API return bool
It can only fail with no memory, so simplify it.
2019-05-14 10:07:50 -07:00
Omar Sandoval
0135dbd0cc libdrgn: get loaded module names from /proc/modules when possible
Similar to the last optimization, for the running kernel, we can just
read /proc/modules instead of walking the kernel data structures.
2019-05-13 18:05:17 -07:00
Omar Sandoval
ed6a6f0b3e libdrgn: get module section address from sysfs when possible
In the running kernel, we don't have to walk the list of modules and
module sections, since we can just look it up directly in sysfs.
2019-05-13 18:05:09 -07:00
Omar Sandoval
f11e030aaa libdrgn: factor out kernel module iteration and section lookup 2019-05-13 16:39:30 -07:00
Omar Sandoval
9b563170f8 libdrgn: make load_debug_info() API saner
Rather than exposing the underlying open and load steps of DWARF index,
simplify it down to a single load step.
2019-05-13 15:04:27 -07:00
Omar Sandoval
60c9e26ff5 libdrgn: make C string hash table helpers work with char *
const char * const * is not compatible with char * const *, so make
c_string_hash() and c_string_eq() macros so they can work with both
const char * and char * keys.
2019-05-13 11:52:55 -07:00
Omar Sandoval
1206730730 libdrgn: fix hash_set_insert_searched_pos() documentation 2019-05-13 11:52:55 -07:00
Omar Sandoval
ab58a5bff0 libdrgn: determine default size_t and ptrdiff_t more intelligently
Currently, size_t and ptrdiff_t default to typedefs of the default
unsigned long and long, respectively, regardless of what the program
actually defines unsigned long or long as. Instead, make them refer the
whatever integer type (long, long long, or int) is the same size as the
word size.
2019-05-10 15:14:03 -07:00
Omar Sandoval
83285d3f29 cli: add --symbols and --no-default-symbols
Now we can finally, for example, use vmlinux in a non-standard location.
2019-05-10 13:20:03 -07:00
Omar Sandoval
e65ff24975 cli: group together -c, -k, and -p in --help output 2019-05-10 13:11:48 -07:00
Omar Sandoval
8231414dc9 cli: add --quiet option
Currently, we print warnings for interactive mode but not for script
mode. Make it more explicit with a --quiet option.
2019-05-10 12:57:07 -07:00
Omar Sandoval
baba1ff3f0 libdrgn: make program components pluggable
Currently, programs can be created for three main use-cases: core dumps,
the running kernel, and a running process. However, internally, the
program memory, types, and symbols are pluggable. Expose that as a
callback API, which makes it possible to use drgn in much more creative
ways.
2019-05-10 12:41:07 -07:00
Omar Sandoval
ac946ba8a7 libdrgn: fix zero-filling reads from core dump segments 2019-05-09 16:35:48 -07:00
Omar Sandoval
15bc0286b9 libdrgn: add drgn_error_create_nodup() 2019-05-09 16:35:14 -07:00
Omar Sandoval
fb10623903 libdrgn: use next_power_of_two() for string_builder 2019-05-09 16:01:07 -07:00
Omar Sandoval
6d7b0631b9 libdrgn: simplify string_builder API
Instead of maintaining a null-terminated string, null-terminate just
before returning the string as a "finalize" step.
2019-05-09 15:25:58 -07:00
Omar Sandoval
5200a6652c libdrgn: embed memory reader, type index, and symbol index in program 2019-05-06 14:55:34 -07:00
Omar Sandoval
bb2357bc09 libdrgn: don't require word size for type index initialization 2019-05-06 14:55:34 -07:00
Omar Sandoval
640b1c011d libdrgn: embed DWARF index in DWARF info cache 2019-05-06 14:55:34 -07:00
Omar Sandoval
2ed8e3148c libdrgn: get architecture info from core file instead of DWARF index 2019-05-06 14:55:34 -07:00
Omar Sandoval
ba162ac001 libdrgn: remove endianness from type index
The type index doesn't need to know or care about endianness. Move it to
the program.
2019-05-06 14:55:34 -07:00
Omar Sandoval
565e0343ef libdrgn: make symbol index pluggable with callbacks
The last piece of making the major program components pluggable.
2019-05-06 14:55:34 -07:00
Omar Sandoval
47151c4554 libdrgn/python: add Program.object() 2019-05-06 14:55:34 -07:00
Omar Sandoval
0ea2825817 libdrgn: refactor gen_constants.py
All of the constants are generated with basically the same code, so
refactor it.
2019-05-06 14:55:34 -07:00
Omar Sandoval
9c6575e783 libdrgn: move relocation hook to drgn_info_cache 2019-05-06 14:55:34 -07:00
Omar Sandoval
52a8681a8d libdrgn: rename drgn_dwarf_type_cache to drgn_dwarf_info_cache
This is preparation for sharing this with the symbol index.
2019-05-06 14:55:34 -07:00
Omar Sandoval
a98445c277 libdrgn: make type index pluggable with callbacks
Similar to "libdrgn: make memory reader pluggable with callbacks", we
want to support custom type indexes (imagine, e.g., using drgn to parse
a binary format). For now, this disables the dwarf index tests; we'll
have a better way to test them later, so let's not bother adding more
test scaffolding.
2019-05-06 14:55:34 -07:00
Omar Sandoval
77443cecd1 libdrgn: use NULL-terminated arrays for mock {type,symbol} index
This will simplify the next couple of changes.
2019-05-06 14:55:34 -07:00