aboutsummaryrefslogtreecommitdiff
AgeCommit message (Collapse)AuthorFilesLines
2023-03-30aarch64: Resync field namesRichard Sandiford1-7/+7
This patch just makes the comments in aarch64-opc.c:fields match the names of the associated FLD_* enum.
2023-03-30aarch64: Regularise FLD_* suffixesRichard Sandiford6-55/+55
Some FLD_imm* suffixes used a counting scheme such as FLD_immN, FLD_immN_2, FLD_immN_3, etc., while others used the lsb as the suffix. The latter seems more mnemonic, and was a big help in doing the SME2 work. Similarly, the _10 suffix on FLD_SME_size_10 was nonobvious. Presumably it indicated a 2-bit field, but it actually starts in bit 22.
2023-03-30aarch64: Rename some of GAS's REG_TYPE_* macrosRichard Sandiford1-71/+71
In GAS, the vector and predicate registers are identified by REG_TYPE_VN, REG_TYPE_ZN and REG_TYPE_PN. This "N" is obviously a placeholder for the register number. However, we don't use that convention for integer and FP registers, and (more importantly) SME2 adds "predicate-as-counter" registers that are denoted PN. This patch therefore drops the "N" suffix from the existing registers. The main hitch is that Z was also used for the zero register in things like R_Z, but using ZR seems more consistent with the SP-based names.
2023-03-30aarch64: Add a aarch64_cpu_supports_inst_p helperRichard Sandiford3-2/+17
Quite a lot of SME2 instructions have an opcode bit that selects between 32-bit and 64-bit forms of an instruction, with the 32-bit forms being part of base SME2 and with the 64-bit forms being part of an optional extension. It's nevertheless useful to have a single opcode entry for both forms since (a) that matches the ISA definition and (b) it tends to improve error reporting. This patch therefore adds a libopcodes function called aarch64_cpu_supports_inst_p that tests whether the target supports a particular instruction. In future it will depend on internal libopcodes routines.
2023-03-30aarch64: Reorder some OP_SVE_* macrosRichard Sandiford1-16/+16
This patch just moves some out-of-order-looking OP_SVE_* macros.
2023-03-30aarch64: Rename aarch64-tbl.h OP_SME_* macrosRichard Sandiford1-81/+77
This patch renames the OP_SME_* macros in aarch64-tbl.h so that they follow the same scheme as the OP_SVE_* ones. It also uses OP_SVE_ as the prefix, since there is no real distinction between the SVE and SME uses of qualifiers: a macro defined for one can be useful for the other too.
2023-03-30aarch64: Tweak priorities of parsing-related errorsRichard Sandiford2-11/+51
There are three main kinds of error reported during parsing, in increasing order of priority: - AARCH64_OPDE_RECOVERABLE (register seen instead of immediate) - AARCH64_OPDE_SYNTAX_ERROR - AARCH64_OPDE_FATAL_SYNTAX_ERROR This priority makes sense when comparing errors reported against the same operand. But if we get to operand 3 (say) and see a register instead of an immediate, that's likely to be a better match than something that fails with a syntax error at operand 1. The idea of this patch is to prioritise parsing-related errors based on operand index first, then by error code. Post-parsing errors still win over parsing errors, and their relative priorities don't change.
2023-03-30aarch64: Try to report invalid variants against the closest matchRichard Sandiford7-112/+131
If an instruction has invalid qualifiers, GAS would report the error against the final opcode entry that got to the qualifier- checking stage. It seems better to report the error against the opcode entry that had the closest match, just like we pick the closest match within an opcode entry for the "did you mean this?" message. This patch adds the number of invalid operands as an argument to AARCH64_OPDE_INVALID_VARIANT and then picks the AARCH64_OPDE_INVALID_VARIANT with the lowest argument.
2023-03-30aarch64: Tweak register list errorsRichard Sandiford4-20/+18
The error for invalid register lists had the form: invalid number of registers in the list; N registers are expected at operand M -- `insn' This seems a bit verbose. Also, the "bracketing" is really: (invalid number of registers in the list; N registers are expected) at operand M but the semicolon works against that. This patch goes for slightly shorter messages, setting a template that later patches can use for more complex cases.
2023-03-30aarch64: Make AARCH64_OPDE_REG_LIST take a bitfieldRichard Sandiford2-21/+35
AARCH64_OPDE_REG_LIST took a single operand that specified the expected number of registers. However, there are quite a few SME2 instructions that have both 2-register forms and (separate) 4-register forms. If the user tries to use a 3-register list, it isn't obvious which opcode entry they meant. Saying that we expect 2 registers and saying that we expect 4 registers would both be wrong. This patch therefore switches the operand to a bitfield. If a AARCH64_OPDE_REG_LIST is reported against multiple opcode entries, the patch ORs up the expected lengths. This has no user-visible effect yet. A later patch adds more error strings, alongside tests that use them.
2023-03-30aarch64: Add an operand class for SVE register listsRichard Sandiford5-27/+27
SVE register lists were classified as SVE_REG, since there had been no particular reason to separate them out. However, some SME2 instructions have tied register list operands, and so we need to distinguish registers and register lists when checking whether two operands match. Also, the register list operands used a general error message, even though we already have a dedicated error code for register lists that are the wrong length.
2023-03-30aarch64: Commonise checks for index operandsRichard Sandiford1-18/+32
This patch splits out the constraint checking for index operands, so that it can be reused by new SME2 operands.
2023-03-30aarch64: Add an error code for out-of-range registersRichard Sandiford3-7/+31
libopcodes currently reports out-of-range registers as a general AARCH64_OPDE_OTHER_ERROR. However, this means that each register range needs its own hard-coded string, which is a bit cumbersome if the range is determined programmatically. This patch therefore adds a dedicated error type for out-of-range errors.
2023-03-30aarch64: Deprioritise AARCH64_OPDE_REG_LISTRichard Sandiford2-8/+12
SME2 has many instructions that take a list of SVE registers. There are often multiple forms, with different forms taking different numbers of registers. This means that if, after a successful parse and qualifier match, we find that the number of registers does not match the opcode entry, the associated error should have a lower priority/severity than other errors reported at the same stage. For example, if there are 2-register and 4-register forms of an instruction, and if the assembly code uses the 2-register form with an out-of-range value, the out-of-range value error against the 2-register instruction should have a higher priority than the "wrong number of registers" error against the 4-register instruction. This is tested by the main SME2 patches, but seemed worth splitting out.
2023-03-30aarch64: Update operand_mismatch_kind_namesRichard Sandiford2-1/+6
The contents of operand_mismatch_kind_names were out of sync with the enum.
2023-03-30aarch64: Rework reporting of failed register checksRichard Sandiford23-972/+1202
There are many opcode table entries that share the same mnemonic. Trying to parse an invalid assembly line will trigger an error for each of these entries, but the specific error might vary from one entry to another, depending on the exact nature of the problem. GAS has quite an elaborate system for picking the most appropriate error out of all the failed matches. And in many cases it works well. However, one of the limitations is that the error is always reported against a single opcode table entry. If that table entry isn't the one that the user intended to use, then the error can end up being overly specific. This is particularly true if an instruction has a typoed register name, or uses a type of register that is not accepted by any opcode table entry. For example, one of the expected error matches for an attempted SVE2 instruction is: Error: operand 1 must be a SIMD scalar register -- `addp z32\.s,p0/m,z32\.s,z0\.s' even though the hypothetical user was presumably attempting to use the SVE form of ADDP rather than the Advanced SIMD one. There are many other instances of this in the testsuite. The problem becomes especially acute with SME2, since many SME2 instructions reuse existing mnemonics. This could lead to us reporting an SME-related error against a non-SME instruction, or a non-SME-related error against an SME instruction. This patch tries to improve things by collecting together all the register types that an opcode table entry expected for a given operand. It also records what kind of register was actually seen, if any. It then tries to summarise all this in a more directed way, falling back to a generic error if the combination defies a neat summary. The patch includes tests for all new messages except REG_TYPE_ZA, which only triggers with SME2. To test this, I created an assembly file that contained the cross product of all known mnemonics and one example from each register class. I then looked for cases where the new routines fell back on the generic errors ("expected a register" or "unexpected register type"). I locally added dummy messages for each one until there were no more hits. The patch adds a specimen instruction to diagnostics.s for each of these combinations. In each case, the combination didn't seem like something that could be summarised in a natural way, so the generic messages seemed better. There's always going to be an element of personal taste around this kind of thing though. Adding more register types made 1<<REG_TYPE_MAX exceed the range of the type, but we don't actually need/want 1<<REG_TYPE_MAX.
2023-03-30aarch64: Try to avoid inappropriate default errorsRichard Sandiford6-5/+26
After parsing a '{' and the first register, parse_typed_reg would report errors in subsequent registers in the same way as for the first register. It used set_default_error, which reports errors of the form "operand N must be X". The problem is that if there are multiple opcode entries for the same mnemonic, there could be several matches that lead to a default error. There's no guarantee that the default error for the register list is the one that will be chosen. To take an example from the testsuite: ext z0.b,{z31.b,z32.b},#0 gave: operand 2 must be an SVE vector register with the error being reported against the single-vector version of ext, even though the operand is clearly a list. This patch uses set_fatal_syntax_error to bump the priority of the error once we're sure that the operand is a list of the right type.
2023-03-30aarch64: Improve errors for malformed register listsRichard Sandiford6-21/+41
parse_typed_reg is used for parsing both bare registers and registers that occur in lists. If it doesn't see a register, or sees an unexpected kind of register, it queues a default error to report the problem. These default errors have the form "operand N must be an X", where X comes from the operand table. If there are multiple opcode entries that report default errors, GAS tries to pick the most appropriate one, using the opcode table order as a tiebreaker. But this can lead to cases where a syntax error in a register list is reported against an opcode that doesn't accept register lists. For example, the unlikely error: ext z0.b,{,},#0 is reported as: operand 2 must be an SVE vector register -- `ext z0.b,{,},#0' even though operand 2 can be a register list. If we've parsed the opening '{' of a register list, and then see something that isn't remotely register-like, it seems better to report that directly as a syntax error, rather than rely on the default error. The operand won't be a valid list of anything, so there's no need to pick a specific Y in "operand N must be a list of Y".
2023-03-30aarch64: Tweak parsing of integer & FP registersRichard Sandiford1-29/+42
Integer registers were parsed indirectly through aarch64_reg_parse_32_64 (and thus aarch64_addr_reg_parse) rather than directly through parse_reg. This was because we need the qualifier associated with the register, and the logic to calculate that was buried in aarch64_addr_reg_parse. The code that parses FP registers had the same need, but it open-coded the calculation of the qualifier. This patch tries to handle both cases in the same way. It is needed by a later patch that tries to improve the register-related diagnostics.
2023-03-30aarch64: Tweak errors for base & offset registersRichard Sandiford9-293/+308
parse_address_main currently uses get_reg_expected_msg to report invalid base and offset registers, but the disadvantage of doing that is that it isn't immediately clear which register is wrong (the base or the offset). A later patch moves away from using get_reg_expected_msg for failed type checks, but doing that here didn't seem like the best approach. The patch tries to use more tailored messages instead.
2023-03-30aarch64: Tweak error for missing immediate offsetRichard Sandiford5-18/+18
This patch tweaks the error message that is printed when a ZA-style index is missing the immediate offset.
2023-03-30aarch64: Move w12-w15 range check to libopcodesRichard Sandiford8-32/+51
In SME, the vector select register had to be in the range w12-w15, so it made sense to enforce that during parsing. However, SME2 adds instructions for which the range is w8-w11 instead. This patch therefore moves the range check from the parsing stage to the constraint-checking stage. Also, the previous error used a capitalised range W12-W15, whereas other register range errors used lowercase ranges like p0-p7. A quick internal poll showed a preference for the lowercase form, so the patch uses that. The patch uses "selection register" rather than "vector select register" so that the terminology extends more naturally to PSEL.
2023-03-30aarch64: Commonise index parsingRichard Sandiford1-21/+21
Just a minor clean-up to factor out the index parsing, partly to ensure that the error handling remains consistent. No behavioural change intended.
2023-03-30aarch64: Consolidate ZA slice parsingRichard Sandiford5-72/+55
Now that parse_typed_reg checks the range of tile register numbers and libopcodes checks the range of vector select offsets, there's very little difference between the parsing of ZA tile indices, ZA array indices, and PSEL indices. The main one is that ZA array indices don't currently allow "za" to be qualified, but we need to remove that restriction for SME2. This patch therefore consolidates all three parsers into a single routine, parameterised by the type of register that they expect.
2023-03-30aarch64: Move ZA range checks to aarch64-opc.cRichard Sandiford12-165/+145
This patch moves the range checks on ZA vector select offsets from gas to libopcodes. Doing the checks there means that the error messages contain the expected range. It also fits in better with the error severity scheme, which becomes important later. (This is because out-of-range indices are treated as more severe than syntax errors, on the basis that parsing must have succeeded if we get to the point of checking the completed opcode.) The patch also adds a new check_za_access function for checking ZA accesses. That's a bit over the top for one offset check, but the function becomes more complex with later patches. sme-9-illegal.s checked for an invalid .q suffix using: psel p1, p15, p3.q[w15] but this is doubly invalid because it misses the immediate part of the index. The patch keeps that test but adds another with a zero index, so that .q is the only thing wrong. The aarch64-tbl.h change includes neatening up the backslash positions.
2023-03-30aarch64: Pass aarch64_indexed_za to parsersRichard Sandiford1-152/+78
ZA indices have more parts than most operands, so passing these parts around individually is more awkward than for other operand types. Things aren't too bad at the moment, but SME2 adds two further pieces: an offset range and a vector group size. This patch therefore replaces arguments for the individual pieces with a single argument for the index as a whole.
2023-03-30aarch64: Make indexed_za use 64-bit immediatesRichard Sandiford2-4/+4
A later patch moves the range checking for ZA vector select offsets from gas to libopcodes. That in turn requires the immediate field to be big enough to support all parsed values. This shouldn't be a particularly size-sensitive structure, so there should be no memory problems with doing this.
2023-03-30aarch64: Rename za_tile_vector to za_indexRichard Sandiford5-55/+58
za_tile_vector is also used for indexing ZA as a whole, rather than just for indexing tiles. The former is more common than the latter in SME2, so this patch generalises the name to "indexed_za". The patch also names the associated structure, so that later patches can reuse it during parsing.
2023-03-30aarch64: Treat ZA as a registerRichard Sandiford5-48/+91
We already treat the ZA tiles ZA0-ZA15 as registers. This patch does the same for ZA itself. parse_sme_zero_mask can then parse ZA tiles and ZA in the same way, through parsed_type_reg. One important effect of going through parsed_type_reg (in general) is that it allows ZA to take qualifiers. This is necessary for many SME2 instructions. However, to support existing unqualified uses of ZA, parse_reg_with_qual needs to treat the qualiier as optional. Hopefully the net effect is to give better error messages, since now that SME2 makes "za.<T>" valid in some contexts, it might be natural to use it (incorrectly) in ZERO too. While there, the patch also tweaks the error messages for invalid ZA tiles, to try to make some cases more specific. For now, parse_sme_za_array just uses parse_reg, rather than parse_typed_reg/parse_reg_with_qual. A later patch consolidates the parsing further.
2023-03-30aarch64: Consolidate ZA tile range checksRichard Sandiford6-163/+127
Now that all parsing of ZA tile names goes through parse_typed_reg, we can check there for out-of-range tile numbers. The other check performed by parse_sme_zada_operand was to reject .q, but that can now be done via F_STRICT instead. (.q tiles are valid in other contexts, so they shouldn't be rejected in parse_typed_reg.)
2023-03-30aarch64: Reuse parse_typed_reg for ZA tilesRichard Sandiford1-51/+47
This patch reuses the general parse_typed_reg for ZA tiles. This involves adding a way of suppressing the usual treatment of register indices, since ZA indices look very different from Advanced SIMD and SVE vector indices.
2023-03-30aarch64: Rework parse_typed_reg interfaceRichard Sandiford1-71/+53
parse_typed_reg returned a register number and passed the register type back using a pointer parameter. It seems simpler to return the register entry instead, since that has both pieces of information in one place. The patch also replaces the boolean in_reg_list parameter with a mask of flags. This hopefully makes calls easier to read (more self-documenting than "true" or "false"), but more importantly, it allows a later patch to add a second flag.
2023-03-30aarch64: Move vectype_to_qualifier further upRichard Sandiford1-75/+75
This patch just moves vectype_to_qualifier further up, so that a later patch can call it at an earlier point in the file. No behavioural change intended.
2023-03-30aarch64: Add REG_TYPE_ZATHVRichard Sandiford1-14/+9
This patch adds a multi-register type that includes both REG_TYPE_ZATH and REG_TYPE_ZATV. This slightly simplifies the existing code, but the main purpose is to enable later patches.
2023-03-30aarch64: Rename REG_TYPE_ZA* to REG_TYPE_ZAT*Richard Sandiford1-10/+11
The ZA tile registers were called REG_TYPE_ZA, REG_TYPE_ZAH and REG_TYPE_ZAV. However, a later patch wants to make plain "za" a register type too, and REG_TYPE_ZA is the obvious name for that. This patch therefore adds "T" (tile) to the existing names.
2023-03-30aarch64: Use aarch64_operand_error more widelyRichard Sandiford1-22/+8
GAS's aarch64_instruction had its own cut-down error record, but it's better for later patches if it reuses the binutils-wide aarch64_operand_error instead. The main difference is that aarch64_operand_error can store arguments to the error while aarch64_instruction couldn't.
2023-03-30aarch64: Make SME instructions use F_STRICTRichard Sandiford4-57/+64
This patch makes all SME instructions use F_STRICT, so that qualifiers have to be provided explicitly rather than being inferred from other operands. The main change is to move the qualifier setting from the operand-level decoders to the opcode level. This is one step towards consolidating the ZA parsing code and extending it to handle SME2.
2023-03-30aarch64: Fix SVE2 register/immediate distinctionRichard Sandiford3-1/+13
GAS refuses to interpret register names like x0 as unadorned immediates, due to the obvious potential for confusion with register operands. (An explicit #x0 is OK.) For compatibility reasons, we can't extend the set of registers that GAS rejects for existing instructions. For example: mov x0, z0 was valid code before SVE was added, so it needs to stay valid code even when SVE is enabled. But we can make GAS reject newer registers in newer instructions. The SVE instruction: and z0.s, z0.s, z0.h is therefore invalid, rather than z0.h being an immediate. This patch extends the SVE behaviour to SVE2. The old call to AARCH64_CPU_HAS_FEATURE was technically the wrong way around, although it didn't matter in practice for base SVE instructions since their avariants only set SVE.
2023-03-30aarch64: Restrict range of PRFM opcodesRichard Sandiford5-17/+26
In the register-index forms of PRFM, the unallocated prefetch opcodes 24-31 have been reused for the encoding of the new RPRFM instruction. The PRFM opcode space is now capped at 23 for these forms. The other forms of PRFM are unaffected.
2023-03-30aarch64: Fix PSEL opcode maskRichard Sandiford3-1/+9
The opcode mask for PSEL was missing some bits, which meant that some upcoming SME2 opcodes would be misinterpreted as PSELs.
2023-03-30aarch64: Add sme-i16i64 and sme-f64f64 aliasesRichard Sandiford6-30/+184
Most extension flags are named after the associated architectural FEAT_* flags, but sme-i64 and sme-f64 were exceptions. This patch adds sme-i16i64 and sme-f64f64 aliases, but keeps the old names too for compatibility.
2023-03-30Fix an illegal memory access triggered by parsing corrupt DWARF info.Nick Clifton2-3/+35
PR 30284 * dwarf.c (read_and_display_attr_value): Detect and ignore negative base values.
2023-03-30gdb/python: Add new gdb.unwinder.FrameId classAndrew Burgess4-23/+73
When writing an unwinder it is necessary to create a new class to act as a frame-id. This new class is almost certainly just going to set a 'sp' and 'pc' attribute within the instance. This commit adds a little helper class gdb.unwinder.FrameId that does this job. Users can make use of this to avoid having to write out standard boilerplate code any time they write an unwinder. Of course, if the user wants their FrameId class to be more complicated in some way, then they can still write their own class, just like they could before. I've simplified the example code in the documentation to now use the new helper class, and I've also made use of this helper within the testsuite. Any existing user code will continue to work just as it did before after this change. Reviewed-By: Eli Zaretskii <eliz@gnu.org> Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: Allow gdb.UnwindInfo to be created with non gdb.Value argsAndrew Burgess5-51/+111
Currently when creating a gdb.UnwindInfo object a user must call gdb.PendingFrame.create_unwind_info and pass a frame-id object. The frame-id object should have at least a 'sp' attribute, and probably a 'pc' attribute too (it can also, in some cases have a 'special' attribute). Currently all of these frame-id attributes need to be gdb.Value objects, but the only reason for that requirement is that we have some code in py-unwind.c that only handles gdb.Value objects. If instead we switch to using get_addr_from_python in py-utils.c then we will support both gdb.Value objects and also raw numbers, which might make things simpler in some cases. So, I started rewriting pyuw_object_attribute_to_pointer (in py-unwind.c) to use get_addr_from_python. However, while looking at the code I noticed a problem. The pyuw_object_attribute_to_pointer function returns a boolean flag, if everything goes OK we return true, but we return false in two cases, (1) when the attribute is not present, which might be acceptable, or might be an error, and (2) when we get an error trying to extract the attribute value, in which case a Python error will have been set. Now in pending_framepy_create_unwind_info we have this code: if (!pyuw_object_attribute_to_pointer (pyo_frame_id, "sp", &sp)) { PyErr_SetString (PyExc_ValueError, _("frame_id should have 'sp' attribute.")); return NULL; } Notice how we always set an error. This will override any error that is already set. So, if you create a frame-id object that has an 'sp' attribute, but the attribute is not a gdb.Value, then currently we fail to extract the attribute value (it's not a gdb.Value) and set this error in pyuw_object_attribute_to_pointer: rc = pyuw_value_obj_to_pointer (pyo_value.get (), addr); if (!rc) PyErr_Format ( PyExc_ValueError, _("The value of the '%s' attribute is not a pointer."), attr_name); Then we return to pending_framepy_create_unwind_info and immediately override this error with the error about 'sp' being missing. This all feels very confused. Here's my proposed solution: pyuw_object_attribute_to_pointer will now return a tri-state enum, with states OK, MISSING, or ERROR. The meanings of these states are: OK - Attribute exists and was extracted fine, MISSING - Attribute doesn't exist, no Python error was set. ERROR - Attribute does exist, but there was an error while extracting it, a Python error was set. We need to update pending_framepy_create_unwind_info, the only user of pyuw_object_attribute_to_pointer, but now I think things are much clearer. Errors from lower levels are not blindly overridden with the generic meaningless error message, but we still get the "missing 'sp' attribute" error when appropriate. This change also includes the switch to get_addr_from_python which was what started this whole journey. For well behaving user code there should be no visible changes after this commit. For user code that hits an error, hopefully the new errors should be more helpful in figuring out what's gone wrong. Additionally, users can now use integers for the 'sp' and 'pc' attributes in their frame-id objects if that is useful. Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb: have value_as_address call unpack_pointerAndrew Burgess1-5/+4
While refactoring some other code in gdb/python/* I wanted to merge two code paths. One path calls value_as_address, while the other calls unpack_pointer. I suspect calling value_as_address is the correct choice, but, while examining the code I noticed that value_as_address calls unpack_long rather than unpack_pointer. Under the hood, unpack_pointer does just call unpack_long so there's no real difference here, but it feels like value_as_address should call unpack_pointer. I've updated the code to use unpack_pointer, and changed a related comment to say that we call unpack_pointer. I've also adjusted the header comment on value_as_address. The existing header refers to some code that is now commented out. Rather than trying to describe the whole algorithm of value_as_address, which is already well commented within the function, I've just trimmed the comment on value_as_address to be a brief summary of what the function does. There should be no user visible changes after this commit. Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: remove Py_TPFLAGS_BASETYPE from gdb.UnwindInfoAndrew Burgess2-1/+18
It is not currently possible to directly create gdb.UnwindInfo instances, they need to be created by calling gdb.PendingFrame.create_unwind_info so that the newly created UnwindInfo can be linked to the pending frame. As such there's no tp_init method defined for UnwindInfo. A consequence of all this is that it doesn't really make sense to allow sub-classing of gdb.UnwindInfo. Any sub-class can't call the parents __init__ method to correctly link up the PendingFrame object (there is no parent __init__ method). And any instances that sub-classes UnwindInfo but doesn't call the parent __init__ is going to be invalid for use in GDB. This commit removes the Py_TPFLAGS_BASETYPE flag from the UnwindInfo class, which prevents the class being sub-classed. Then I've added a test to check that this is indeed prevented. Any functional user code will not have any issues with this change. Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: add __repr__ for PendingFrame and UnwindInfoAndrew Burgess3-3/+99
Having a useful __repr__ method can make debugging Python code that little bit easier. This commit adds __repr__ for gdb.PendingFrame and gdb.UnwindInfo classes, along with some tests. Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: add some additional methods to gdb.PendingFrameAndrew Burgess5-1/+417
The gdb.Frame class has far more methods than gdb.PendingFrame. Given that a PendingFrame hasn't yet been claimed by an unwinder, there is a limit to which methods we can add to it, but many of the methods that the Frame class has, the PendingFrame class could also support. In this commit I've added those methods to PendingFrame that I believe are safe. In terms of implementation: if I was starting from scratch then I would implement many of these (or most of these) as attributes rather than methods. However, given both Frame and PendingFrame are just different representation of a frame, I think there is value in keeping the interface for the two classes the same. For this reason everything here is a method -- that's what the Frame class does. The new methods I've added are: - gdb.PendingFrame.is_valid: Return True if the pending frame object is valid. - gdb.PendingFrame.name: Return the name for the frame's function, or None. - gdb.PendingFrame.pc: Return the $pc register value for this frame. - gdb.PendingFrame.language: Return a string containing the language for this frame, or None. - gdb.PendingFrame.find_sal: Return a gdb.Symtab_and_line object for the current location within the pending frame, or None. - gdb.PendingFrame.block: Return a gdb.Block for the current pending frame, or None. - gdb.PendingFrame.function: Return a gdb.Symbol for the current pending frame, or None. In every case I've just copied the implementation over from gdb.Frame and cleaned the code slightly e.g. NULL to nullptr. Additionally each function required a small update to reflect the PendingFrame type, but that's pretty minor. There are tests for all the new methods. For more extensive testing, I added the following code to the file gdb/python/lib/command/unwinders.py: from gdb.unwinder import Unwinder class TestUnwinder(Unwinder): def __init__(self): super().__init__("XXX_TestUnwinder_XXX") def __call__(self,pending_frame): lang = pending_frame.language() try: block = pending_frame.block() assert isinstance(block, gdb.Block) except RuntimeError as rte: assert str(rte) == "Cannot locate block for frame." function = pending_frame.function() arch = pending_frame.architecture() assert arch is None or isinstance(arch, gdb.Architecture) name = pending_frame.name() assert name is None or isinstance(name, str) valid = pending_frame.is_valid() pc = pending_frame.pc() sal = pending_frame.find_sal() assert sal is None or isinstance(sal, gdb.Symtab_and_line) return None gdb.unwinder.register_unwinder(None, TestUnwinder()) This registers a global unwinder that calls each of the new PendingFrame methods and checks the result is of an acceptable type. The unwinder never claims any frames though, so shouldn't change how GDB actually behaves. I then ran the testsuite. There was only a single regression, a test that uses 'disable unwinder' and expects a single unwinder to be disabled -- the extra unwinder is now disabled too, which changes the test output. So I'm reasonably confident that the new methods are not going to crash GDB. Reviewed-By: Eli Zaretskii <eliz@gnu.org> Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: add PENDING_FRAMEPY_REQUIRE_VALID macro in py-unwind.cAndrew Burgess3-26/+53
This commit copies the pattern that is present in many other py-*.c files: having a single macro to check that the Python object is still valid. This cleans up the code a little throughout the py-unwind.c file. Some of the exception messages will change slightly with this commit, though the type of the exceptions is still ValueError in all cases. I started writing some tests for this change and immediately ran into a problem: GDB would crash. It turns out that the PendingFrame objects are not being marked as invalid! In pyuw_sniffer where the pending frames are created, we make use of a scoped_restore to invalidate the pending frame objects. However, this only restores the pending_frame_object::frame_info field to its previous value -- and it turns out we never actually give this field an initial value, it's left undefined. So, when the scoped_restore (called invalidate_frame) performs its cleanup, it actually restores the frame_info field to an undefined value. If this undefined value is not nullptr then any future accesses to the PendingFrame object result in undefined behaviour and most likely, a crash. As part of this commit I now initialize the frame_info field, which ensures all the new tests now pass. Reviewed-By: Tom Tromey <tom@tromey.com>
2023-03-30gdb/python: remove unneeded nullptr check in frapy_blockAndrew Burgess1-7/+1
Spotted a redundant nullptr check in python/py-frame.c in the function frapy_block. This was introduced in commit 57126e4a45e3000e when we expanded an earlier check in return early if the pointer in question is nullptr. There should be no user visible changes after this commit. Reviewed-By: Tom Tromey <tom@tromey.com>