aboutsummaryrefslogtreecommitdiff
path: root/gdb/python
AgeCommit message (Collapse)AuthorFilesLines
2022-04-07gdb: use 'const reggroup *' in python/py-registers.c fileAndrew Burgess1-8/+8
Convert uses of 'struct reggroup *' in python/py-registers.c to be 'const'. There should be no user visible changes after this commit.
2022-04-06gdb: move gdb_disassembly_flag into a new disasm-flags.h fileAndrew Burgess1-1/+0
While working on the disassembler I was getting frustrated. Every time I touched disasm.h it seemed like every file in GDB would need to be rebuilt. Surely the disassembler can't be required by that many parts of GDB, right? Turns out that disasm.h is included in target.h, so pretty much every file was being rebuilt! The only thing from disasm.h that target.h needed is the gdb_disassembly_flag enum, as this is part of the target_ops api. In this commit I move gdb_disassembly_flag into its own file. This is then included in target.h and disasm.h, after which, the number of files that depend on disasm.h is much reduced. I also audited all the other includes of disasm.h and found that the includes in mep-tdep.c and python/py-registers.c are no longer needed, so I've removed these. Now, after changing disasm.h, GDB rebuilds much quicker. There should be no user visible changes after this commit.
2022-04-04Remove more Python 2 codeTom Tromey1-10/+1
I found another more place that still had a workaround for Python 2. This patch removes it.
2022-03-29Rename print_spaces_filteredTom Tromey1-3/+3
print_spaces_filtered is now misnamed, because whether filtering happens is up to the stream. So, rename it.
2022-03-29Unify gdb printf functionsTom Tromey9-31/+31
Now that filtered and unfiltered output can be treated identically, we can unify the printf family of functions. This is done under the name "gdb_printf". Most of this patch was written by script.
2022-03-29Unify gdb puts functionsTom Tromey2-16/+16
Now that filtered and unfiltered output can be treated identically, we can unify the puts family of functions. This is done under the name "gdb_puts". Most of this patch was written by script.
2022-03-23gdb/python: remove Python 2/3 compatibility macrosSimon Marchi25-116/+93
New in this version: - Rebase on master, fix a few more issues that appeared. python-internal.h contains a number of macros that helped make the code work with both Python 2 and 3. Remove them and adjust the code to use the Python 3 functions. Change-Id: I99a3d80067fb2d65de4f69f6473ba6ffd16efb2d
2022-03-23gdb/python: remove Python 2 supportSimon Marchi16-300/+19
New in this version: - Add a PY_MAJOR_VERSION check in configure.ac / AC_TRY_LIBPYTHON. If the user passes --with-python=python2, this will cause a configure failure saying that GDB only supports Python 3. Support for Python 2 is a maintenance burden for any patches touching Python support. Among others, the differences between Python 2 and 3 string and integer types are subtle. It requires a lot of effort and thinking to get something that behaves correctly on both. And that's if the author and reviewer of the patch even remember to test with Python 2. See this thread for an example: https://sourceware.org/pipermail/gdb-patches/2021-December/184260.html So, remove Python 2 support. Update the documentation to state that GDB can be built against Python 3 (as opposed to Python 2 or 3). Update all the spots that use: - sys.version_info - IS_PY3K - PY_MAJOR_VERSION - gdb_py_is_py3k ... to only keep the Python 3 portions and drop the use of some now-removed compatibility macros. I did not update the configure script more than just removing the explicit references to Python 2. We could maybe do more there, like check the Python version and reject it if that version is not supported. Otherwise (with this patch), things will only fail at compile time, so it won't really be clear to the user that they are trying to use an unsupported Python version. But I'm a bit lost in the configure code that checks for Python, so I kept that for later. Change-Id: I75b0f79c148afbe3c07ac664cfa9cade052c0c62
2022-03-22gdb/python: add gdb.format_address functionAndrew Burgess4-2/+152
Add a new function, gdb.format_address, which is a wrapper around GDB's print_address function. This method takes an address, and returns a string with the format: ADDRESS <SYMBOL+OFFSET> Where, ADDRESS is the original address, formatted as hexadecimal, SYMBOL is a symbol with an address lower than ADDRESS, and OFFSET is the offset from SYMBOL to ADDRESS in decimal. If there's no SYMBOL suitably close to ADDRESS then the <SYMBOL+OFFSET> part is not included. This is useful if a user wants to write a Python script that pretty-prints addresses, the user no longer needs to do manual symbol lookup, or worry about correctly formatting addresses. Additionally, there are some settings that effect how GDB picks SYMBOL, and whether the file name and line number should be included with the SYMBOL name, the gdb.format_address function ensures that the users Python script also benefits from these settings. The gdb.format_address by default selects SYMBOL from the current inferiors program space, and address is formatted using the architecture for the current inferior. However, a user can also explicitly pass a program space and architecture like this: gdb.format_address(ADDRESS, PROGRAM_SPACE, ARCHITECTURE) In order to format an address for a different inferior. Notes on the implementation: In py-arch.c I extended arch_object_to_gdbarch to add an assertion for the type of the PyObject being worked on. Prior to this commit all uses of arch_object_to_gdbarch were guaranteed to pass this function a gdb.Architecture object, but, with this commit, this might not be the case. So, with this commit I've made it a requirement that the PyObject be a gdb.Architecture, and this is checked with the assert. And in order that callers from other files can check if they have a gdb.Architecture object, I've added the new function gdbpy_is_architecture. In py-progspace.c I've added two new function, the first progspace_object_to_program_space, converts a PyObject of type gdb.Progspace to the associated program_space pointer, and gdbpy_is_progspace checks if a PyObject is a gdb.Progspace or not.
2022-03-18gdb/python: remove gdb._mi_commands dictSimon Marchi4-156/+83
The motivation for this patch is the fact that py-micmd.c doesn't build with Python 2, due to PyDict_GetItemWithError being a Python 3-only function: CXX python/py-micmd.o /home/smarchi/src/binutils-gdb/gdb/python/py-micmd.c: In function ‘int micmdpy_uninstall_command(micmdpy_object*)’: /home/smarchi/src/binutils-gdb/gdb/python/py-micmd.c:430:20: error: ‘PyDict_GetItemWithError’ was not declared in this scope; did you mean ‘PyDict_GetItemString’? 430 | PyObject *curr = PyDict_GetItemWithError (mi_cmd_dict.get (), | ^~~~~~~~~~~~~~~~~~~~~~~ | PyDict_GetItemString A first solution to fix this would be to try to replace PyDict_GetItemWithError equivalent Python 2 code. But I looked at why we are doing this in the first place: it is to maintain the `gdb._mi_commands` Python dictionary that we use as a `name -> gdb.MICommand object` map. Since the `gdb._mi_commands` dictionary is never actually used in Python, it seems like a lot of trouble to use a Python object for this. My first idea was to replace it with a C++ map (std::unordered_map<std::string, gdbpy_ref<micmdpy_object>>). While implementing this, I realized we don't really need this map at all. The mi_command_py objects registered in the main MI command table can own their backing micmdpy_object (that's a gdb.MICommand, but seen from the C++ code). To know whether an mi_command is an mi_command_py, we can use a dynamic cast. Since there's one less data structure to maintain, there are less chances of messing things up. - Change mi_command_py::m_pyobj to a gdbpy_ref, the mi_command_py is now what keeps the MICommand alive. - Set micmdpy_object::mi_command in the constructor of mi_command_py. If mi_command_py manages setting/clearing that field in swap_python_object, I think it makes sense that it also takes care of setting it initially. - Move a bunch of checks from micmdpy_install_command to swap_python_object, and make them gdb_asserts. - In micmdpy_install_command, start by doing an mi_cmd_lookup. This is needed to know whether there's a Python MI command already registered with that name. But we can already tell if there's a non-Python command registered with that name. Return an error if that happens, rather than waiting for insert_mi_cmd_entry to fail. Change the error message to "name is already in use" rather than "may already be in use", since it's more precise. I asked Andrew about the original intent of using a Python dictionary object to hold the command objects. The reason was to make sure the objects get destroyed when the Python runtime gets finalized, not later. Holding the objects in global C++ data structures and not doing anything more means that the held Python objects will be decref'd after the Python interpreter has been finalized. That's not desirable. I tried it and it indeed segfaults. Handle this by adding a gdbpy_finalize_micommands function called in finalize_python. This is the mirror of gdbpy_initialize_micommands called in do_start_initialization. In there, delete all Python MI commands. I think it makes sense to do it this way: if it was somehow possible to unload Python support from GDB in the middle of a session we'd want to unregister any Python MI command. Otherwise, these MI commands would be backed with a stale PyObject or simply nothing. Delete tests that were related to `gdb._mi_commands`. Co-Authored-By: Andrew Burgess <aburgess@redhat.com> Change-Id: I060d5ebc7a096c67487998a8a4ca1e8e56f12cd3
2022-03-16gdb/mi: consistently notify user when GDB/MI client uses -thread-selectJan Vrany1-3/+2
GDB notifies users about user selected thread changes somewhat inconsistently as mentioned on gdb-patches mailing list here: https://sourceware.org/pipermail/gdb-patches/2022-February/185989.html Consider GDB debugging a multi-threaded inferior with both CLI and GDB/MI interfaces connected to separate terminals. Assuming inferior is stopped and thread 1 is selected, when a thread 2 is selected using '-thread-select 2' command on GDB/MI terminal: -thread-select 2 ^done,new-thread-id="2",frame={level="0",addr="0x00005555555551cd",func="child_sub_function",args=[],file="/home/jv/Projects/gdb/users_jv_patches/gdb/testsuite/gdb.mi/user-selected-context-sync.c",fullname="/home/uuu/gdb/gdb/testsuite/gdb.mi/user-selected-context-sync.c",line="30",arch="i386:x86-64"} (gdb) and on CLI terminal we get the notification (as expected): [Switching to thread 2 (Thread 0x7ffff7daa640 (LWP 389659))] #0 child_sub_function () at /home/uuu/gdb/gdb/testsuite/gdb.mi/user-selected-context-sync.c:30 30 volatile int dummy = 0; However, now that thread 2 is selected, if thread 1 is selected using 'thread-select --thread 1 1' command on GDB/MI terminal terminal: -thread-select --thread 1 1 ^done,new-thread-id="1",frame={level="0",addr="0x0000555555555294",func="main",args=[],file="/home/jv/Projects/gdb/users_jv_patches/gdb/testsuite/gdb.mi/user-selected-context-sync.c",fullname="/home/jv/Projects/gdb/users_jv_patches/gdb/testsuite/gdb.mi/user-selected-context-sync.c",line="66",arch="i386:x86-64"} (gdb) but no notification is printed on CLI terminal, despite the fact that user selected thread has changed. The problem is that when `-thread-select --thread 1 1` is executed then thread is switched to thread 1 before mi_cmd_thread_select () is called, therefore the condition "inferior_ptid != previous_ptid" there does not hold. To address this problem, we have to move notification logic up to mi_cmd_execute () where --thread option is processed and notify user selected contents observers there if context changes. However, this in itself breaks GDB/MI because it would cause context notification to be sent on MI channel. This is because by the time we notify, MI notification suppression is already restored (done in mi_command::invoke(). Therefore we had to lift notification suppression logic also up to mi_cmd_execute (). This change in made distinction between mi_command::invoke() and mi_command::do_invoke() unnecessary as all mi_command::invoke() did (after the change) was to call do_invoke(). So this patches removes do_invoke() and moves the command execution logic directly to invoke(). With this change, all gdb.mi tests pass, tested on x86_64-linux. Co-authored-by: Andrew Burgess <aburgess@redhat.com> Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=20631
2022-03-14gdb/python/mi: create MI commands using pythonAndrew Burgess5-1/+848
This commit allows a user to create custom MI commands using Python similarly to what is possible for Python CLI commands. A new subclass of mi_command is defined for Python MI commands, mi_command_py. A new file, gdb/python/py-micmd.c contains the logic for Python MI commands. This commit is based on work linked too from this mailing list thread: https://sourceware.org/pipermail/gdb/2021-November/049774.html Which has also been previously posted to the mailing list here: https://sourceware.org/pipermail/gdb-patches/2019-May/158010.html And was recently reposted here: https://sourceware.org/pipermail/gdb-patches/2022-January/185190.html The version in this patch takes some core code from the previously posted patches, but also has some significant differences, especially after the feedback given here: https://sourceware.org/pipermail/gdb-patches/2022-February/185767.html A new MI command can be implemented in Python like this: class echo_args(gdb.MICommand): def invoke(self, args): return { 'args': args } echo_args("-echo-args") The 'args' parameter (to the invoke method) is a list containing (almost) all command line arguments passed to the MI command (--thread and --frame are handled before the Python code is called, and removed from the args list). This list can be empty if the MI command was passed no arguments. When used within gdb the above command produced output like this: (gdb) -echo-args a b c ^done,args=["a","b","c"] (gdb) The 'invoke' method of the new command must return a dictionary. The keys of this dictionary are then used as the field names in the mi command output (e.g. 'args' in the above). The values of the result returned by invoke can be dictionaries, lists, iterators, or an object that can be converted to a string. These are processed recursively to create the mi output. And so, this is valid: class new_command(gdb.MICommand): def invoke(self,args): return { 'result_one': { 'abc': 123, 'def': 'Hello' }, 'result_two': [ { 'a': 1, 'b': 2 }, { 'c': 3, 'd': 4 } ] } Which produces output like: (gdb) -new-command ^done,result_one={abc="123",def="Hello"},result_two=[{a="1",b="2"},{c="3",d="4"}] (gdb) I have required that the fields names used in mi result output must match the regexp: "^[a-zA-Z][-_a-zA-Z0-9]*$" (without the quotes). This restriction was never written down anywhere before, but seems sensible to me, and we can always loosen this rule later if it proves to be a problem. Much harder to try and add a restriction later, once people are already using the API. What follows are some details about how this implementation differs from the original patch that was posted to the mailing list. In this patch, I have changed how the lifetime of the Python gdb.MICommand objects is managed. In the original patch, these object were kept alive by an owned reference within the mi_command_py object. As such, the Python object would not be deleted until the mi_command_py object itself was deleted. This caused a problem, the mi_command_py were held in the global mi command table (in mi/mi-cmds.c), which, as a global, was not cleared until program shutdown. By this point the Python interpreter has already been shutdown. Attempting to delete the mi_command_py object at this point was causing GDB to try and invoke Python code after finalising the Python interpreter, and we would crash. To work around this problem, the original patch added code in python/python.c that would search the mi command table, and delete the mi_command_py objects before the Python environment was finalised. In contrast, in this patch, I have added a new global dictionary to the gdb module, gdb._mi_commands. We already have several such global data stores related to pretty printers, and frame unwinders. The MICommand objects are placed into the new gdb.mi_commands dictionary, and it is this reference that keeps the objects alive. When GDB's Python interpreter is shut down gdb._mi_commands is deleted, and any MICommand objects within it are deleted at this point. This change avoids having to make the mi_cmd_table global, and walk over it from within GDB's python related code. This patch handles command redefinition entirely within GDB's python code, though this does impose one small restriction which is not present in the original code (detailed below), I don't think this is a big issue. However, the original patch relied on being able to finish executing the mi_command::do_invoke member function after the mi_command object had been deleted. Though continuing to execute a member function after an object is deleted is well defined, it is also (IMHO) risky, its too easy for someone to later add a use of the object without realising that the object might sometimes, have been deleted. The new patch avoids this issue. The one restriction that is added to avoid this, is that an MICommand object can't be reinitialised with a different command name, so: (gdb) python cmd = MyMICommand("-abc") (gdb) python cmd.__init__("-def") can't reinitialize object with a different command name This feels like a pretty weird edge case, and I'm happy to live with this restriction. I have also changed how the memory is managed for the command name. In the most recently posted patch series, the command name is moved into a subclass of mi_command, the python mi_command_py, which inherits from mi_command is then free to use a smart pointer to manage the memory for the name. In this patch, I leave the mi_command class unchanged, and instead hold the memory for the name within the Python object, as the lifetime of the Python object always exceeds the c++ object stored in the mi_cmd_table. This adds a little more complexity in py-micmd.c, but leaves the mi_command class nice and simple. Next, this patch adds some extra functionality, there's a MICommand.name read-only attribute containing the name of the command, and a read-write MICommand.installed attribute that can be used to install (make the command available for use) and uninstall (remove the command from the mi_cmd_table so it can't be used) the command. This attribute will be automatically updated if a second command replaces an earlier command. This patch adds additional error handling, and makes more use the gdbpy_handle_exception function. Co-Authored-By: Jan Vrany <jan.vrany@labware.com>
2022-03-07gdb/python: add Type.is_signed propertyAndrew Burgess1-0/+23
Add a new read-only property, Type.is_signed, which is True for signed types, and False otherwise. This property should only be read on types for which Type.is_scalar is true, attempting to read this property for non-scalar types will raise a ValueError. I chose 'is_signed' rather than 'is_unsigned' in order to match the existing Architecture.integer_type method, which takes a 'signed' parameter. As far as I could find, that was the only existing signed/unsigned selector in the Python API, so it seemed reasonable to stay consistent.
2022-03-07gdb/python: add Type.is_scalar propertyAndrew Burgess1-0/+15
Add a new read-only property which is True for scalar types, otherwise, it's False.
2022-02-28Fix maybe-uninitialized warning in py-infthread.cTom Tromey1-1/+3
I got this warning from py-infthread.c using the Fedora 34 system GCC: ../../binutils-gdb/gdb/python/py-infthread.c:102:30: warning: ‘extra_info’ may be used uninitialized in this function [-Wmaybe-uninitialized] I think this happens because GDB_PY_HANDLE_EXCEPTION expands to an 'if' whose condition is always true -- but GCC can't know this. This patch avoids the warning by adding a harmless initialization.
2022-02-28gdb/python: Add gdb.InferiorThread.details attributeAndrew Burgess1-0/+29
This adds a new read-only attribute gdb.InferiorThread.details, this attribute contains a string, the results of target_extra_thread_info for the thread, or None, if target_extra_thread_info returns nullptr. As the string returned by target_extra_thread_info is unstructured, this attribute is only really useful for echoing straight through to the user, but, if a user wants to write a command that displays the same, or a similar 'Thread Id' to the one seen in 'info threads', then they need access to this string. Given that the string produced by target_extra_thread_info varies by target, there's only minimal testing of this attribute, I check that the attribute can be accessed, and that the return value is either None, or a string.
2022-02-24gdb: use a range based for loop when iterating over an arrayAndrew Burgess1-6/+2
Make use of a range based for loop to iterate over a static global array, removing the need to have a null entry at the end of the array. There should be no user visible changes after this commit.
2022-02-15gdb: add a symbol* argument to get_return_valueLancelot SIX1-26/+31
Add an argument to the get_return_value function to indicate the symbol of the function the debuggee is returning from. This will be used by the following patch. Since the function return type can be deduced from the symbol remove the value_type argument which becomes redundant. No user visible change after this patch. Tested on x86_64-linux. Change-Id: Idf1279f1f7199f5022738a6679e0fa63fbd22edc Co-authored-by: Simon Marchi <simon.marchi@polymtl.ca>
2022-02-14Remove LA_PRINT_TYPETom Tromey1-2/+3
This removes the LA_PRINT_TYPE macro, in favor of using ordinary method calls.
2022-02-14gdb/python: move styling support to gdb.stylingAndrew Burgess3-39/+68
This commit moves the two Python functions that are used for styling into a new module, gdb.styling, there's then a small update in python.c so GDB can find the functions in their new location. The motivation for this change is purely to try and reduce the clutter in the top-level gdb module, and encapsulate related functions into modules. I did ponder documenting these functions as part of the Python API, however, doing so would effectively "fix" the API, and I'm still wondering if there's improvements that could be made, also, the colorize function is only called in some cases now that GDB prefers libsource-highlight, so it's not entirely sure how this would work as part of a user facing API. Still, despite these functions never having been part of a documented API, it is possible that a user out there has overridden these to, in some way, customize how GDB performs styling. Moving the function as I propose in this patch could break things for that user, however, fixing this breakage is trivial, and, as these functions were never documented, I don't think we should be obliged to not break user code that relies on them.
2022-02-14gdb: use python to colorize disassembler outputAndrew Burgess2-0/+80
This commit adds styling support to the disassembler output, as such two new commands are added to GDB: set style disassembler enabled on|off show style disassembler enabled In this commit I make use of the Python Pygments package to provide the styling. I did investigate making use of libsource-highlight, however, I found the highlighting results to be inferior to those of Pygments; only some mnemonics were highlighted, and highlighting of register names such as r9d and r8d (on x86-64) was incorrect. To enable disassembler highlighting via Pygments, I've added a new extension language hook, which is then implemented for Python. This hook is very similar to the existing hook for source code colorization. One possibly odd choice I made with the new hook is to pass a gdb.Architecture through, even though this is currently unused. The reason this argument is not used is that, currently, styling is performed identically for all architectures. However, even though the Python function used to perform styling of disassembly output is not part of any documented API, I don't want to close the door on a user overriding this function to provide architecture specific styling. To do this, the user would inevitably require access to the gdb.Architecture, and so I decided to add this field now. The styling is applied within gdb_disassembler::print_insn, to achieve this, gdb_disassembler now writes its output into a temporary buffer, styling is then applied to the contents of this buffer. Finally the gdb_disassembler buffer is copied out to its final destination stream. There's a new test to check that the disassembler output includes some escape sequences, though I don't check for specific colours; the precise colors will depend on which instructions are in the disassembler output, and, I guess, how pygments is configured. The only negative change with this commit is how we currently style addresses in GDB. Currently, when the disassembler wants to print an address, we call back into GDB, and GDB prints the address value using the `address` styling, and the symbol name using `function` styling. After this commit, if pygments is used, then all disassembler styling is done through pygments, and this include the address and symbol name parts of the disassembler output. I don't know how much of an issue this will be for people. There's already some precedent for this in GDB when we look at source styling. For example, function names in styled source listings are not styled using the `function` style, but instead, either GNU Source Highlight, or pygments gets to decide how the function name should be styled. If the Python pygments library is not present then GDB will continue to behave as it always has, the disassembler output is mostly unstyled, but the address and symbols are styled using the `address` and `function` styles, as they are today. However, if the user does `set style disassembler enabled off`, then all disassembler styling is switched off. This obviously covers the use of pygments, but also includes the minimal styling done by GDB when pygments is not available.
2022-02-07gdb/python: allow Value.format_string to return styled outputAndrew Burgess1-2/+5
Add a new argument to the gdb.Value.format_string method, 'styling'. This argument is False by default. When this argument is True, then the returned string can contain output styling escape sequences. When this argument is False, then the returned string will not contain any styling escape sequences. If the returned string is going to be printed to the user, then it is often nice to retain the GDB styling. For the testing, we need to adjust the TERM environment variable, as we do for all the styling tests. I'm now running all of the C tests in gdb.python/py-format-string.exp in an environment where styling could be generated, but only my new test should actually produce styled output, hopefully this will catch the case where a bug might cause format_string to always produce styled output.
2022-02-06gdb: remove SYMBOL_LINE macroSimon Marchi1-1/+1
Add a getter and a setter for a symbol's line. Remove the corresponding macro and adjust all callers. Change-Id: I229f2b8fcf938c07975f641361313a8761fad9a5
2022-02-06gdb: remove SYMBOL_TYPE macroSimon Marchi3-4/+4
Add a getter and a setter for a symbol's type. Remove the corresponding macro and adjust all callers. Change-Id: Ie1a137744c5bfe1df4d4f9ae5541c5299577c8de
2022-02-06gdb: remove SYMBOL_IS_ARGUMENT macroSimon Marchi2-4/+4
Add a getter and a setter for whether a symbol is an argument. Remove the corresponding macro and adjust all callers. Change-Id: I71b4f0465f3dfd2ed8b9e140bd3f7d5eb8d9ee81
2022-02-06gdb: remove SYMBOL_OBJFILE_OWNED macroSimon Marchi1-3/+3
Add a getter and a setter for whether a symbol is objfile owned. Remove the corresponding macro and adjust all callers. Change-Id: Ib7ef3718d65553ae924ca04c3fd478b0f4f3147c
2022-02-06gdb: remove SYMBOL_CLASS macro, add getterSimon Marchi3-8/+8
Change-Id: I83211d5a47efc0564386e5b5ea4a29c00b1fd46a
2022-02-06gdb: remove SYMTAB_OBJFILE macroSimon Marchi1-9/+9
Remove the macro, replace with an equivalent method. Change-Id: I8f9ecd290ad28502e53c1ceca5006ba78bf042eb
2022-02-06gdb: remove SYMTAB_BLOCKVECTOR macroSimon Marchi1-2/+2
Remove the macro, replace with an equivalent method. Change-Id: Id6fe2a79c04bcd6c69ccaefb7a69bc06a476288c
2022-02-06gdb: remove SYMTAB_LINETABLE macro, add getter/setterSimon Marchi1-10/+10
Add a getter and a setter for a symtab's linetable. Remove the corresponding macro and adjust all callers. Change-Id: I159183fc0ccd8e18ab937b3c2f09ef2244ec6e9c
2022-02-06gdb: remove SYMTAB_COMPUNIT macro, add getter/setterSimon Marchi1-1/+1
Add a getter and a setter for a symtab's compunit_symtab. Remove the corresponding macro and adjust all callers. For brevity, I chose the name "compunit" instead of "compunit_symtab" the the field, getter and setter names. Since we are already in symtab context, the _symtab suffix seems redundant. Change-Id: I4b9b731c96e3594f7733e75af1e3d01bc0e4fe92
2022-02-06gdb: remove COMPUNIT_BLOCKVECTOR macro, add getter/setterSimon Marchi1-1/+1
Add a getter and a setter for a compunit_symtab's blockvector. Remove the corresponding macro and adjust all callers. Change-Id: I99484c6619dcbbea7c5d89c72aa660316ca62f64
2022-02-06gdb: remove COMPUNIT_PRODUCER macro, add getter/setterSimon Marchi1-2/+2
Add a getter and a setter for a compunit_symtab's producer. Remove the corresponding macro and adjust all callers. Change-Id: Ia1d6d8a0e247a08a21af23819d71e49b37d8931b
2022-02-06gdb: remove COMPUNIT_OBJFILE macroSimon Marchi1-3/+3
Remove the macro, update all users to use the getter directly. Change-Id: I3f0fd6f4455d1c4ebd5da73b561eb18a979ef1f6
2022-02-04Remove host_hex_valueTom Tromey1-1/+1
I noticed that host_hex_value is redundant, because gdbsupport already has fromhex. This patch removes the former in favor of the latter. Regression tested on x86-64 Fedora 34.
2022-02-02gdb: fix formatting for help set/show extended-promptAndrew Burgess1-3/+2
The formatting of the help text for 'help set extended-prompt' and 'help show extended-prompt' is a little off. Here's the offending snippet: Substitutions are applied to VALUE to compute the real prompt. The currently defined substitutions are: \[ Begins a sequence of non-printing characters. \\ A backslash. \] Ends a sequence of non-printing characters. \e The ESC character. Notice that the line for '\[' is indented more that the others. Turns out this is due to how we build this help text, something which is done in Python. We extended a classes __doc__ string with some dynamically generated text. The classes doc string looks like this: """Set the extended prompt. Usage: set extended-prompt VALUE Substitutions are applied to VALUE to compute the real prompt. The currently defined substitutions are: """ Notice the closing """ are in a line of their own, and include some white space just before. It's this extra white space that's causing the problem. Fix the formatting issue by moving the """ to the end of the previous line. I then add the extra newline in at the point where the doc string is merged with the dynamically generated text. Now everything lines up correctly.
2022-02-01gdb/python: fix gdb.Objfile.__repr__ () for dynamically compiled codeJan Vrany1-1/+1
While experimenting with JIT reader API I realized that calling repr () on objfile created by JIT reader crashes GDB. The problem was that objfpy_repr () called objfile_filename () which returned NULL, causing PyString_FromFormat () to crash. This commit fixes this problem by using objfile_name () instead of objfile_filename (). This also makes consistent with the value of gdb.Objfile.filename variable.
2022-01-26gdb/python: handle non utf-8 characters when source highlightingAndrew Burgess2-16/+21
This commit adds support for source files that contain non utf-8 characters when performing source styling using the Python pygments package. This does not change the behaviour of GDB when the GNU Source Highlight library is used. For the following problem description, assume that either GDB is built without GNU Source Highlight support, of that this has been disabled using 'maintenance set gnu-source-highlight enabled off'. The initial problem reported was that a source file containing non utf-8 characters would cause GDB to print a Python exception, and then display the source without styling, e.g.: Python Exception <class 'UnicodeDecodeError'>: 'utf-8' codec can't decode byte 0xc0 in position 142: invalid start byte /* Source code here, without styling... */ Further, as the user steps through different source files, each time the problematic source file was evicted from the source cache, and then later reloaded, the exception would be printed again. Finally, this problem is only present when using Python 3, this issue is not present for Python 2. What makes this especially frustrating is that GDB can clearly print the source file contents, they're right there... If we disable styling completely, or make use of the GNU Source Highlight library, then everything is fine. So why is there an error when we try to apply styling using Python? The problem is the use of PyString_FromString (which is an alias for PyUnicode_FromString in Python 3), this function converts a C string into a either a Unicode object (Py3) or a str object (Py2). For Python 2 there is no unicode encoding performed during this function call, but for Python 3 the input is assumed to be a uft-8 encoding string for the purpose of the conversion. And here of course, is the problem, if the source file contains non utf-8 characters, then it should not be treated as utf-8, but that's what we do, and that's why we get an error. My first thought when looking at this was to spot when the PyString_FromString call failed with a UnicodeDecodeError and silently ignore the error. This would mean that GDB would print the source without styling, but would also avoid the annoying exception message. However, I also make use of `pygmentize`, a command line wrapper around the Python pygments module, which I use to apply syntax highlighting in the output of `less`. And this command line wrapper is quite happy to syntax highlight my source file that contains non utf-8 characters, so it feels like the problem should be solvable. It turns out that inside the pygments module there is already support for guessing the encoding of the incoming file content, if the incoming content is not already a Unicode string. This is what happens for Python 2 where the incoming content is of `str` type. We could try and make GDB smarter when it comes to converting C strings into Python Unicode objects; this would probably require us to just try a couple of different encoding schemes rather than just giving up after utf-8. However, I figure, why bother? The pygments module already does this for us, and the colorize API is not part of the documented external API of GDB. So, why not just change the colorize API, instead of the content being a Unicode string (for Python 3), lets just make the content be a bytes object. The pygments module can then take responsibility for guessing the encoding. So, currently, the colorize API receives a unicode object, and returns a unicode object. I propose that the colorize API receive a bytes object, and return a bytes object.
2022-01-26Always call the wrap_here methodTom Tromey1-1/+1
This changes all existing calls to wrap_here to call the method on the appropriate ui_file instead. The choice of ui_file is determined by context.
2022-01-26Convert wrap_here to use integer parameterTom Tromey2-4/+4
I think it only really makes sense to call wrap_here with an argument consisting solely of spaces. Given this, it seemed better to me that the argument be an int, rather than a string. This patch is the result. Much of it was written by a script.
2022-01-26gdb/python: improve the auto help text for gdb.ParameterAndrew Burgess1-11/+73
This commit attempts to improve the help text that is generated for gdb.Parameter objects when the user fails to provide their own documentation. Documentation for a gdb.Parameter is currently pulled from two sources: the class documentation string, and the set_doc/show_doc class attributes. Thus, a fully documented parameter might look like this: class Param_All (gdb.Parameter): """This is the class documentation string.""" show_doc = "Show the state of this parameter" set_doc = "Set the state of this parameter" def get_set_string (self): val = "on" if (self.value == False): val = "off" return "Test Parameter has been set to " + val def __init__ (self, name): super (Param_All, self).__init__ (name, gdb.COMMAND_DATA, gdb.PARAM_BOOLEAN) self._value = True Param_All ('param-all') Then in GDB we see this: (gdb) help set param-all Set the state of this parameter This is the class documentation string. Which is fine. But, if the user skips both of the documentation parts like this: class Param_None (gdb.Parameter): def get_set_string (self): val = "on" if (self.value == False): val = "off" return "Test Parameter has been set to " + val def __init__ (self, name): super (Param_None, self).__init__ (name, gdb.COMMAND_DATA, gdb.PARAM_BOOLEAN) self._value = True Param_None ('param-none') Now in GDB we see this: (gdb) help set param-none This command is not documented. This command is not documented. That's not great, the duplicated text looks a bit weird. If we drop different parts we get different results. Here's what we get if the user drops the set_doc and show_doc attributes: (gdb) help set param-doc This command is not documented. This is the class documentation string. That kind of sucks, we say it's undocumented, then proceed to print the documentation. Finally, if we drop the class documentation but keep the set_doc and show_doc: (gdb) help set param-set-show Set the state of this parameter This command is not documented. That seems OK. So, I think there's room for improvement. With this patch, for the four cases above we now see this: # All values provided by the user, no change in this case: (gdb) help set param-all Set the state of this parameter This is the class documentation string. # Nothing provided by the user, the first string is now different: (gdb) help set param-none Set the current value of 'param-none'. This command is not documented. # Only the class documentation is provided, the first string is # changed as in the previous case: (gdb) help set param-doc Set the current value of 'param-doc'. This is the class documentation string. # Only the set_doc and show_doc are provided, this case is unchanged # from before the patch: (gdb) help set param-set-show Set the state of this parameter This command is not documented. The one place where this change might be considered a negative is when dealing with prefix commands. If we create a prefix command but don't supply the set_doc / show_doc strings, then this is what we saw before my patch: (gdb) python Param_None ('print param-none') (gdb) help set print set print, set pr, set p Generic command for setting how things print. List of set print subcommands: ... snip ... set print param-none -- This command is not documented. ... snip ... And after my patch: (gdb) python Param_None ('print param-none') (gdb) help set print set print, set pr, set p Generic command for setting how things print. List of set print subcommands: ... snip ... set print param-none -- Set the current value of 'print param-none'. ... snip ... This seems slightly less helpful than before, but I don't think its terrible. Additionally, I've changed what we print when the get_show_string method is not provided in Python. Back when gdb.Parameter was first added to GDB, we didn't provide a show function when registering the internal command object within GDB. As a result, GDB would make use of its "magic" mangling of the show_doc string to create a sentence that would display the current value (see deprecated_show_value_hack in cli/cli-setshow.c). However, when we added support for the get_show_string method to gdb.Parameter, there was an attempt to maintain backward compatibility by displaying the show_doc string with the current value appended, see get_show_value in py-param.c. Unfortunately, this isn't anywhere close to what deprecated_show_value_hack does, and the results are pretty poor, for example, this is GDB before my patch: (gdb) show param-none This command is not documented. off I think we can all agree that this is pretty bad. After my patch, we how show this: (gdb) show param-none The current value of 'param-none' is "off". Which at least is a real sentence, even if it's not very informative. This patch does change the way that the Python API behaves slightly, but only in the cases when the user has missed providing GDB with some information. In most cases I think the new behaviour is a lot better, there's the one case (noted above) which is a bit iffy, but I think is still OK. I've updated the existing gdb.python/py-parameter.exp test to cover the modified behaviour. Finally, I've updated the documentation to (I hope) make it clearer how the various bits of help text come together.
2022-01-26gdb/python: add gdb.history_count functionAndrew Burgess3-0/+11
Add a new function gdb.history_count to the Python api, this function returns an integer, the number of items in GDB's value history. This is useful if you want to pull items from the history by their absolute number, for example, if you wanted to show a complete history list. Previously we could figure out how many items are in the history list by trying to fetch the items, and then catching the exception when the item is not available, but having this function seems nicer.
2022-01-26Add a way to temporarily set a gdb parameter from PythonTom Tromey1-0/+19
It's sometimes useful to temporarily set some gdb parameter from Python. Now that the 'endian' crash is fixed, and now that the current language is no longer captured by the Python layer, it seems reasonable to add a helper function for this situation. This adds a new gdb.with_parameter function. This creates a context manager which temporarily sets some parameter to a specified value. The old value is restored when the context is exited. This is most useful with the Python "with" statement: with gdb.with_parameter('language', 'ada'): ... do Ada stuff This also adds a simple function to set a parameter, gdb.set_parameter, as suggested by Andrew. This is PR python/10790. Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=10790
2022-01-26Fix another crash with gdb parameters in PythonTom Tromey1-2/+2
While looking into the language-capturing issue, I found another way to crash gdb using parameters from Python: (gdb) python print(gdb.parameter('endian')) (This is related to PR python/12188, though this patch isn't going to fix what that bug is really about.) The problem here is that the global variable that underlies the "endian" parameter is initialized to NULL. However, that's not a valid value for an "enum" set/show parameter. My understanding is that, in gdb, an "enum" parameter's underlying variable must have a value that is "==" (not just strcmp-equal) to one of the values coming from the enum array. This invariant is relied on in various places. I started this patch by fixing the problem with "endian". Then I added some assertions to add_setshow_enum_cmd to try to catch other problems of the same type. This patch fixes all the problems that I found. I also looked at all the calls to add_setshow_enum_cmd to ensure that they were all included in the gdb I tested. I think they are: there are no calls in nat-* files, or in remote-sim.c; and I was trying a build with all targets, Python, and Guile enabled. Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=12188
2022-01-26Change how Python architecture and language are handledTom Tromey18-105/+136
Currently, gdb's Python layer captures the current architecture and language when "entering" Python code. This has some undesirable effects, and so this series changes how this is handled. First, there is code like this: gdbpy_enter enter_py (python_gdbarch, python_language); This is incorrect, because both of these are NULL when not otherwise assigned. This can cause crashes in some cases -- I've added one to the test suite. (Note that this crasher is just an example, other ones along the same lines are possible.) Second, when the language is captured in this way, it means that Python code cannot affect the current language for its own purposes. It's reasonable to want to write code like this: gdb.execute('set language mumble') ... stuff using the current language gdb.execute('set language previous-value') However, this won't actually work, because the language is captured on entry. I've added a test to show this as well. This patch changes gdb to try to avoid capturing the current values. The Python concept of the current gdbarch is only set in those few cases where a non-default value is computed or needed; and the language is not captured at all -- instead, in the cases where it's required, the current language is temporarily changed.
2022-01-25Reduce explicit use of gdb_stdoutTom Tromey1-1/+1
In an earlier version of the pager rewrite series, it was important to audit unfiltered output calls to see which were truly necessary. This is no longer necessary, but it still seems like a decent cleanup to change calls to avoid explicitly passing gdb_stdout. That is, rather than using something like fprintf_unfiltered with gdb_stdout, the code ought to use plain printf_unfiltered instead. This patch makes this change. I went ahead and converted all the _filtered calls I could find, as well, for the same clarity.
2022-01-18Move gdb obstack code to gdbsupportTom Tromey1-1/+1
This moves the gdb-specific obstack code -- both extensions like obconcat and obstack_strdup, and things like auto_obstack -- to gdbsupport.
2022-01-12gdb/python: add gdb.host_charset functionAndrew Burgess1-0/+13
We already have gdb.target_charset and gdb.target_wide_charset. This commit adds gdb.host_charset along the same lines.
2022-01-05Fix inferior_thread attribute in new_thread eventHannes Domani1-1/+2
Commit 72ee03ff58 fixed a use-after-move bug in add_thread_object, but it changed the inferior_thread attribute to contain the inferior instead of the actual thread. This now uses the thread_obj in its new location instead. Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=28429
2022-01-01Automatic Copyright Year update after running gdb/copyright.pyJoel Brobecker81-81/+81
This commit brings all the changes made by running gdb/copyright.py as per GDB's Start of New Year Procedure. For the avoidance of doubt, all changes in this commits were performed by the script.