summaryrefslogtreecommitdiff
path: root/lldb/test/API/python_api
AgeCommit message (Collapse)Author
2024-05-28Add SBAddressRange and SBAddressRangeList to SB API (#92014)Miro Bucko
This adds new SB API calls and classes to allow a user of the SB API to obtain an address ranges from SBFunction and SBBlock.
2024-05-24[lldb] Fixed the TestDebuggerAPI test on x86_64 Windows host (#90580)Dmitry Vasilyev
Disable the TestDebuggerAPI test in case of the remote target and Windows host.
2024-05-20SBDebugger: Add new APIs `AddDestroyCallback` and `RemoveDestroyCallback` ↵royitaqi
(#89868) # Motivation Individual callers of `SBDebugger::SetDestroyCallback()` might think that they have registered their callback and expect it to be called when the debugger is destroyed. In reality, only the last caller survives, and all previous callers are forgotten, which might be a surprise to them. Worse, if this is called in a race condition, which callback survives is less predictable, which may case confusing behavior elsewhere. # This PR Allows multiple destroy callbacks to be registered and all called when the debugger is destroyed. **EDIT**: Adds two new APIs: `AddDestroyCallback()` and `ClearDestroyCallback()`. `SetDestroyCallback()` will first clear then add the given callback. Tests are added for the new APIs. ## Tests ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/debugger/TestDebuggerAPI.py ``` ## (out-dated, see comments below) Semantic change to `SetDestroyCallback()` ~~Currently, the method overwrites the old callback with the new one. With this PR, it will NOT overwrite. Instead, it will hold on to both. Both callbacks get called during destroy.~~ ~~**Risk**: Although the documentation of `SetDestroyCallback()` (see [C++](https://lldb.llvm.org/cpp_reference/classlldb_1_1SBDebugger.html#afa1649d9453a376b5c95888b5a0cb4ec) and [python](https://lldb.llvm.org/python_api/lldb.SBDebugger.html#lldb.SBDebugger.SetDestroyCallback)) doesn't really specify the behavior, there is a risk: if existing call sites rely on the "overwrite" behavior, they will be surprised because now the old callback will get called. But as the above said, the current behavior of "overwrite" itself might be unintended, so I don't anticipate users to rely on this behavior. In short, this risk might be less of a problem if we correct it sooner rather than later (which is what this PR is trying to do).~~ ## (out-dated, see comments below) Implementation ~~The implementation holds a `std::vector<std::pair<callback, baton>>`. When `SetDestroyCallback()` is called, callbacks and batons are appended to the `std::vector`. When destroy event happen, the `(callback, baton)` pairs are invoked FIFO. Finally, the `std::vector` is cleared.~~ # (out-dated, see comments below) Alternatives considered ~~Instead of changing `SetDestroyCallback()`, a new method `AddDestroyCallback()` can be added, which use the same `std::vector<std::pair<>>` implementation. Together with `ClearDestroyCallback()` (see below), they will replace and deprecate `SetDestroyCallback()`. Meanwhile, in order to be backward compatible, `SetDestroyCallback()` need to be updated to clear the `std::vector` and then add the new callback. Pros: The end state is semantically more correct. Cons: More steps to take; potentially maintaining an "incorrect" behavior (of "overwrite").~~ ~~A new method `ClearDestroyCallback()` can be added. Might be unnecessary at this point, because workflows which need to set then clear callbacks may exist but shouldn't be too common at least for now. Such method can be added later when needed.~~ ~~The `std::vector` may bring slight performance drawback if its implementation doesn't handle small size efficiently. However, even if that's the case, this path should be very cold (only used during init and destroy). Such performance drawback should be negligible.~~ ~~A different implementation was also considered. Instead of using `std::vector`, the current `m_destroy_callback` field can be kept unchanged. When `SetDestroyCallback()` is called, a lambda function can be stored into `m_destroy_callback`. This lambda function will first call the old callback, then the new one. This way, `std::vector` is avoided. However, this implementation is more complex, thus less readable, with not much perf to gain.~~ --------- Co-authored-by: Roy Shi <royshi@meta.com>
2024-05-20Add new Python API `SBCommandInterpreter::GetTranscript()` (#90703)royitaqi
# Motivation Currently, the user can already get the "transcript" (for "what is the transcript", see `CommandInterpreter::SaveTranscript`). However, the only way to obtain the transcript data as a user is to first destroy the debugger, then read the save directory. Note that destroy-callbacks cannot be used, because 1\ transcript data is private to the command interpreter (see `CommandInterpreter.h`), and 2\ the writing of the transcript is *after* the invocation of destory-callbacks (see `Debugger::Destroy`). So basically, there is no way to obtain the transcript: * during the lifetime of a debugger (including the destroy-callbacks, which often performs logging tasks, where the transcript can be useful) * without relying on external storage In theory, there are other ways for user to obtain transcript data during a debugger's life cycle: * Use Python API and intercept commands and results. * Use CLI and record console input/output. However, such ways rely on the client's setup and are not supported natively by LLDB. # Proposal Add a new Python API `SBCommandInterpreter::GetTranscript()`. Goals: * It can be called at any time during the debugger's life cycle, including in destroy-callbacks. * It returns data in-memory. Structured data: * To make data processing easier, the return type is `SBStructuredData`. See comments in code for how the data is organized. * In the future, `SaveTranscript` can be updated to write different formats using such data (e.g. JSON). This is probably accompanied by a new setting (e.g. `interpreter.save-session-format`). # Alternatives The return type can also be `std::vector<std::pair<std::string, SBCommandReturnObject>>`. This will make implementation easier, without having to translate it to `SBStructuredData`. On the other hand, `SBStructuredData` can convert to JSON easily, so it's more convenient for user to process. # Privacy Both user commands and output/error in the transcript can contain privacy data. However, as mentioned, the transcript is already available to the user. The addition of the new API doesn't increase the level of risk. In fact, it _lowers_ the risk of privacy data being leaked later on, by avoiding writing such data to external storage. Once the user (or their code) gets the transcript, it will be their responsibility to make sure that any required privacy policies are guaranteed. # Tests ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/python_api/interpreter/TestCommandInterpreterAPI.py ``` ``` bin/llvm-lit -sv ../external/llvm-project/lldb/test/API/commands/session/save/TestSessionSave.py ``` --------- Co-authored-by: Roy Shi <royshi@meta.com> Co-authored-by: Med Ismail Bennani <ismail@bennani.ma>
2024-05-10[lldb] Improve type name parsing (#91586)Pavel Labath
Parsing of '::' scopes in TypeQuery was very naive and failed for names with '::''s in template arguments. Interestingly, one of the functions it was calling (Type::GetTypeScopeAndBasename) was already doing the same thing, and getting it (mostly (*)) right. This refactors the function so that it can return the scope results, fixing the parsing of names like std::vector<int, std::allocator<int>>::iterator. Two callers of GetTypeScopeAndBasename are deleted as the functions are not used (I presume they stopped being used once we started pruning type search results more eagerly). (*) This implementation is still not correct when one takes c++ operators into account -- e.g., something like `X<&A::operator<>::T` is a legitimate type name. We do have an implementation that is able to handle names like these (CPlusPlusLanguage::MethodName), but using it is not trivial, because it is hidden in a language plugin and specific to method name parsing. --------- Co-authored-by: Michael Buch <michaelbuch12@gmail.com>
2024-05-09[lldb] Make SBType::GetDirectNestedType (mostly) work with typedefs (#91189)Pavel Labath
The implementation is straight-forward, but comes with a big disclaimer. See #91186 for details.
2024-05-06[lldb] Add SBType::GetByteAlign (#90960)Pavel Labath
lldb already mostly(*) tracks this information. This just makes it available to the SB users. (*) It does not do that for typedefs right now see llvm.org/pr90958
2024-05-03[lldb] Fix Scalar::GetData for non-multiple-of-8-bits values (#90846)Pavel Labath
It was aligning the byte size down. Now it aligns up. This manifested itself as SBTypeStaticField::GetConstantValue returning a zero-sized value for `bool` fields (because clang represents bool as a 1-bit value). I've changed the code for float Scalars as well, although I'm not aware of floating point values that are not multiples of 8 bits.
2024-04-25[lldb] Add SB API to access static constexpr member values (#89730)Pavel Labath
The main change is the addition of a new SBTypeStaticField class, representing a static member of a class. It can be retrieved created through SBType::GetStaticFieldWithName. It contains several methods (GetName, GetMangledName, etc.) whose meaning is hopefully obvious. The most interesting method is lldb::SBValue GetConstantValue(lldb::SBTarget) which returns a the value of the field -- if it is a compile time constant. The reason for that is that only constants have their values represented in the clang AST. For non-constants, we need to go back to the module containing that constant, and ask retrieve the associated ValueObjectVariable. That's easy enough if the we are still in the type system of the module (because then the type system will contain the pointer to the module symbol file), but it's hard when the type has been copied into another AST (e.g. during expression evaluation). To do that we would need to walk the ast import chain backwards to find the source TypeSystem, and I haven't found a nice way to do that. Another possibility would be to use the mangled name of the variable to perform a lookup (in all modules). That is sort of what happens when evaluating the variable in an expression (which does work), but I did not want to commit to that implementation as it's not necessary for my use case (and if anyone wants to, he can use the GetMangledName function and perform the lookup manually). The patch adds a couple of new TypeSystem functions to surface the information needed to implement this functionality.
2024-04-23[lldb/test] Rename a functionPavel Labath
I misunderstood what is the function looking up
2024-04-19[lldb] Make SBType::FindDirectNestedType work with expression ASTs (#89183)Pavel Labath
The types we get out of expressions will not have an associated symbol file, so the current method of looking up the type will fail. Instead, I plumb the query through the TypeSystem class. This correctly finds the type in both cases (importing it into the expression AST if needed). I haven't measured, but it should also be more efficient than doing a type lookup (at least, after the type has already been found once).
2024-04-12Reapply "Fix error in unrecognized register name handling for ↵jimingham
"SBFram…e.register"" (#88468)" (#88535) The only change is a fix for the "register" iterator test to not rely on particular register names. I mistook where the artificial "pc" register is generated. It isn't added to the register list or the register sets (except on arm where that's the name of the actual register), so I can't use it in this test. I instead just assert that the "register" generator produces the same list as flattening the register sets from "registers". This reverts commit 9f14914753599f3879e4c273191959e2f1b3632c.
2024-04-11Revert "Fix error in unrecognized register name handling for ↵Chelsea Cassanova
"SBFrame.register"" (#88468) Reverts llvm/llvm-project#88047. TestFrames.py is failing on x86_64 GreenDragon: https://green.lab.llvm.org/job/llvm.org/view/LLDB/job/lldb-cmake/983/
2024-04-11Fix error in unrecognized register name handling for "SBFrame.register" (#88047)jimingham
The code returned lldb.SBValue() when you passed in an unrecognized register name. But referring to "lldb" is apparently not legal within the module. I changed this to just return SBValue(), but then this construct: (lldb) script >>> for reg_set in lldb.target.process.thread[0].frames[0].register ... print(reg) Runs forever printing "No Value". The __getitem__(key) gets called with a monotonically increasing by 1 series of integers. I don't know why Python decided the class we defined should have a generator that returns positive integers in order, but we can add a more useful one here by returning an iterator over the flattened list of registers. Note, the not very aptly named "SBFrame.registers" is an iterator over register sets, not registers, so the two are not redundant.
2024-03-13[lldb][test] Disable other runlocker test on AArch64 LinuxDavid Spickett
Flaky on the bot: https://lab.llvm.org/buildbot/#/builders/96/builds/54435
2024-03-11Make ValueObject::Cast work for casts from smaller to larger structs in the ↵jimingham
cases where this currently can work. (#84588) The ValueObjectConstResult classes that back expression result variables play a complicated game with where the data for their values is stored. They try to make it appear as though they are still tied to the memory in the target into which their value was written when the expression is run, but they also keep a copy in the Host which they use after the value is made (expression results are "history values" so that's how we make sure they have "the value at the time of the expression".) However, that means that if you ask them to cast themselves to a value bigger than their original size, they don't have a way to get more memory for that purpose. The same thing is true of ValueObjects backed by DataExtractors, the data extractors don't know how to get more data than they were made with in general. The only place where we actually ask ValueObjects to sample outside their captured bounds is when you do ValueObject::Cast from one structure type to a bigger structure type. In https://reviews.llvm.org/D153657 I handled this by just disallowing casts from one structure value to a larger one. My reasoning at the time was that the use case for this was to support discriminator based C inheritance schemes, and you can't directly cast values in C, only pointers, so this was not a natural way to handle those types. It seemed logical that since you would have had to start with pointers in the implementation, that's how you would write your lldb introspection code as well. Famous last words... Turns out there are some heavy users of the SB API's who were relying on this working, and this is a behavior change, so this patch makes this work in the cases where it used to work before, while still disallowing the cases we don't know how to support. Note that if you had done this Cast operation before with either expression results or value objects from data extractors, lldb would not have returned the correct results, so the cases this patch outlaws are ones that actually produce invalid results. So nobody should be using Cast in these cases, or if they were, this patch will point out the bug they hadn't yet noticed.
2024-03-06Skip TestAddressMasks API tests on 32-bit armJason Molenda
TestAddressMasks failed on the lldb-arm-buntu bot with the Code address mask test, mask = process.GetAddressMask(lldb.eAddressMaskTypeAny) process.SetAddressMask(lldb.eAddressMaskTypeCode, mask | 0x3) self.assertEqual( 0x000002950001F694, process.FixAddress(0x00265E950001F697, lldb.eAddressMaskTypeCode), ) The API returned 0x000002950001f694 instead of the expected 0x00265e950001f696. The low bits differ because ABISysV_arm hardcodes the Code address mask to clear the 0th bit, it doesn't use the Process code mask. I didn't debug why some of the high bytes were dropped. The address mask APIs are only important on 64-bit targets, where many of the bits are not used for addressing and are used for metadata instead, so I'm going to skip these tests on 32-bit arm instead of debugging.
2024-03-06[lldb] Address mask sbprocess apis and new mask invalid const (#83663)Jason Molenda
[lldb] Add SBProcess methods for get/set/use address masks (#83095) I'm reviving a patch from phabracator, https://reviews.llvm.org/D155905 which was approved but I wasn't thrilled with all the API I was adding to SBProcess for all of the address mask types / memory regions. In this update, I added enums to control type address mask type (code, data, any) and address space specifiers (low, high, all) with defaulted arguments for the most common case. I originally landed this via https://github.com/llvm/llvm-project/pull/83095 but it failed on CIs outside of arm64 Darwin so I had to debug it on more environments and update the patch. This patch is also fixing a bug in the "addressable bits to address mask" calculation I added in AddressableBits::SetProcessMasks. If lldb were told that 64 bits are valid for addressing, this method would overflow the calculation and set an invalid mask. Added tests to check this specific bug while I was adding these APIs. This patch changes the value of "no mask set" from 0 to LLDB_INVALID_ADDRESS_MASK, which is UINT64_MAX. A mask of all 1's means "no bits are used for addressing" which is an impossible mask, whereas a mask of 0 means "all bits are used for addressing" which is possible. I added a base class implementation of ABI::FixCodeAddress and ABI::FixDataAddress that will apply the Process mask values if they are set to a value other than LLDB_INVALID_ADDRESS_MASK. I updated all the callers/users of the Mask methods which were handling a value of 0 to mean invalid mask to use LLDB_INVALID_ADDRESS_MASK. I added code to the all AArch64 ABI Fix* methods to apply the Highmem masks if they have been set. These will not be set on a Linux environment, but in TestAddressMasks.py I test the highmem masks feature for any AArch64 target, so all AArch64 ABI plugins must handle it. rdar://123530562
2024-02-29Revert "[lldb] Add SBProcess methods for get/set/use address masks (#83095)"Jason Molenda
This reverts commit 9a12b0a60084b2b92f728e1bddec884a47458459. TestAddressMasks fails its first test on lldb-x86_64-debian, lldb-arm-ubuntu, lldb-aarch64-ubuntu bots. Reverting while investigating.
2024-02-29[lldb] Add SBProcess methods for get/set/use address masks (#83095)Jason Molenda
I'm reviving a patch from phabracator, https://reviews.llvm.org/D155905 which was approved but I wasn't thrilled with all the API I was adding to SBProcess for all of the address mask types / memory regions. In this update, I added enums to control type address mask type (code, data, any) and address space specifiers (low, high, all) with defaulted arguments for the most common case. This patch is also fixing a bug in the "addressable bits to address mask" calculation I added in AddressableBits::SetProcessMasks. If lldb were told that 64 bits are valid for addressing, this method would overflow the calculation and set an invalid mask. Added tests to check this specific bug while I was adding these APIs. rdar://123530562
2024-02-21[lldb][test] Modernize assertEqual(value, bool) (#82526)Jordan Rupprecht
Any time we see the pattern `assertEqual(value, bool)`, we can replace that with `assert<bool>(value)`. Likewise for `assertNotEqual`. Technically this relaxes the test a bit, as we may want to make sure `value` is either `True` or `False`, and not something that implicitly converts to a bool. For example, `assertEqual("foo", True)` will fail, but `assertTrue("foo")` will not. In most cases, this distinction is not important. There are two such places that this patch does **not** transform, since it seems intentional that we want the result to be a bool: * https://github.com/llvm/llvm-project/blob/5daf2001a1e4d71ce1273a1e7e31cf6e6ac37c10/lldb/test/API/python_api/sbstructureddata/TestStructuredDataAPI.py#L90 * https://github.com/llvm/llvm-project/blob/5daf2001a1e4d71ce1273a1e7e31cf6e6ac37c10/lldb/test/API/commands/settings/TestSettings.py#L940 Followup to 9c2468821ec51defd09c246fea4a47886fff8c01. I patched `teyit` with a `visit_assertEqual` node handler to generate this.
2024-02-21Bump the minimum LLVM version for TestTypeList.pyShubham Sandeep Rastogi
2024-02-21[lldb][test] Modernize asserts (#82503)Jordan Rupprecht
This uses [teyit](https://pypi.org/project/teyit/) to modernize asserts, as recommended by the [unittest release notes](https://docs.python.org/3.12/whatsnew/3.12.html#id3). For example, `assertTrue(a == b)` is replaced with `assertEqual(a, b)`. This produces better error messages, e.g. `error: unexpectedly found 1 and 2 to be different` instead of `error: False`.
2024-02-16[lldb] Replace assertEquals with assertEqual (NFC) (#82073)Jonas Devlieghere
assertEquals is a deprecated alias for assertEqual and has been removed in Python 3.12. This wasn't an issue previously because we used a vendored version of the unittest module. Now that we use the built-in version this gets updated together with the Python version used to run the test suite.
2024-02-16Re-land "[lldb] Fix `FindDirectNestedType` not working with class templates ↵Vlad Serebrennikov
(#81666)" This patch attempts to fix lookup in class template specialization. The first fixed problem is that during type lookup `DeclContextGetName` have been dropping template arguments. So when such a name was compared against a name in `DW_AT_name`, which contains template arguments, false mismatches have been occurring. The second fixed problem is that LLDB's printing policy hasn't been matching Clang's printing policy when it comes to integral non-type template arguments. This again caused some false mismatches during type lookup, because Clang puts e.g. `3U` in debug info for class specializations, but LLDB has been expecting just `3`. This patch brings printing policy in line with what Clang does.
2024-02-16Revert "[lldb] Fix `FindDirectNestedType` not working with class templates ↵Shubham Sandeep Rastogi
(#81666)" This reverts commit 7b7d411de9f731d2bcf6b093f6cee2cf57a5196e.
2024-02-16[lldb] Fix `FindDirectNestedType` not working with class templates (#81666)Vlad Serebrennikov
This patch attempts to fix lookup in class template specialization. The first fixed problem is that during type lookup `DeclContextGetName` have been dropping template arguments. So when such a name was compared against a name in `DW_AT_name`, which contains template arguments, false mismatches have been occurring. The second fixed problem is that LLDB's printing policy hasn't been matching Clang's printing policy when it comes to integral non-type template arguments. This again caused some false mismatches during type lookup, because Clang puts e.g. `3U` in debug info for class specializations, but LLDB has been expecting just `3`. This patch brings printing policy in line with what Clang does.
2024-02-15[lldb] Fix Python test formatting (NFC)Jonas Devlieghere
2024-02-06[lldb] Fix a crasher when using the public API. (#80508)Greg Clayton
A user found a crash when they would do code like: ``` (lldb) script >>> target = lldb.SBTarget() >>> lldb.debugger.SetSelectedTarget(target) ``` We were not checking if the target was valid in and it caused a crash..
2024-01-03[lldb][test] Skip other Global Module Cache tests on Arm/AArch64 LinuxDavid Spickett
These are expected to fail but sometimes crash during the test leaving them as unresolved. Same failure message and likely same cause as the other test in this file.
2023-12-21[LLDB] Fix write permission error in TestGlobalModuleCache.py (#76171)cmtice
TestGlobalModuleCache.py, a recently added test, tries to update a source file in the build directory, but it assumes the file is writable. In our distributed build and test system, this is not always true, so the test often fails with a write permissions error. This change fixes that by setting the permissions on the file to be writable before attempting to write to it.
2023-12-20[lldb][test] Skip global module cache on Arm/AArch64 Linux (again)David Spickett
This reverts commit 01c4ecb7ae21a61312ff0c0176c0ab9f8656c159, d14d52158bc444e2d036067305cf54aeea7c9edb and a756dc4724a279d76898bacd054a04832b02caa8. This removes the logging and workaround I added earlier, and puts back the skip for Arm/AArch64 Linux. I've not seen it fail on AArch64 since, but let's not create more noise if it does. I've written up the issue as https://github.com/llvm/llvm-project/issues/76057. It's something to do with trying to destroy a process while a thread is doing a single sep. So my workaround wouldn't have worked in any case. It needs a more involved fix.
2023-12-20[lldb][test] Skip runlocker test on AArch64 LinuxDavid Spickett
This has been flaky for a while, for example https://lab.llvm.org/buildbot/#/builders/96/builds/50350 ``` Command Output (stdout): -- lldb version 18.0.0git (https://github.com/llvm/llvm-project.git revision 3974d89bde66a2ec61261b969b51993da81205c7) clang revision 3974d89bde66a2ec61261b969b51993da81205c7 llvm revision 3974d89bde66a2ec61261b969b51993da81205c7 "can't evaluate expressions when the process is running." ``` ``` PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace. #0 0x0000ffffa46191a0 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x529a1a0) #1 0x0000ffffa4617144 llvm::sys::RunSignalHandlers() (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x5298144) #2 0x0000ffffa46198d0 SignalHandler(int) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x529a8d0) #3 0x0000ffffab25b7dc (linux-vdso.so.1+0x7dc) #4 0x0000ffffab13d050 /build/glibc-Q8DG8B/glibc-2.31/string/../sysdeps/aarch64/multiarch/memcpy_advsimd.S:92:0 #5 0x0000ffffa446f420 lldb_private::process_gdb_remote::GDBRemoteRegisterContext::PrivateSetRegisterValue(unsigned int, llvm::ArrayRef<unsigned char>) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x50f0420) #6 0x0000ffffa446f7b8 lldb_private::process_gdb_remote::GDBRemoteRegisterContext::GetPrimordialRegister(lldb_private::RegisterInfo const*, lldb_private::process_gdb_remote::GDBRemoteCommunicationClient&) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x50f07b8) #7 0x0000ffffa446f308 lldb_private::process_gdb_remote::GDBRemoteRegisterContext::ReadRegisterBytes(lldb_private::RegisterInfo const*) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x50f0308) #8 0x0000ffffa446ec1c lldb_private::process_gdb_remote::GDBRemoteRegisterContext::ReadRegister(lldb_private::RegisterInfo const*, lldb_private::RegisterValue&) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x50efc1c) #9 0x0000ffffa412eaa4 lldb_private::RegisterContext::ReadRegisterAsUnsigned(lldb_private::RegisterInfo const*, unsigned long) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x4dafaa4) #10 0x0000ffffa420861c ReadLinuxProcessAddressMask(std::shared_ptr<lldb_private::Process>, llvm::StringRef) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x4e8961c) #11 0x0000ffffa4208430 ABISysV_arm64::FixCodeAddress(unsigned long) (/home/tcwg-buildbot/worker/lldb-aarch64-ubuntu/build/lib/python3.8/site-packages/lldb/_lldb.cpython-38-aarch64-linux-gnu.so+0x4e89430) ``` Judging by the backtrace something is trying to read the pointer authentication address/code mask registers. This explains why I've not seen this issue locally, as the buildbot runs on Graviton 3 with has the pointer authentication extension. I will try to reproduce, fix and re-enable the test.
2023-12-20[lldb][test] Remove Arm/AArch64 Linux skip for global modules testDavid Spickett
So we can see it failing and get the extra logged information.
2023-12-20[lldb][test] Add extra logging for module cache testDavid Spickett
And remove the workaround I was trying, as this logging may prove what the actual issue is. Which I think is that the thread plan map in Process is cleared before the threads are destroyed. So Thread::ShouldStop could be getting the current plan, then the plan map is cleared, then Thread::ShouldStop is deciding based on that plan to pop a plan from the now empty stack.
2023-12-20[lldb][test] Try a workaround for module cache test on Arm/AArch64 LinuxDavid Spickett
If this works it'll give me a clue for the underlying issue.
2023-12-19[lldb] Fix TestSBValueSynthetic on windows (#75908)Pavel Labath
We don't have a std::vector formatter on windows, so use a custom formatter in this test to avoid relying on std::vector.
2023-12-18[lldb] Fix a quirk in SBValue::GetDescription (#75793)Pavel Labath
The function was using the default version of ValueObject::Dump, which has a default of using the synthetic-ness of the top-level value for determining whether to print _all_ values as synthetic. This resulted in some unusual behavior, where e.g. a std::vector is stringified as synthetic if its dumped as the top level object, but in its raw form if it is a member of a struct without a pretty printer. The SBValue class already has properties which determine whether one should be looking at the synthetic view of the object (and also whether to use dynamic types), so it seems more natural to use that.
2023-12-14[lldb] Remove PopPlan asserts and skip test on Arm/AArch64 LinuxDavid Spickett
This reverts commit 481bb62e50317cf20df9493aad842790162ac3e7 and 71b4d7498ffecca5957fa0a63b1abf141d7b8441, along with the logging and assert I had added to the test previously. Now that I've caught it failing on Arm: https://lab.llvm.org/buildbot/#/builders/17/builds/46598 Now I have enough to investigate, skip the test on the effected platforms while I do that.
2023-12-14Reland "Add a test for evicting unreachable modules from the global module ↵David Spickett
cache (#74894)" This reverts commit 35dacf2f51af251a74ac98ed29e7c454a619fcf1. And relands the original change with two additions so I can debug the failure on Arm/AArch64: * Enable lldb step logging in the tests. * Assert that the current plan is not the base plan at the spot I believe is calling PopPlan. These will be removed and replaced with a proper fix once I see some failures on the bots, I couldn't reproduce it locally. (also, no sign of it on the x86_64 bot)
2023-12-13Revert "Add a test for evicting unreachable modules from the global module ↵David Spickett
cache (#74894)" This reverts commit 2684281d208612a746b05c891f346bd7b95318d5. Due to being flaky on Arm and AArch64 buildbots.
2023-12-12Add a test for evicting unreachable modules from the global module cache ↵jimingham
(#74894) When you debug a binary and the change & rebuild and then rerun in lldb w/o quitting lldb, the Modules in the Global Module Cache for the old binary & .o files if used are now "unreachable". Nothing in lldb is holding them alive, and they've already been unlinked. lldb will properly discard them if there's not another Target referencing them. However, this only works in simple cases at present. If you have several Targets that reference the same modules, it's pretty easy to end up stranding Modules that are no longer reachable, and if you use a sequence of SBDebuggers unreachable modules can also get stranded. If you run a long-lived lldb process and are iteratively developing on a large code base, lldb's memory gets filled with useless Modules. This patch adds a test for the mode that currently works: (lldb) target create foo (lldb) run <rebuild foo outside lldb> (lldb) run In that case, we do delete the unreachable Modules. The next step will be to add tests for the cases where we fail to do this, then see how to safely/efficiently evict unreachable modules in those cases as well.
2023-11-30[lldb] [mostly NFC] Large WP foundation: WatchpointResources (#68845)Jason Molenda
This patch is rearranging code a bit to add WatchpointResources to Process. A WatchpointResource is meant to represent a hardware watchpoint register in the inferior process. It has an address, a size, a type, and a list of Watchpoints that are using this WatchpointResource. This current patch doesn't add any of the features of WatchpointResources that make them interesting -- a user asking to watch a 24 byte object could watch this with three 8 byte WatchpointResources. Or a Watchpoint on 1 byte at 0x1002 and a second watchpoint on 1 byte at 0x1003, these must both be served by a single WatchpointResource on that doubleword at 0x1000 on a 64-bit target, if two hardware watchpoint registers were used to track these separately, one of them may not be hit. Or if you have one Watchpoint on a variable with a condition set, and another Watchpoint on that same variable with a command defined or different condition, or ignorecount, both of those Watchpoints need to evaluate their criteria/commands when their WatchpointResource has been hit. There's a bit of code movement to rearrange things in the direction I'll need for implementing this feature, so I want to start with reviewing & landing this mostly NFC patch and we can focus on the algorithmic choices about how WatchpointResources are shared and handled as they're triggeed, separately. This patch also stops printing "Watchpoint <n> hit: old value: <x>, new vlaue: <y>" for Read watchpoints. I could make an argument for print "Watchpoint <n> hit: current value <x>" but the current output doesn't make any sense, and the user can print the value if they are particularly interested. Read watchpoints are used primarily to understand what code is reading a variable. This patch adds more fallbacks for how to print the objects being watched if we have types, instead of assuming they are all integral values, so a struct will print its elements. As large watchpoints are added, we'll be doing a lot more of those. To track the WatchpointSP in the WatchpointResources, I changed the internal API which took a WatchpointSP and devolved it to a Watchpoint*, which meant touching several different Process files. I removed the watchpoint code in ProcessKDP which only reported that watchpoints aren't supported, the base class does that already. I haven't yet changed how we receive a watchpoint to identify the WatchpointResource responsible for the trigger, and identify all Watchpoints that are using this Resource to evaluate their conditions etc. This is the same work that a BreakpointSite needs to do when it has been tiggered, where multiple Breakpoints may be at the same address. There is not yet any printing of the Resources that a Watchpoint is implemented in terms of ("watchpoint list", or SBWatchpoint::GetDescription). "watchpoint set var" and "watchpoint set expression" take a size argument which was previously 1, 2, 4, or 8 (an enum). I've changed this to an unsigned int. Most hardware implementations can only watch 1, 2, 4, 8 byte ranges, but with Resources we'll allow a user to ask for different sized watchpoints and set them in hardware-expressble terms soon. I've annotated areas where I know there is work still needed with LWP_TODO that I'll be working on once this is landed. I've tested this on aarch64 macOS, aarch64 Linux, and Intel macOS. https://discourse.llvm.org/t/rfc-large-watchpoint-support-in-lldb/72116 (cherry picked from commit fc6b72523f3d73b921690a713e97a433c96066c6)
2023-11-30Send an explicit interrupt to cancel an attach waitfor. (#72565)jimingham
Currently when you interrupt a: (lldb) process attach -w -n some_process lldb just closes the connection to the stub and kills the lldb_private::Process it made for the attach. The stub at the other end notices the connection go down and exits because of that. But when communication to a device is handled through some kind of proxy server which isn't as well behaved as one would wish, that signal might not be reliable, causing debugserver to persist on the machine, waiting to steal the next instance of that process. We can work around those failures by sending an explicit interrupt before closing down the connection. The stub will also have to be waiting for the interrupt for this to make any difference. I changed debugserver to do that. I didn't make the equivalent change in lldb-server. So long as you aren't faced with a flakey connection, this should not be necessary.
2023-11-28Revert "[lldb] [mostly NFC] Large WP foundation: WatchpointResources (#68845)"David Spickett
...and follow ups. As it has caused test failures on Linux Arm and AArch64: https://lab.llvm.org/buildbot/#/builders/96/builds/49126 https://lab.llvm.org/buildbot/#/builders/17/builds/45824 ``` lldb-shell :: Subprocess/clone-follow-child-wp.test lldb-shell :: Subprocess/fork-follow-child-wp.test lldb-shell :: Subprocess/vfork-follow-child-wp.test ``` This reverts commit a6c62bf1a4717accc852463b664cd1012237d334, commit a0a1ff3ab40e347589b4e27d8fd350c600526735 and commit fc6b72523f3d73b921690a713e97a433c96066c6.
2023-11-27[lldb] [mostly NFC] Large WP foundation: WatchpointResources (#68845)Jason Molenda
This patch is rearranging code a bit to add WatchpointResources to Process. A WatchpointResource is meant to represent a hardware watchpoint register in the inferior process. It has an address, a size, a type, and a list of Watchpoints that are using this WatchpointResource. This current patch doesn't add any of the features of WatchpointResources that make them interesting -- a user asking to watch a 24 byte object could watch this with three 8 byte WatchpointResources. Or a Watchpoint on 1 byte at 0x1002 and a second watchpoint on 1 byte at 0x1003, these must both be served by a single WatchpointResource on that doubleword at 0x1000 on a 64-bit target, if two hardware watchpoint registers were used to track these separately, one of them may not be hit. Or if you have one Watchpoint on a variable with a condition set, and another Watchpoint on that same variable with a command defined or different condition, or ignorecount, both of those Watchpoints need to evaluate their criteria/commands when their WatchpointResource has been hit. There's a bit of code movement to rearrange things in the direction I'll need for implementing this feature, so I want to start with reviewing & landing this mostly NFC patch and we can focus on the algorithmic choices about how WatchpointResources are shared and handled as they're triggeed, separately. This patch also stops printing "Watchpoint <n> hit: old value: <x>, new vlaue: <y>" for Read watchpoints. I could make an argument for print "Watchpoint <n> hit: current value <x>" but the current output doesn't make any sense, and the user can print the value if they are particularly interested. Read watchpoints are used primarily to understand what code is reading a variable. This patch adds more fallbacks for how to print the objects being watched if we have types, instead of assuming they are all integral values, so a struct will print its elements. As large watchpoints are added, we'll be doing a lot more of those. To track the WatchpointSP in the WatchpointResources, I changed the internal API which took a WatchpointSP and devolved it to a Watchpoint*, which meant touching several different Process files. I removed the watchpoint code in ProcessKDP which only reported that watchpoints aren't supported, the base class does that already. I haven't yet changed how we receive a watchpoint to identify the WatchpointResource responsible for the trigger, and identify all Watchpoints that are using this Resource to evaluate their conditions etc. This is the same work that a BreakpointSite needs to do when it has been tiggered, where multiple Breakpoints may be at the same address. There is not yet any printing of the Resources that a Watchpoint is implemented in terms of ("watchpoint list", or SBWatchpoint::GetDescription). "watchpoint set var" and "watchpoint set expression" take a size argument which was previously 1, 2, 4, or 8 (an enum). I've changed this to an unsigned int. Most hardware implementations can only watch 1, 2, 4, 8 byte ranges, but with Resources we'll allow a user to ask for different sized watchpoints and set them in hardware-expressble terms soon. I've annotated areas where I know there is work still needed with LWP_TODO that I'll be working on once this is landed. I've tested this on aarch64 macOS, aarch64 Linux, and Intel macOS. https://discourse.llvm.org/t/rfc-large-watchpoint-support-in-lldb/72116
2023-11-15Remove hardware index from watchpoints and breakpoints (#72012)Jason Molenda
The Watchpoint and Breakpoint objects try to track the hardware index that was used for them, if they are hardware wp/bp's. The majority of our debugging goes over the gdb remote serial protocol, and when we set the watchpoint/breakpoint, there is no (standard) way for the remote stub to communicate to lldb which hardware index was used. We have an lldb-extension packet to query the total number of watchpoint registers. When a watchpoint is hit, there is an lldb extension to the stop reply packet (documented in lldb-gdb-remote.txt) to describe the watchpoint including its actual hardware index, <addr within wp range> <wp hw index> <actual accessed address> (the third field is specifically needed for MIPS). At this point, if the stub reported these three fields (the stub is only required to provide the first), we can know the actual hardware index for this watchpoint. Breakpoints are worse; there's never any way for us to be notified about which hardware index was used. Breakpoints got this as a side effect of inherting from StoppointSite with Watchpoints. We expose the watchpoint hardware index through "watchpoint list -v" and through SBWatchpoint::GetHardwareIndex. With my large watchpoint support, there is no *single* hardware index that may be used for a watchpoint, it may need multiple resources. Also I don't see what a user is supposed to do with this information, or an IDE. Knowing the total number of watchpoint registers on the target, and knowing how many Watchpoint Resources are currently in use, is helpful. Knowing how many Watchpoint Resources a single user-specified watchpoint needed to be implemented is useful. But knowing which registers were used is an implementation detail and not available until we hit the watchpoint when using gdb remote serial protocol. So given all that, I'm removing watchpoint hardware index numbers. I'm changing the SB API to always return -1.
2023-11-13[lldb-dap] Add an option to provide a format for stack frames (#71843)Walter Erquinigo
When this option gets enabled, descriptions of stack frames will be generated using the format provided in the launch configuration instead of simply calling `SBFrame::GetDisplayFunctionName`. This allows lldb-dap to show an output similar to the one in the CLI.
2023-10-14[lldb] Add SBType::FindDirectNestedType() function (#68705)Vlad Serebrennikov
This patch adds a `SBType::FindDirectNestedType(name)` function which performs a non-recursive search in given class for a type with specified name. The intent is to perform a fast search in debug info, so that it can be used in formatters, and let them remain responsive. This is driven by my work on formatters for Clang and LLVM types. In particular, by [`PointerIntPairInfo::MaskAndShiftConstants`](https://github.com/llvm/llvm-project/blob/cde9f9df79805a0850310870d6dcc64004292727/llvm/include/llvm/ADT/PointerIntPair.h#L174C16-L174C16), which is required to extract pointer and integer from `PointerIntPair`. Related Discourse thread: https://discourse.llvm.org/t/traversing-member-types-of-a-type/72452
2023-09-21Reland "[lldb] Add 'modify' type watchpoints, make it default (#66308)"David Spickett
This reverts commit a7b78cac9a77e3ef6bbbd8ab1a559891dc693401. With updates to the tests. TestWatchTaggedAddress.py: Updated the expected watchpoint types, though I'm not sure there should be a differnt default for the two ways of setting them, that needs to be confirmed. TestStepOverWatchpoint.py: Skipped this everywhere because I think what used to happen is you couldn't put 2 watchpoints on the same address (after alignment). I guess that this is now allowed because modify watchpoints aren't accounted for, but likely should be. Needs investigating.