[Lldb-commits] [lldb] [lldb] Handle an empty SBMemoryRegionInfo from scripted process (PR #115963)

2024-11-15 Thread LLVM Continuous Integration via lldb-commits

llvm-ci wrote:

LLVM Buildbot has detected a new failure on builder `lldb-arm-ubuntu` running 
on `linaro-lldb-arm-ubuntu` while building `lldb` at step 6 "test".

Full details are available at: 
https://lab.llvm.org/buildbot/#/builders/18/builds/7002


Here is the relevant piece of the build log for the reference

```
Step 6 (test) failure: build (failure)
...
UNSUPPORTED: lldb-api :: 
functionalities/ptrauth_diagnostics/LDRAA_error/TestPtrauthLDRAADiagnostic.py 
(561 of 2829)
UNSUPPORTED: lldb-api :: 
functionalities/ptrauth_diagnostics/brkC47x_code/TestPtrauthBRKc47xDiagnostic.py
 (562 of 2829)
UNSUPPORTED: lldb-api :: 
functionalities/ptrauth_diagnostics/brkC47x_x16_invalid/TestPtrauthBRKc47xX16Invalid.py
 (563 of 2829)
PASS: lldb-api :: functionalities/rerun/TestRerun.py (564 of 2829)
PASS: lldb-api :: functionalities/rerun_and_expr/TestRerunAndExpr.py (565 of 
2829)
UNSUPPORTED: lldb-api :: 
functionalities/rerun_and_expr_dylib/TestRerunAndExprDylib.py (566 of 2829)
PASS: lldb-api :: functionalities/scripted_process/TestScriptedProcess.py (567 
of 2829)
UNSUPPORTED: lldb-api :: 
functionalities/scripted_process/TestStackCoreScriptedProcess.py (568 of 2829)
PASS: lldb-api :: functionalities/return-value/TestReturnValue.py (569 of 2829)
UNSUPPORTED: lldb-api :: functionalities/set-data/TestSetData.py (570 of 2829)
FAIL: lldb-api :: 
functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
 (571 of 2829)
 TEST 'lldb-api :: 
functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py'
 FAILED 
Script:
--
/usr/bin/python3.10 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/llvm-project/lldb/test/API/dotest.py 
-u CXXFLAGS -u CFLAGS --env 
LLVM_LIBS_DIR=/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./lib --env 
LLVM_INCLUDE_DIR=/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/include --env 
LLVM_TOOLS_DIR=/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./bin --arch 
armv8l --build-dir 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/lldb-test-build.noindex 
--lldb-module-cache-dir 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/lldb-test-build.noindex/module-cache-lldb/lldb-api
 --clang-module-cache-dir 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/lldb-test-build.noindex/module-cache-clang/lldb-api
 --executable /home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./bin/lldb 
--compiler /home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./bin/clang 
--dsymutil /home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./bin/dsymutil 
--make /usr/bin/make --llvm-tools-dir 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./bin --lldb-obj-root 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/tools/lldb --lldb-libs-dir 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/./lib 
/home/tcwg-buildbot/worker/lldb-arm-ubuntu/llvm-project/lldb/test/API/functionalities/scripted_process_empty_memory_region
 -p TestScriptedProcessEmptyMemoryRegion.py
--
Exit Code: 1

Command Output (stdout):
--
lldb version 20.0.0git (https://github.com/llvm/llvm-project.git revision 
a1a1a4ced9d4ecba428175c45a24da476bdc55f4)
  clang revision a1a1a4ced9d4ecba428175c45a24da476bdc55f4
  llvm revision a1a1a4ced9d4ecba428175c45a24da476bdc55f4
Skipping the following test categories: ['libc++', 'dsym', 'gmodules', 
'debugserver', 'objc']

--
Command Output (stderr):
--
error: failed to launch or debug process
Traceback (most recent call last):
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/llvm-project/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py",
 line 15, in __init__
self.threads[0] = DummyScriptedThread(self, None)
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/llvm-project/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py",
 line 65, in __init__
super().__init__(process, args)
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/local/lib/python3.10/dist-packages/lldb/plugins/scripted_process.py",
 line 273, in __init__
self.get_register_info()
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/local/lib/python3.10/dist-packages/lldb/plugins/scripted_process.py",
 line 364, in get_register_info
raise ValueError("Unknown architecture", self.originating_process.arch)
ValueError: ('Unknown architecture', 'arm')

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/llvm-project/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py",
 line 108, in __lldb_init_module
debugger.HandleCommand(
  File 
"/home/tcwg-buildbot/worker/lldb-arm-ubuntu/build/local/lib/python3.10/dist-packages/lldb/__init__.py",
 line 4878, in HandleCommand
return _lldb.SBDebugger_HandleCommand(self, command)
SystemError:  returned a result 
with an exception set
FAIL: LLDB (/home/tcwg-buildbot/wor

[Lldb-commits] [lldb] [lldb] Handle an empty SBMemoryRegionInfo from scripted process (PR #115963)

2024-11-15 Thread Jason Molenda via lldb-commits


@@ -6184,7 +6184,14 @@ Status Process::GetMemoryRegionInfo(lldb::addr_t 
load_addr,
 MemoryRegionInfo &range_info) {
   if (const lldb::ABISP &abi = GetABI())
 load_addr = abi->FixAnyAddress(load_addr);
-  return DoGetMemoryRegionInfo(load_addr, range_info);
+  Status error = DoGetMemoryRegionInfo(load_addr, range_info);
+  // Reject a region that does not contain the requested address.
+  if (error.Success() && (range_info.GetRange().GetRangeBase() < load_addr ||
+  range_info.GetRange().GetRangeEnd() <= load_addr))

jasonmolenda wrote:

Ah, you did catch a mistake there, thanks.  I was focusing on "lookup of 0, get 
back range start 0x0 size 0" and this check happens to work correctly for that, 
but this should be `(range_info.GetRange().GetRangeBase() < load_addr || 
range_info.GetRange().GetRangeEnd() >= load_addr)`.  `ContainsEndInclusive` 
isn't correct, but the `Contains` method is, good call.

https://github.com/llvm/llvm-project/pull/115963
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX updated 
https://github.com/llvm/llvm-project/pull/116338

>From 0c63800bdcbadcfceed4c9a81305eda7d5a15960 Mon Sep 17 00:00:00 2001
From: Dhruv-Srivastava 
Date: Fri, 15 Nov 2024 02:16:31 -0600
Subject: [PATCH 1/2] Added XCOFF Header Parsing

---
 .../ObjectFile/XCOFF/ObjectFileXCOFF.cpp  | 126 +-
 .../ObjectFile/XCOFF/ObjectFileXCOFF.h|  58 
 2 files changed, 181 insertions(+), 3 deletions(-)

diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..c06ece4347822d 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,92 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ModuleType = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.CpuFlag = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.CpuType = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.TextPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.DataPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.StackPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.FlagAndTDataAlignment = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.TextSize = data.GetU64(offset_p

[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread via lldb-commits

github-actions[bot] wrote:




:warning: C/C++ code formatter, clang-format found issues in your code. 
:warning:



You can test this locally with the following command:


``bash
git-clang-format --diff 5845688e91d85d46c0f47daaf4edfdfc772853cf 
132418ff433eb684b23dcb7d6fa8374b774bb06c --extensions h,cpp -- 
lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.h
``





View the diff from clang-format here.


``diff
diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index b4b1603330..dd1aea9dfc 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -200,7 +200,7 @@ bool 
ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
   xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
   xcoff_header.flags = data.GetU16(offset_ptr);
   xcoff_header.nsyms = data.GetU32(offset_ptr);
-  
+
   return true;
 }
 
@@ -239,11 +239,11 @@ bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
   m_xcoff_aux_header.SecNumOfTData = data.GetU16(offset_ptr);
   m_xcoff_aux_header.SecNumOfTBSS = data.GetU16(offset_ptr);
   m_xcoff_aux_header.XCOFF64Flag = data.GetU16(offset_ptr);
-  
+
   lldb::offset_t last_offset = *offset_ptr;
   if ((last_offset - init_offset) < m_xcoff_header.auxhdrsize)
 *offset_ptr += (m_xcoff_header.auxhdrsize - (last_offset - init_offset));
-  
+
   return true;
 }
 

``




https://github.com/llvm/llvm-project/pull/116338
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] fda4a32 - [lldb] Only run scripted process test on x86_64/arm64

2024-11-15 Thread Jason Molenda via lldb-commits

Author: Jason Molenda
Date: 2024-11-15T00:56:34-08:00
New Revision: fda4a324a384af8dc57cbe0a9b6284c2e8ca073f

URL: 
https://github.com/llvm/llvm-project/commit/fda4a324a384af8dc57cbe0a9b6284c2e8ca073f
DIFF: 
https://github.com/llvm/llvm-project/commit/fda4a324a384af8dc57cbe0a9b6284c2e8ca073f.diff

LOG: [lldb] Only run scripted process test on x86_64/arm64

The newly added
test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
imports
examples/python/templates/scripted_process.py
which only has register definitions for x86_64 and arm64.

Only run this test on those two architectures for now.

Added: 


Modified: 
lldb/examples/python/templates/scripted_process.py

lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py

Removed: 




diff  --git a/lldb/examples/python/templates/scripted_process.py 
b/lldb/examples/python/templates/scripted_process.py
index b7b6499580e50c..c7d5b28b52c00a 100644
--- a/lldb/examples/python/templates/scripted_process.py
+++ b/lldb/examples/python/templates/scripted_process.py
@@ -5,7 +5,6 @@
 
 
 class ScriptedProcess(metaclass=ABCMeta):
-
 """
 The base class for a scripted process.
 
@@ -229,7 +228,6 @@ def create_breakpoint(self, addr, error):
 
 
 class ScriptedThread(metaclass=ABCMeta):
-
 """
 The base class for a scripted thread.
 
@@ -357,7 +355,10 @@ def get_register_info(self):
 if self.originating_process.arch == "x86_64":
 self.register_info["sets"] = ["General Purpose Registers"]
 self.register_info["registers"] = INTEL64_GPR
-elif "arm64" in self.originating_process.arch:
+elif (
+"arm64" in self.originating_process.arch
+or self.originating_process.arch == "aarch64"
+):
 self.register_info["sets"] = ["General Purpose Registers"]
 self.register_info["registers"] = ARM64_GPR
 else:
@@ -411,9 +412,9 @@ def __init__(self, exe_ctx, args, 
launched_driving_process=True):
 )
 )
 
-self.threads[
-driving_thread.GetThreadID()
-] = PassthroughScriptedThread(self, structured_data)
+self.threads[driving_thread.GetThreadID()] = (
+PassthroughScriptedThread(self, structured_data)
+)
 
 for module in self.driving_target.modules:
 path = module.file.fullpath
@@ -507,9 +508,9 @@ def get_stop_reason(self):
 if self.driving_thread.GetStopReason() != lldb.eStopReasonNone:
 if "arm64" in self.originating_process.arch:
 stop_reason["type"] = lldb.eStopReasonException
-stop_reason["data"][
-"desc"
-] = self.driving_thread.GetStopDescription(100)
+stop_reason["data"]["desc"] = (
+self.driving_thread.GetStopDescription(100)
+)
 elif self.originating_process.arch == "x86_64":
 stop_reason["type"] = lldb.eStopReasonSignal
 stop_reason["data"]["signal"] = signal.SIGTRAP

diff  --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
index 1ff084cfb0278e..85d7db59cba1e4 100644
--- 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
@@ -14,6 +14,9 @@
 class ScriptedProcessEmptyMemoryRegion(TestBase):
 NO_DEBUG_INFO_TESTCASE = True
 
+# imports examples/python/templates/scripted_process.py
+# which only has register definitions for x86_64 and arm64.
+@skipIf(archs=no_match(["arm64", "x86_64"]))
 def test_scripted_process_empty_memory_region(self):
 """Test that lldb handles an empty SBMemoryRegionInfo object from
 a scripted process plugin."""



___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Added XCOFF Object File Header Parsing (PR #116337)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX closed 
https://github.com/llvm/llvm-project/pull/116337
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Handle an empty SBMemoryRegionInfo from scripted process (PR #115963)

2024-11-15 Thread Jason Molenda via lldb-commits

https://github.com/jasonmolenda closed 
https://github.com/llvm/llvm-project/pull/115963
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX created 
https://github.com/llvm/llvm-project/pull/116338

This PR is in reference to porting LLDB on AIX.

Link to discussions on llvm discourse and github:

1. https://discourse.llvm.org/t/port-lldb-to-ibm-aix/80640
2. https://github.com/llvm/llvm-project/issues/101657
The complete changes for porting are present in this draft PR:
https://github.com/llvm/llvm-project/pull/102601

Added XCOFF Object File Header Parsing for AIX.
This PR is an incremental PR to the base:
- https://github.com/llvm/llvm-project/pull/111814

Details about XCOFF file format on AIX: 
[XCOFF](https://www.ibm.com/docs/en/aix/7.3?topic=formats-xcoff-object-file-format)

Review Request: @labath @DavidSpickett

>From 0c63800bdcbadcfceed4c9a81305eda7d5a15960 Mon Sep 17 00:00:00 2001
From: Dhruv-Srivastava 
Date: Fri, 15 Nov 2024 02:16:31 -0600
Subject: [PATCH] Added XCOFF Header Parsing

---
 .../ObjectFile/XCOFF/ObjectFileXCOFF.cpp  | 126 +-
 .../ObjectFile/XCOFF/ObjectFileXCOFF.h|  58 
 2 files changed, 181 insertions(+), 3 deletions(-)

diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..c06ece4347822d 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,92 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = da

[Lldb-commits] [lldb] a1a1a4c - [lldb] Handle an empty SBMemoryRegionInfo from scripted process (#115963)

2024-11-15 Thread via lldb-commits

Author: Jason Molenda
Date: 2024-11-15T00:26:10-08:00
New Revision: a1a1a4ced9d4ecba428175c45a24da476bdc55f4

URL: 
https://github.com/llvm/llvm-project/commit/a1a1a4ced9d4ecba428175c45a24da476bdc55f4
DIFF: 
https://github.com/llvm/llvm-project/commit/a1a1a4ced9d4ecba428175c45a24da476bdc55f4.diff

LOG: [lldb] Handle an empty SBMemoryRegionInfo from scripted process (#115963)

A scripted process implementation might return an SBMemoryRegionInfo
object in its implementation of `get_memory_region_containing_address`
which will have an address 0 and size 0, without realizing the problems
this can cause. Several algorithms in lldb will try to iterate over the
MemoryRegions of the process, starting at address 0 and expecting to
iterate up to the highest vm address, stepping by the size of each
region, so a 0-length region will result in an infinite loop. Add a
check to Process::GetMemoryRegionInfo that rejects a MemoryRegion which
does not contain the requested address; a 0-length memory region will
therefor always be rejected.

rdar://139678032

Added: 
lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile

lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py

lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
lldb/test/API/functionalities/scripted_process_empty_memory_region/main.c

Modified: 
lldb/source/Target/Process.cpp

Removed: 




diff  --git a/lldb/source/Target/Process.cpp b/lldb/source/Target/Process.cpp
index b99692b8a0bfd9..9125ceca74a003 100644
--- a/lldb/source/Target/Process.cpp
+++ b/lldb/source/Target/Process.cpp
@@ -6184,7 +6184,12 @@ Status Process::GetMemoryRegionInfo(lldb::addr_t 
load_addr,
 MemoryRegionInfo &range_info) {
   if (const lldb::ABISP &abi = GetABI())
 load_addr = abi->FixAnyAddress(load_addr);
-  return DoGetMemoryRegionInfo(load_addr, range_info);
+  Status error = DoGetMemoryRegionInfo(load_addr, range_info);
+  // Reject a region that does not contain the requested address.
+  if (error.Success() && !range_info.GetRange().Contains(load_addr))
+error = Status::FromErrorString("Invalid memory region");
+
+  return error;
 }
 
 Status Process::GetMemoryRegions(lldb_private::MemoryRegionInfos ®ion_list) 
{

diff  --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile
new file mode 100644
index 00..10495940055b63
--- /dev/null
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile
@@ -0,0 +1,3 @@
+C_SOURCES := main.c
+
+include Makefile.rules

diff  --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
new file mode 100644
index 00..1ff084cfb0278e
--- /dev/null
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
@@ -0,0 +1,33 @@
+"""
+Test python scripted process which returns an empty SBMemoryRegionInfo
+"""
+
+import os, shutil
+
+import lldb
+from lldbsuite.test.decorators import *
+from lldbsuite.test.lldbtest import *
+from lldbsuite.test import lldbutil
+from lldbsuite.test import lldbtest
+
+
+class ScriptedProcessEmptyMemoryRegion(TestBase):
+NO_DEBUG_INFO_TESTCASE = True
+
+def test_scripted_process_empty_memory_region(self):
+"""Test that lldb handles an empty SBMemoryRegionInfo object from
+a scripted process plugin."""
+self.build()
+
+target = self.dbg.CreateTarget(self.getBuildArtifact("a.out"))
+self.assertTrue(target, VALID_TARGET)
+
+scripted_process_example_relpath = "dummy_scripted_process.py"
+self.runCmd(
+"command script import "
++ os.path.join(self.getSourceDir(), 
scripted_process_example_relpath)
+)
+
+self.expect("memory region 0", error=True, substrs=["Invalid memory 
region"])
+
+self.expect("expr -- 5", substrs=["5"])

diff  --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
new file mode 100644
index 00..31e28a57122f66
--- /dev/null
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
@@ -0,0 +1,110 @@
+import os, struct, signal
+
+from typing import Any, Dict
+
+import lldb
+from lldb.plugins.scripted_process import ScriptedProcess
+from lldb.plugins.scripted_process import ScriptedThread
+
+
+class DummyScriptedProcess(ScriptedProcess):
+memory = None
+
+def __init__(self,

[Lldb-commits] [lldb] [lldb][AIX] Added XCOFF Object File Header Parsing (PR #116337)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX created 
https://github.com/llvm/llvm-project/pull/116337

This PR is in reference to porting LLDB on AIX.

Link to discussions on llvm discourse and github:

1. https://discourse.llvm.org/t/port-lldb-to-ibm-aix/80640
2. https://github.com/llvm/llvm-project/issues/101657
The complete changes for porting are present in this draft PR:
https://github.com/llvm/llvm-project/pull/102601

Added XCOFF Object File Header Parsing for AIX.
This PR is an incremental PR to the base: 
#111814

Details about XCOFF file format on AIX: 
[XCOFF](https://www.ibm.com/docs/en/aix/7.3?topic=formats-xcoff-object-file-format)

Review Request: @labath @DavidSpickett

>From 0c63800bdcbadcfceed4c9a81305eda7d5a15960 Mon Sep 17 00:00:00 2001
From: Dhruv-Srivastava 
Date: Fri, 15 Nov 2024 02:16:31 -0600
Subject: [PATCH] Added XCOFF Header Parsing

---
 .../ObjectFile/XCOFF/ObjectFileXCOFF.cpp  | 126 +-
 .../ObjectFile/XCOFF/ObjectFileXCOFF.h|  58 
 2 files changed, 181 insertions(+), 3 deletions(-)

diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..c06ece4347822d 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,92 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = data.GetU16(offset_ptr);
+  m_xcoff_aux_head

[Lldb-commits] [lldb] [lldb][AIX] Added XCOFF Object File Header Parsing (PR #116337)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX edited 
https://github.com/llvm/llvm-project/pull/116337
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Added XCOFF Object File Header Parsing (PR #116337)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX edited 
https://github.com/llvm/llvm-project/pull/116337
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

DhruvSrivastavaX wrote:

Hi @labath , not sure why the `Labelling new pull requests` check failed. Also, 
the build check didnt automatically start for this one. 

https://github.com/llvm/llvm-project/pull/116338
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Make CompilerDecl::GetName (always) return template args (PR #116068)

2024-11-15 Thread Pavel Labath via lldb-commits

labath wrote:

> Very interesting find, I _think_ this makes sense since the `FindTypes` query 
> expects to find template parameters if we're looking up templates. And given 
> this API is used specifically to perform these kinds of queries, this LGTM. 
> But please confirm if my understanding is correct:
> 
> In the non-simple names case, when we stop at the breakpoint and start 
> formatting the function arguments, LLDB creates a `CXXRecordDecl` with the 
> name `bar` in the shared library TypeSystem because it only sees a 
> `DW_TAG_structure_type "bar"` forward declaration without any template 
> parameter children DIEs. Then when we call `FindCompleteType`, the `Decl`s 
> `DeclarationName` would've been set to `bar`, so the `TypeQuery` will be 
> able to match the `bar` definition using the index. When `FindTypes` 
> resolves the definition DIE we get from the index, it triggers the creation 
> of a `ClassTemplateSpecializationDecl` in the main module's TypeSystem and 
> everything works out.
> 
> But in the simple names case we create a `ClassTemplateSpecializationDecl` in 
> the shared library module (as opposed to a plain `CXXRecordDecl`), because 
> the forward declaration with `-gsimple-template-names` has a template 
> parameter DIE. But that declaration name is `bar`, because that's what DWARF 
> told us the `DeclarationName` of this `ClassTemplateSpecializationDecl` was. 
> But then `FindTypes` doesn't know what to do. It finds the `bar` definition 
> DIE from the index, but we actually end up _not_ doing a 
> `simple-template-names` lookup because 
> [UpdateCompilerContextForSimpleTemplateNames](https://github.com/llvm/llvm-project/blob/593be023615a456ca6ee0ef9bedc21301d73b73c/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp#L2816)
>  is only true if the query contained template parameters.

That is all correct. 

> 
> So I guess my question is, why is a `TypeQuery` by basename without template 
> parameters not supported if we compiled with `-gsimple-template-names`? 
> Despite us being able to find the definition DIE in the index? I guess the 
> idea of `UpdateCompilerContextForSimpleTemplateNames` was to avoid doing a 
> double-lookup if the first `FindTypes` failed for a template basename? (I 
> vaguely remember this coming up on the original review)

I think the problem here is of a more fundamental nature. `FindTypes` finds 
**types**. `bar` is *not* a type. `bar` is. So, while a type query for 
`bar` will find the definition DIE with `DW_AT_name="bar"`, that DIE will 
actually be defining the type `bar`. So when the implementation looks at 
the type constructed from that DIE, it will see that the name does not match 
what is being asked (it gets this name through a different API, so it will 
include the template args even without this patch), and discard the type.

As far as i know, this is all WAI. Existing FindType callers expect to get a 
specific type as a result of their query -- not a collection of instantiations 
of that template. (That's definitely true in this case, where returning the 
collection of instantiations would just push the burden of filtering them onto 
the caller.) That's not to say this kind of a template search is not useful. 
Having something like that would go a long way towards making expressions like 
`(bar *) ptr` work. But that would probably be a different API and the 
problem is that this is basically impossible to implement in a 
non-simplified-template-name world, and even with simplified names, returning 
all instantiations might be too expensive.

https://github.com/llvm/llvm-project/pull/116068
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

https://github.com/DhruvSrivastavaX updated 
https://github.com/llvm/llvm-project/pull/116338

>From 0c63800bdcbadcfceed4c9a81305eda7d5a15960 Mon Sep 17 00:00:00 2001
From: Dhruv-Srivastava 
Date: Fri, 15 Nov 2024 02:16:31 -0600
Subject: [PATCH 1/3] Added XCOFF Header Parsing

---
 .../ObjectFile/XCOFF/ObjectFileXCOFF.cpp  | 126 +-
 .../ObjectFile/XCOFF/ObjectFileXCOFF.h|  58 
 2 files changed, 181 insertions(+), 3 deletions(-)

diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..c06ece4347822d 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,92 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ModuleType = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.CpuFlag = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.CpuType = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.TextPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.DataPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.StackPageSize = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.FlagAndTDataAlignment = data.GetU8(offset_ptr);
+  m_xcoff_aux_header.TextSize = data.GetU64(offset_p

[Lldb-commits] [lldb] [lldb] Make CompilerDecl::GetName (always) return template args (PR #116068)

2024-11-15 Thread Michael Buch via lldb-commits

Michael137 wrote:

> I think the problem here is of a more fundamental nature. `FindTypes` finds 
> **types**. `bar` is _not_ a type. `bar` is. So, while a type query for 
> `bar` will find the definition DIE with `DW_AT_name="bar"`, that DIE will 
> actually be defining the type `bar`. So when the implementation looks at 
> the type constructed from that DIE, it will see that the name does not match 
> what is being asked (it gets this name through a different API, so it will 
> include the template args even without this patch), and discard the type.
> 
> As far as i know, this is all WAI. Existing FindType callers expect to get a 
> specific type as a result of their query -- not a collection of 
> instantiations of that template. (That's definitely true in this case, where 
> returning the collection of instantiations would just push the burden of 
> filtering them onto the caller.) That's not to say this kind of a template 
> search is not useful. Having something like that would go a long way towards 
> making expressions like `(bar *) ptr` work. But that would probably be a 
> different API and the problem is that this is basically impossible to 
> implement in a non-simplified-template-name world, and even with simplified 
> names, returning all instantiations might be too expensive.

Makes sense, thanks for elaborating

LGTM

The `TestDAP_evaluate.py` failure is 
https://github.com/llvm/llvm-project/issues/116041 (which should be fixed once 
you rebase)

https://github.com/llvm/llvm-project/pull/116068
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Make CompilerDecl::GetName (always) return template args (PR #116068)

2024-11-15 Thread Michael Buch via lldb-commits

https://github.com/Michael137 approved this pull request.


https://github.com/llvm/llvm-project/pull/116068
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Dhruv Srivastava via lldb-commits

DhruvSrivastavaX wrote:

> Do you actually need to parse the headers yourself? The reason for using the 
> llvm implementation was so that we can avoid that. FWICS, all of this data 
> should be available through the `(file|auxiliary)Header(32|64)` APIs.

Okay, I'll take a look at that. 



> BTW, this is exactly the kind of granularity I was looking for.

Happy to hear that! Will follow the similar practice.

> I don't know, but I wouldn't be worried about that. The test failure is more 
> of a concern.

Yeah, I think I missed the test case modification accordingly. Will update!

https://github.com/llvm/llvm-project/pull/116338
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactor lldb-dap.cpp to not use global DAP variable. (PR #116272)

2024-11-15 Thread John Harrison via lldb-commits


@@ -5046,30 +5026,48 @@ int main(int argc, char *argv[]) {
 pause();
   }
 #endif
+
+  // Initialize LLDB first before we do anything.
+  lldb::SBDebugger::Initialize();
+
+  // Terminate the debugger before the C++ destructor chain kicks in.
+  auto terminate_debugger =
+  llvm::make_scope_exit([] { lldb::SBDebugger::Terminate(); });
+
+  DAP dap = DAP(program_path.str(), default_repl_mode);

ashgti wrote:

I can follow up with a delete of the copy constructor 

https://github.com/llvm/llvm-project/pull/116272
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-da] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread John Harrison via lldb-commits

https://github.com/ashgti created 
https://github.com/llvm/llvm-project/pull/116392

This refactors the port listening mode to allocate a new DAP object for each 
connection, allowing multiple connections to run concurrently.

>From 43b8fc2a222e5460dd56782e31bd1b1ac399e03e Mon Sep 17 00:00:00 2001
From: John Harrison 
Date: Fri, 15 Nov 2024 09:56:43 -0500
Subject: [PATCH] [lldb-da] Refactoring lldb-dap port listening mode to allow
 multiple connections.

This refactors the port listening mode to allocate a new DAP object for each 
connection, allowing multiple connections to run concurrently.
---
 .../Python/lldbsuite/test/lldbtest.py |   8 +
 .../test/tools/lldb-dap/dap_server.py |  75 +++-
 .../test/tools/lldb-dap/lldbdap_testcase.py   |  32 +-
 lldb/test/API/tools/lldb-dap/server/Makefile  |   3 +
 .../tools/lldb-dap/server/TestDAP_server.py   |  66 
 lldb/test/API/tools/lldb-dap/server/main.c|   6 +
 lldb/tools/lldb-dap/DAP.cpp   |  23 +-
 lldb/tools/lldb-dap/DAP.h |  50 +--
 lldb/tools/lldb-dap/Options.td|   9 +
 lldb/tools/lldb-dap/OutputRedirector.cpp  |   7 +-
 lldb/tools/lldb-dap/OutputRedirector.h|  12 +-
 lldb/tools/lldb-dap/lldb-dap.cpp  | 366 ++
 12 files changed, 506 insertions(+), 151 deletions(-)
 create mode 100644 lldb/test/API/tools/lldb-dap/server/Makefile
 create mode 100644 lldb/test/API/tools/lldb-dap/server/TestDAP_server.py
 create mode 100644 lldb/test/API/tools/lldb-dap/server/main.c

diff --git a/lldb/packages/Python/lldbsuite/test/lldbtest.py 
b/lldb/packages/Python/lldbsuite/test/lldbtest.py
index 8884ef5933ada8..a899854bb5ae14 100644
--- a/lldb/packages/Python/lldbsuite/test/lldbtest.py
+++ b/lldb/packages/Python/lldbsuite/test/lldbtest.py
@@ -39,6 +39,7 @@
 import signal
 from subprocess import *
 import sys
+import socket
 import time
 import traceback
 
@@ -250,6 +251,13 @@ def which(program):
 return None
 
 
+def pickrandomport():
+"""Returns a random open port."""
+with socket.socket() as sock:
+sock.bind(("", 0))
+return sock.getsockname()[1]
+
+
 class ValueCheck:
 def __init__(
 self,
diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py 
b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
index c29992ce9c7848..e4a53fe0d45907 100644
--- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
+++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
@@ -903,7 +903,7 @@ def request_setBreakpoints(self, file_path, line_array, 
data=None):
 "sourceModified": False,
 }
 if line_array is not None:
-args_dict["lines"] = "%s" % line_array
+args_dict["lines"] = line_array
 breakpoints = []
 for i, line in enumerate(line_array):
 breakpoint_data = None
@@ -1154,34 +1154,38 @@ class DebugAdaptorServer(DebugCommunication):
 def __init__(
 self,
 executable=None,
+launch=True,
 port=None,
+unix_socket=None,
 init_commands=[],
 log_file=None,
 env=None,
 ):
 self.process = None
-if executable is not None:
-adaptor_env = os.environ.copy()
-if env is not None:
-adaptor_env.update(env)
-
-if log_file:
-adaptor_env["LLDBDAP_LOG"] = log_file
-self.process = subprocess.Popen(
-[executable],
-stdin=subprocess.PIPE,
-stdout=subprocess.PIPE,
-stderr=subprocess.PIPE,
-env=adaptor_env,
+if launch:
+self.process = DebugAdaptorServer.launch(
+executable,
+port=port,
+unix_socket=unix_socket,
+log_file=log_file,
+env=env,
 )
-DebugCommunication.__init__(
-self, self.process.stdout, self.process.stdin, init_commands, 
log_file
-)
-elif port is not None:
+
+if port:
 s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
 s.connect(("127.0.0.1", port))
 DebugCommunication.__init__(
-self, s.makefile("r"), s.makefile("w"), init_commands
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+elif unix_socket:
+s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
+s.connect(unix_socket)
+DebugCommunication.__init__(
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+else:
+DebugCommunication.__init__(
+self, self.process.stdout, self.process.stdin, init_commands, 
log_file
 )
 
 def get_pid(self):
@@ -1196,6 +1200,39 @@ def terminate(self):
   

[Lldb-commits] [lldb] [lldb-da] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread John Harrison via lldb-commits

https://github.com/ashgti updated 
https://github.com/llvm/llvm-project/pull/116392

>From acfdb2da30b7a49711c3d1ec3be3c9282d6c51b4 Mon Sep 17 00:00:00 2001
From: John Harrison 
Date: Fri, 15 Nov 2024 09:56:43 -0500
Subject: [PATCH] [lldb-da] Refactoring lldb-dap port listening mode to allow
 multiple connections.

This refactors the port listening mode to allocate a new DAP object for each 
connection, allowing multiple connections to run concurrently.
---
 .../Python/lldbsuite/test/lldbtest.py |   8 +
 .../test/tools/lldb-dap/dap_server.py |  75 +++-
 .../test/tools/lldb-dap/lldbdap_testcase.py   |  32 +-
 lldb/test/API/tools/lldb-dap/server/Makefile  |   3 +
 .../tools/lldb-dap/server/TestDAP_server.py   |  66 
 lldb/test/API/tools/lldb-dap/server/main.c|   6 +
 lldb/tools/lldb-dap/DAP.cpp   |  23 +-
 lldb/tools/lldb-dap/DAP.h |  50 +--
 lldb/tools/lldb-dap/Options.td|   9 +
 lldb/tools/lldb-dap/OutputRedirector.cpp  |   7 +-
 lldb/tools/lldb-dap/OutputRedirector.h|  12 +-
 lldb/tools/lldb-dap/lldb-dap.cpp  | 366 ++
 12 files changed, 506 insertions(+), 151 deletions(-)
 create mode 100644 lldb/test/API/tools/lldb-dap/server/Makefile
 create mode 100644 lldb/test/API/tools/lldb-dap/server/TestDAP_server.py
 create mode 100644 lldb/test/API/tools/lldb-dap/server/main.c

diff --git a/lldb/packages/Python/lldbsuite/test/lldbtest.py 
b/lldb/packages/Python/lldbsuite/test/lldbtest.py
index 8884ef5933ada8..a899854bb5ae14 100644
--- a/lldb/packages/Python/lldbsuite/test/lldbtest.py
+++ b/lldb/packages/Python/lldbsuite/test/lldbtest.py
@@ -39,6 +39,7 @@
 import signal
 from subprocess import *
 import sys
+import socket
 import time
 import traceback
 
@@ -250,6 +251,13 @@ def which(program):
 return None
 
 
+def pickrandomport():
+"""Returns a random open port."""
+with socket.socket() as sock:
+sock.bind(("", 0))
+return sock.getsockname()[1]
+
+
 class ValueCheck:
 def __init__(
 self,
diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py 
b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
index c29992ce9c7848..e4a53fe0d45907 100644
--- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
+++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
@@ -903,7 +903,7 @@ def request_setBreakpoints(self, file_path, line_array, 
data=None):
 "sourceModified": False,
 }
 if line_array is not None:
-args_dict["lines"] = "%s" % line_array
+args_dict["lines"] = line_array
 breakpoints = []
 for i, line in enumerate(line_array):
 breakpoint_data = None
@@ -1154,34 +1154,38 @@ class DebugAdaptorServer(DebugCommunication):
 def __init__(
 self,
 executable=None,
+launch=True,
 port=None,
+unix_socket=None,
 init_commands=[],
 log_file=None,
 env=None,
 ):
 self.process = None
-if executable is not None:
-adaptor_env = os.environ.copy()
-if env is not None:
-adaptor_env.update(env)
-
-if log_file:
-adaptor_env["LLDBDAP_LOG"] = log_file
-self.process = subprocess.Popen(
-[executable],
-stdin=subprocess.PIPE,
-stdout=subprocess.PIPE,
-stderr=subprocess.PIPE,
-env=adaptor_env,
+if launch:
+self.process = DebugAdaptorServer.launch(
+executable,
+port=port,
+unix_socket=unix_socket,
+log_file=log_file,
+env=env,
 )
-DebugCommunication.__init__(
-self, self.process.stdout, self.process.stdin, init_commands, 
log_file
-)
-elif port is not None:
+
+if port:
 s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
 s.connect(("127.0.0.1", port))
 DebugCommunication.__init__(
-self, s.makefile("r"), s.makefile("w"), init_commands
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+elif unix_socket:
+s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
+s.connect(unix_socket)
+DebugCommunication.__init__(
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+else:
+DebugCommunication.__init__(
+self, self.process.stdout, self.process.stdin, init_commands, 
log_file
 )
 
 def get_pid(self):
@@ -1196,6 +1200,39 @@ def terminate(self):
 self.process.wait()
 self.process = None
 
+@classmethod
+def launch(
+cls, executable: str, /, port=None, u

[Lldb-commits] [lldb] [lldb-da] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread John Harrison via lldb-commits

https://github.com/ashgti ready_for_review 
https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-da] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread via lldb-commits

github-actions[bot] wrote:




:warning: C/C++ code formatter, clang-format found issues in your code. 
:warning:



You can test this locally with the following command:


``bash
git-clang-format --diff 0fb8fac5d6c10610574e6e472670823eaff0c949 
acfdb2da30b7a49711c3d1ec3be3c9282d6c51b4 --extensions h,c,cpp -- 
lldb/test/API/tools/lldb-dap/server/main.c lldb/tools/lldb-dap/DAP.cpp 
lldb/tools/lldb-dap/DAP.h lldb/tools/lldb-dap/OutputRedirector.cpp 
lldb/tools/lldb-dap/OutputRedirector.h lldb/tools/lldb-dap/lldb-dap.cpp
``





View the diff from clang-format here.


``diff
diff --git a/lldb/tools/lldb-dap/DAP.cpp b/lldb/tools/lldb-dap/DAP.cpp
index 8998036fbe..a1e4159965 100644
--- a/lldb/tools/lldb-dap/DAP.cpp
+++ b/lldb/tools/lldb-dap/DAP.cpp
@@ -34,8 +34,8 @@ namespace lldb_dap {
 
 DAP::DAP(llvm::StringRef path, std::shared_ptr log,
  ReplMode repl_mode, std::vector pre_init_commands)
-: debug_adaptor_path(path), broadcaster("lldb-dap"),
-  log(log), exception_breakpoints(), pre_init_commands(pre_init_commands),
+: debug_adaptor_path(path), broadcaster("lldb-dap"), log(log),
+  exception_breakpoints(), pre_init_commands(pre_init_commands),
   focus_tid(LLDB_INVALID_THREAD_ID), stop_at_entry(false), 
is_attach(false),
   enable_auto_variable_summaries(false),
   enable_synthetic_child_debugging(false),

``




https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Fix regex support in SBTarget.modules_access (PR #116452)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Dave Lee (kastiglione)


Changes

First, `SRE_Pattern` does not exist on newer Python's, use 
`type(re.compile(''))` like other Python extensions do. The dynamic type is 
because some earlier versions of Python 3 do not have `re.Pattern`.

Second, `SBModule` has a `file` property, not a `path` property.

---
Full diff: https://github.com/llvm/llvm-project/pull/116452.diff


2 Files Affected:

- (modified) lldb/bindings/interface/SBTargetExtensions.i (+2-2) 
- (modified) lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py (+6-9) 


``diff
diff --git a/lldb/bindings/interface/SBTargetExtensions.i 
b/lldb/bindings/interface/SBTargetExtensions.i
index d756a351a810ab..43125d8970615b 100644
--- a/lldb/bindings/interface/SBTargetExtensions.i
+++ b/lldb/bindings/interface/SBTargetExtensions.i
@@ -79,11 +79,11 @@ STRING_EXTENSION_LEVEL_OUTSIDE(SBTarget, 
lldb::eDescriptionLevelBrief)
 module = self.sbtarget.GetModuleAtIndex(idx)
 if module.uuid == key:
 return module
-elif type(key) is re.SRE_Pattern:
+elif isinstance(key, type(re.compile(''))):
 matching_modules = []
 for idx in range(num_modules):
 module = self.sbtarget.GetModuleAtIndex(idx)
-re_match = key.search(module.path.fullpath)
+re_match = key.search(module.file.fullpath)
 if re_match:
 matching_modules.append(module)
 return matching_modules
diff --git a/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py 
b/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
index 06f338b3ed1ded..bcf8735c7c3f98 100644
--- a/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
+++ b/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
@@ -3,6 +3,7 @@
 """
 
 import os
+import re
 import lldb
 from lldbsuite.test.lldbtest import *
 import lldbsuite.test.lldbutil as lldbutil
@@ -30,15 +31,11 @@ def test_stdcxx_disasm(self):
 self.runCmd("disassemble -n '%s'" % function.GetName())
 
 lib_stdcxx = "FAILHORRIBLYHERE"
-# Iterate through the available modules, looking for stdc++ library...
-for i in range(target.GetNumModules()):
-module = target.GetModuleAtIndex(i)
-fs = module.GetFileSpec()
-if fs.GetFilename().startswith("libstdc++") or 
fs.GetFilename().startswith(
-"libc++"
-):
-lib_stdcxx = str(fs)
-break
+# Find the stdc++ library...
+stdlib_regex = re.compile(r"/lib(std)?c\+\+")
+for module in target.module[stdlib_regex]:
+lib_stdcxx = module.file.fullpath
+break
 
 # At this point, lib_stdcxx is the full path to the stdc++ library and
 # module is the corresponding SBModule.

``




https://github.com/llvm/llvm-project/pull/116452
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Fix regex support in SBTarget.modules_access (PR #116452)

2024-11-15 Thread Dave Lee via lldb-commits

https://github.com/kastiglione edited 
https://github.com/llvm/llvm-project/pull/116452
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Improve editline completion formatting (PR #116456)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere created 
https://github.com/llvm/llvm-project/pull/116456

This patch improves the formatting of editline completions. The current 
implementation is naive and doesn't account for the terminal width.

Concretely, the old implementation suffered from the following issues:

 - We would unconditionally pad to the longest completion. If that completion 
exceeds the width of the terminal, that would result in a lot of superfluous 
white space and line wrapping.
 - When printing the description, we wouldn't account for the presence of 
newlines, and they would continue without leading padding.

The new code accounts for both. If the completion exceeds the available 
terminal width, we show what fits on the current lined followed by ellipsis. We 
also no longer pad beyond the length of the current line. Finally, we print the 
description line by line, with the proper leading padding. If a line of the 
description exceeds the available terminal width, we print ellipsis and won't 
print the next line.

Before:

```
Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorthand
 formats.
_regexp-bt-- Show backtrace of the current thread's call sta
ck. Any numeric argument displays at most that many frames. The argument 'al
l' displays all threads. Use 'settings set frame-format' to customize the pr
inting of individual frames and 'settings set thread-format' to customize th
e thread header. Frame recognizers may filter thelist. Use 'thread backtrace
 -u (--unfiltered)' to see them all.
_regexp-display   -- Evaluate an expression at every stop (see 'help
 target stop-hook'.)

```

After:
```
 Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorth...
_regexp-bt-- Show backtrace of the current thread's call ...
_regexp-display   -- Evaluate an expression at every stop (see 'h...
```

rdar://135818198

>From a694405bd2e1b8cc96183c2f406dddbb8555cd51 Mon Sep 17 00:00:00 2001
From: Jonas Devlieghere 
Date: Fri, 15 Nov 2024 16:06:47 -0800
Subject: [PATCH] [lldb] Improve editline completion formatting

This patch improves the formatting of editline completions. The current
implementation is naive and doesn't account for the terminal width.

Concretely, the old implementation suffered from the following issues:

 - We would unconditionally pad to the longest completion. If that
   completion exceeds the width of the terminal, that would result in a
   lot of superfluous white space and line wrapping.
 - When printing the description, we wouldn't account for the presence
   of newlines, and they would continue without leading padding.

The new code accounts for both. If the completion exceeds the available
terminal width, we show what fits on the current lined followed by
ellipsis. We also no longer pad beyond the length of the current line.
Finally, we print the description line by line, with the proper leading
padding. If a line of the description exceeds the available terminal
width, we print ellipsis and won't print the next line.

Before:

```
Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorthand
 formats.
_regexp-bt-- Show backtrace of the current thread's call sta
ck. Any numeric argument displays at most that many frames. The argument 'al
l' displays all threads. Use 'settings set frame-format' to customize the pr
inting of individual frames and 'settings set thread-format' to customize th
e thread header. Frame recognizers may filter thelist. Use 'thread backtrace
 -u (--unfiltered)' to see them all.
_regexp-display   -- Evaluate an expression at every stop (see 'help
 target stop-hook'.)

```

After:
```
 Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorth...
_regexp-bt-- Show backtrace of the current thread's call ...
_regexp-display   -- Evaluate an expression at every stop (see 'h...
```

rdar://135818198
---
 lldb/include/lldb/Host/Editline.h|  2 +
 lldb/source/Host/common/Editline.cpp | 96 ++--
 2 files changed, 91 insertions(+), 7 deletions(-)

diff --git a/lldb/include/lldb/Host/Editline.h 
b/lldb/include/lldb/Host/Editline.h
index 57e2c831e3499d..e8e8a6c0d4f67e 100644
--- a/lldb/include/lldb/Host/Editline.h
+++ b/lldb/include/lldb/Host/Editline.h
@@ -238,6 +238,8 @@ class Editline {
   /// Convert the current input lines into a UTF8 StringList
   StringList GetInputAsStringList(int line_count = UINT32_MAX);
 
+  size_t GetTerminalWidth() { return m_terminal_width; }
+
 private:
   /// Sets the lowest line number for multi-line editing sessions. 

[Lldb-commits] [lldb] [lldb] Improve editline completion formatting (PR #116456)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere updated 
https://github.com/llvm/llvm-project/pull/116456

>From 3434c7de701e4851b4eefe25f23e49d415ba4dd3 Mon Sep 17 00:00:00 2001
From: Jonas Devlieghere 
Date: Fri, 15 Nov 2024 16:06:47 -0800
Subject: [PATCH] [lldb] Improve editline completion formatting

This patch improves the formatting of editline completions. The current
implementation is naive and doesn't account for the terminal width.

Concretely, the old implementation suffered from the following issues:

 - We would unconditionally pad to the longest completion. If that
   completion exceeds the width of the terminal, that would result in a
   lot of superfluous white space and line wrapping.
 - When printing the description, we wouldn't account for the presence
   of newlines, and they would continue without leading padding.

The new code accounts for both. If the completion exceeds the available
terminal width, we show what fits on the current lined followed by
ellipsis. We also no longer pad beyond the length of the current line.
Finally, we print the description line by line, with the proper leading
padding. If a line of the description exceeds the available terminal
width, we print ellipsis and won't print the next line.

Before:

```
Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorthand
 formats.
_regexp-bt-- Show backtrace of the current thread's call sta
ck. Any numeric argument displays at most that many frames. The argument 'al
l' displays all threads. Use 'settings set frame-format' to customize the pr
inting of individual frames and 'settings set thread-format' to customize th
e thread header. Frame recognizers may filter thelist. Use 'thread backtrace
 -u (--unfiltered)' to see them all.
_regexp-display   -- Evaluate an expression at every stop (see 'help
 target stop-hook'.)

```

After:
```
 Available completions:
_regexp-attach-- Attach to process by ID or name.
_regexp-break -- Set a breakpoint using one of several shorth...
_regexp-bt-- Show backtrace of the current thread's call ...
_regexp-display   -- Evaluate an expression at every stop (see 'h...
```

rdar://135818198
---
 lldb/include/lldb/Host/Editline.h|  2 +
 lldb/source/Host/common/Editline.cpp | 95 ++--
 2 files changed, 90 insertions(+), 7 deletions(-)

diff --git a/lldb/include/lldb/Host/Editline.h 
b/lldb/include/lldb/Host/Editline.h
index 57e2c831e3499d..e8e8a6c0d4f67e 100644
--- a/lldb/include/lldb/Host/Editline.h
+++ b/lldb/include/lldb/Host/Editline.h
@@ -238,6 +238,8 @@ class Editline {
   /// Convert the current input lines into a UTF8 StringList
   StringList GetInputAsStringList(int line_count = UINT32_MAX);
 
+  size_t GetTerminalWidth() { return m_terminal_width; }
+
 private:
   /// Sets the lowest line number for multi-line editing sessions.  A value of
   /// zero suppresses line number printing in the prompt.
diff --git a/lldb/source/Host/common/Editline.cpp 
b/lldb/source/Host/common/Editline.cpp
index f95f854c5f220c..109cc897b853f3 100644
--- a/lldb/source/Host/common/Editline.cpp
+++ b/lldb/source/Host/common/Editline.cpp
@@ -927,12 +927,92 @@ unsigned char Editline::BufferEndCommand(int ch) {
 static void
 PrintCompletion(FILE *output_file,
 llvm::ArrayRef results,
-size_t max_len) {
+size_t max_completion_length, size_t max_lenght) {
+
+  constexpr size_t ellipsis_length = 3;
+  constexpr size_t tab_legnth = 8;
+  constexpr size_t separator_length = 4;
+  const size_t description_col =
+  std::min(max_completion_length + tab_legnth, max_lenght);
+
   for (const CompletionResult::Completion &c : results) {
-fprintf(output_file, "\t%-*s", (int)max_len, c.GetCompletion().c_str());
-if (!c.GetDescription().empty())
-  fprintf(output_file, " -- %s", c.GetDescription().c_str());
-fprintf(output_file, "\n");
+// Print the leading tab-sized padding.
+fprintf(output_file, "");
+size_t cursor = tab_legnth;
+
+if (!c.GetCompletion().empty()) {
+  const size_t completion_length = c.GetCompletion().size();
+  if (cursor + completion_length < max_lenght) {
+fprintf(output_file, "%s", c.GetCompletion().c_str());
+cursor = cursor + completion_length;
+  } else {
+// If the completion doesn't fit on the screen, print ellipsis and 
don't
+// bother with the description.
+fprintf(output_file, "%s...\n",
+c.GetCompletion()
+.substr(0, max_lenght - cursor - ellipsis_length)
+.c_str());
+continue;
+  }
+}
+
+if (!c.GetDescription().empty()) {
+  // If we have a description, we need at least 4 columns for the 
separator.
+  if (cursor + separator_length < max_lenght) {
+// Add padding before the sep

[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

jimingham wrote:

Ah, right.  The one place where a ThreadPlan should be messing with the 
ThreadPlanStack (through its Thread) is ThreadPlan::DidPush.  The point of that 
is largely that thread plans can't push new thread plans on the stack in their 
constructor - since they aren't on the stack yet.  However there are plans that 
work by delegating so they need to push the delegate plan before getting asked 
any questions.   That's what DidPush is for.

https://github.com/llvm/llvm-project/pull/116438
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits

https://github.com/vogelsgesang edited 
https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -137,42 +141,232 @@ lldb::SBValueList *GetTopLevelScope(DAP &dap, int64_t 
variablesReference) {
   }
 }
 
-SOCKET AcceptConnection(DAP &dap, int portno) {
-  // Accept a socket connection from any host on "portno".
-  SOCKET newsockfd = -1;
-  struct sockaddr_in serv_addr, cli_addr;
+/// Redirect stdout and stderr fo the IDE's console output.
+///
+/// Errors in this operation will be printed to the log file and the IDE's
+/// console output as well.
+///
+/// \return
+/// A fd pointing to the original stdout.
+void SetupRedirection(DAP &dap, int stdoutfd = -1, int stderrfd = -1) {

vogelsgesang wrote:

what is the intended behavior here if we have multiple DAP connections running 
in parallel?

Should the `stdin` be redirected to all of them? Only the latest one? Only the 
first one?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Add logging for missing `.dwo` files (PR #116436)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Adrian Vogelsgesang (vogelsgesang)


Changes

I had a hard time to debug a `dwo` file whose file was not found. This log 
message would have saved me a lot of time.

---
Full diff: https://github.com/llvm/llvm-project/pull/116436.diff


1 Files Affected:

- (modified) lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp (+8) 


``diff
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp 
b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
index 666595a6d0635f..2bb41903beb3b4 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
@@ -1963,6 +1963,14 @@ SymbolFileDWARF::GetDwoSymbolFileForCompileUnit(
 "{1:x16}",
 error_dwo_path.GetPath().c_str(), cu_die.GetOffset()));
 
+if (Log *log = GetLog(LLDBLog::Symbols)) {
+  GetObjectFile()->GetModule()->LogMessage(
+  log,
+  "unable to locate .dwo debug file \"{0}\" for skeleton DIE "
+  "{1:x16}",
+  error_dwo_path.GetPath().c_str(), unit.GetOffset());
+}
+
 if (m_dwo_warning_issued.test_and_set(std::memory_order_relaxed) == false) 
{
   GetObjectFile()->GetModule()->ReportWarning(
   "unable to locate separate debug file (dwo, dwp). Debugging will be "

``




https://github.com/llvm/llvm-project/pull/116436
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere edited 
https://github.com/llvm/llvm-project/pull/116438
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Fix regex support in SBTarget.modules_access (PR #116452)

2024-11-15 Thread Dave Lee via lldb-commits

https://github.com/kastiglione created 
https://github.com/llvm/llvm-project/pull/116452

First, `SRE_Pattern` does not exist on newer Python's, use
`type(re.compile(''))` like other Python extensions do. The dynamic type is
because some earlier versions of Python 3 do not have `re.Pattern`.

Second, `SBModule` has a `file` property, not a `path` property.


>From 5379412f53352acafd75575d8b54806050de535d Mon Sep 17 00:00:00 2001
From: Dave Lee 
Date: Fri, 15 Nov 2024 15:24:44 -0800
Subject: [PATCH] [lldb] Fix regex support in SBTarget.modules_access

First, `SRE_Pattern` does not exist on newer Python's, use
`type(re.compile(''))` like other Python extensions do. The dynamic type is
because some earlier versions of Python 3 do not have `re.Pattern`.

Second, `SBModule` has a `file` property, not a `path` property.
---
 lldb/bindings/interface/SBTargetExtensions.i  |  4 ++--
 .../API/lang/cpp/stl/TestStdCXXDisassembly.py | 15 ++-
 2 files changed, 8 insertions(+), 11 deletions(-)

diff --git a/lldb/bindings/interface/SBTargetExtensions.i 
b/lldb/bindings/interface/SBTargetExtensions.i
index d756a351a810ab..43125d8970615b 100644
--- a/lldb/bindings/interface/SBTargetExtensions.i
+++ b/lldb/bindings/interface/SBTargetExtensions.i
@@ -79,11 +79,11 @@ STRING_EXTENSION_LEVEL_OUTSIDE(SBTarget, 
lldb::eDescriptionLevelBrief)
 module = self.sbtarget.GetModuleAtIndex(idx)
 if module.uuid == key:
 return module
-elif type(key) is re.SRE_Pattern:
+elif isinstance(key, type(re.compile(''))):
 matching_modules = []
 for idx in range(num_modules):
 module = self.sbtarget.GetModuleAtIndex(idx)
-re_match = key.search(module.path.fullpath)
+re_match = key.search(module.file.fullpath)
 if re_match:
 matching_modules.append(module)
 return matching_modules
diff --git a/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py 
b/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
index 06f338b3ed1ded..bcf8735c7c3f98 100644
--- a/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
+++ b/lldb/test/API/lang/cpp/stl/TestStdCXXDisassembly.py
@@ -3,6 +3,7 @@
 """
 
 import os
+import re
 import lldb
 from lldbsuite.test.lldbtest import *
 import lldbsuite.test.lldbutil as lldbutil
@@ -30,15 +31,11 @@ def test_stdcxx_disasm(self):
 self.runCmd("disassemble -n '%s'" % function.GetName())
 
 lib_stdcxx = "FAILHORRIBLYHERE"
-# Iterate through the available modules, looking for stdc++ library...
-for i in range(target.GetNumModules()):
-module = target.GetModuleAtIndex(i)
-fs = module.GetFileSpec()
-if fs.GetFilename().startswith("libstdc++") or 
fs.GetFilename().startswith(
-"libc++"
-):
-lib_stdcxx = str(fs)
-break
+# Find the stdc++ library...
+stdlib_regex = re.compile(r"/lib(std)?c\+\+")
+for module in target.module[stdlib_regex]:
+lib_stdcxx = module.file.fullpath
+break
 
 # At this point, lib_stdcxx is the full path to the stdc++ library and
 # module is the corresponding SBModule.

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Fix regex support in SBTarget.modules_access (PR #116452)

2024-11-15 Thread Dave Lee via lldb-commits


@@ -79,11 +79,11 @@ STRING_EXTENSION_LEVEL_OUTSIDE(SBTarget, 
lldb::eDescriptionLevelBrief)
 module = self.sbtarget.GetModuleAtIndex(idx)
 if module.uuid == key:
 return module
-elif type(key) is re.SRE_Pattern:
+elif isinstance(key, type(re.compile(''))):
 matching_modules = []
 for idx in range(num_modules):
 module = self.sbtarget.GetModuleAtIndex(idx)
-re_match = key.search(module.path.fullpath)
+re_match = key.search(module.file.fullpath)

kastiglione wrote:

Since this was broken, and obviously not used, I'd like to also change this 
from `fullpath` to `basename`. Opinions?

https://github.com/llvm/llvm-project/pull/116452
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -22,8 +22,17 @@ def port: S<"port">,
   HelpText<"Communicate with the lldb-dap tool over the defined port.">;
 def: Separate<["-"], "p">,
   Alias,
+  MetaVarName<"">,
   HelpText<"Alias for --port">;
 
+def unix_socket: S<"unix-socket">,
+  MetaVarName<"">,
+  HelpText<"Communicate with the lldb-dap tool over the unix socket or named 
pipe.">;
+def: Separate<["-"], "u">,

vogelsgesang wrote:

```suggestion
def: Separate<["-"], "s">,
```

(assuming we rename `unix_socket` to `socket`)

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Convert file address to load address when reading memory for DW_OP_piece (PR #116411)

2024-11-15 Thread Ilia Kuklin via lldb-commits

https://github.com/kuilpd created 
https://github.com/llvm/llvm-project/pull/116411

When parsing an optimized value and reading a piece from a file address, LLDB 
tries to read the data from memory using that address.
This patch converts file address to load address before reading the memory.

Fixes #111313 #97484

>From 37f9b0f2388349bbf74e1225391efd61c55f756c Mon Sep 17 00:00:00 2001
From: Ilia Kuklin 
Date: Thu, 14 Nov 2024 20:15:19 +0500
Subject: [PATCH 1/2] Convert file address to load address when reading memory
 for DW_OP_piece

---
 lldb/source/Expression/DWARFExpression.cpp | 19 ---
 1 file changed, 16 insertions(+), 3 deletions(-)

diff --git a/lldb/source/Expression/DWARFExpression.cpp 
b/lldb/source/Expression/DWARFExpression.cpp
index f92f25ed342a9c..a7126b25c1cc38 100644
--- a/lldb/source/Expression/DWARFExpression.cpp
+++ b/lldb/source/Expression/DWARFExpression.cpp
@@ -1853,12 +1853,25 @@ llvm::Expected DWARFExpression::Evaluate(
   const Value::ValueType curr_piece_source_value_type =
   curr_piece_source_value.GetValueType();
   Scalar &scalar = curr_piece_source_value.GetScalar();
-  const lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+  lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
   switch (curr_piece_source_value_type) {
   case Value::ValueType::Invalid:
 return llvm::createStringError("invalid value type");
-  case Value::ValueType::LoadAddress:
-  case Value::ValueType::FileAddress: {
+  case Value::ValueType::FileAddress:
+if (target) {
+  curr_piece_source_value.ConvertToLoadAddress(module_sp.get(),
+   target);
+  addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+} else {
+  return llvm::createStringError(
+  "unable to convert file address 0x%" PRIx64
+  " to load address "
+  "for DW_OP_piece(%" PRIu64 "): "
+  "no target available",
+  addr, piece_byte_size);
+}
+[[fallthrough]];
+  case Value::ValueType::LoadAddress: {
 if (target) {
   if (curr_piece.ResizeData(piece_byte_size) == piece_byte_size) {
 if (target->ReadMemory(addr, curr_piece.GetBuffer().GetBytes(),

>From 86c66f7084fb35371e057388d4edc50790c1c6b8 Mon Sep 17 00:00:00 2001
From: Ilia Kuklin 
Date: Fri, 15 Nov 2024 20:42:58 +0500
Subject: [PATCH 2/2] Add a test

---
 .../Shell/SymbolFile/DWARF/DW_OP_piece-O3.c   | 23 +++
 1 file changed, 23 insertions(+)
 create mode 100644 lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c

diff --git a/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c 
b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
new file mode 100644
index 00..d31250426dc112
--- /dev/null
+++ b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
@@ -0,0 +1,23 @@
+// Check that optimized with -O3 values that have a file address can be read
+// DWARF info:
+// 0x0023:   DW_TAG_variable
+// DW_AT_name  ("array")
+// DW_AT_type  (0x0032 "char[5]")
+// DW_AT_location  (DW_OP_piece 0x2, DW_OP_addrx 0x0, 
DW_OP_piece 0x1)
+
+// RUN: %clang_host -O3 -gdwarf %s -o %t
+// RUN: %lldb %t \
+// RUN:   -o "b 22" \
+// RUN:   -o "r" \
+// RUN:   -o "p/x array[2]" \
+// RUN:   -b | FileCheck %s
+//
+// CHECK: (lldb) p/x array[2]
+// CHECK: (char) 0x03
+
+static char array[5] = {0, 1, 2, 3, 4};
+
+int main(void) {
+  array[2]++;
+  return 0;
+}
\ No newline at end of file

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Convert file address to load address when reading memory for DW_OP_piece (PR #116411)

2024-11-15 Thread Ilia Kuklin via lldb-commits

https://github.com/kuilpd edited 
https://github.com/llvm/llvm-project/pull/116411
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -22,8 +22,17 @@ def port: S<"port">,
   HelpText<"Communicate with the lldb-dap tool over the defined port.">;
 def: Separate<["-"], "p">,
   Alias,
+  MetaVarName<"">,
   HelpText<"Alias for --port">;
 
+def unix_socket: S<"unix-socket">,
+  MetaVarName<"">,
+  HelpText<"Communicate with the lldb-dap tool over the unix socket or named 
pipe.">;

vogelsgesang wrote:

should we maybe name this `socket` instead of `unix-socket`? As it apparently 
also support Windows named pipes, which are not UNIX?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -137,42 +141,232 @@ lldb::SBValueList *GetTopLevelScope(DAP &dap, int64_t 
variablesReference) {
   }
 }
 
-SOCKET AcceptConnection(DAP &dap, int portno) {
-  // Accept a socket connection from any host on "portno".
-  SOCKET newsockfd = -1;
-  struct sockaddr_in serv_addr, cli_addr;
+/// Redirect stdout and stderr fo the IDE's console output.
+///
+/// Errors in this operation will be printed to the log file and the IDE's
+/// console output as well.
+///
+/// \return
+/// A fd pointing to the original stdout.
+void SetupRedirection(DAP &dap, int stdoutfd = -1, int stderrfd = -1) {

vogelsgesang wrote:

should this be a member function of the `DAP` class?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -140,13 +137,16 @@ struct DAP {
   llvm::StringRef debug_adaptor_path;
   InputStream input;
   OutputStream output;
+  lldb::SBFile in;
+  lldb::SBFile out;
+  lldb::SBFile err;
   lldb::SBDebugger debugger;
   lldb::SBTarget target;
   Variables variables;
   lldb::SBBroadcaster broadcaster;
   std::thread event_thread;
   std::thread progress_event_thread;
-  std::unique_ptr log;
+  std::shared_ptr log;

vogelsgesang wrote:

should this be a `shared_ptr`? Afaict a reference should be sufficient, given 
that the log file is global and will always outlive the `DAP` instances

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -22,8 +22,17 @@ def port: S<"port">,
   HelpText<"Communicate with the lldb-dap tool over the defined port.">;
 def: Separate<["-"], "p">,
   Alias,
+  MetaVarName<"">,
   HelpText<"Alias for --port">;
 
+def unix_socket: S<"unix-socket">,
+  MetaVarName<"">,
+  HelpText<"Communicate with the lldb-dap tool over the unix socket or named 
pipe.">;
+def: Separate<["-"], "u">,
+  Alias,
+  MetaVarName<"">,
+  HelpText<"Alias for --unix_socket">;

vogelsgesang wrote:

```suggestion
  HelpText<"Alias for --unix-socket">;
```

afaict, the above entry calls it `unix-socket`, not `unix_socket`?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -0,0 +1,6 @@
+#include 
+
+int main(int argc, char const *argv[]) {
+  printf("hello world!\n"); // breakpoint 1
+  return 0;
+}

vogelsgesang wrote:

missing trailing new line (afaik, we are using UNIX conventions, not Windows 
conventions?)

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -137,42 +141,232 @@ lldb::SBValueList *GetTopLevelScope(DAP &dap, int64_t 
variablesReference) {
   }
 }
 
-SOCKET AcceptConnection(DAP &dap, int portno) {
-  // Accept a socket connection from any host on "portno".
-  SOCKET newsockfd = -1;
-  struct sockaddr_in serv_addr, cli_addr;
+/// Redirect stdout and stderr fo the IDE's console output.
+///
+/// Errors in this operation will be printed to the log file and the IDE's
+/// console output as well.
+///
+/// \return
+/// A fd pointing to the original stdout.
+void SetupRedirection(DAP &dap, int stdoutfd = -1, int stderrfd = -1) {
+  auto output_callback_stderr = [&dap](llvm::StringRef data) {
+dap.SendOutput(OutputType::Stderr, data);
+  };
+  auto output_callback_stdout = [&dap](llvm::StringRef data) {
+dap.SendOutput(OutputType::Stdout, data);
+  };
+
+  llvm::Expected new_stdout_fd =
+  RedirectFd(stdoutfd, output_callback_stdout);
+  if (auto err = new_stdout_fd.takeError()) {
+std::string error_message = llvm::toString(std::move(err));
+if (dap.log)
+  *dap.log << error_message << std::endl;
+output_callback_stderr(error_message);
+  }
+  dap.out = lldb::SBFile(new_stdout_fd.get(), "w", false);
+
+  llvm::Expected new_stderr_fd =
+  RedirectFd(stderrfd, output_callback_stderr);
+  if (auto err = new_stderr_fd.takeError()) {
+std::string error_message = llvm::toString(std::move(err));
+if (dap.log)
+  *dap.log << error_message << std::endl;
+output_callback_stderr(error_message);
+  }
+  dap.err = lldb::SBFile(new_stderr_fd.get(), "w", false);

vogelsgesang wrote:

in the `else` branch?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -116,6 +118,8 @@ enum LaunchMethod { Launch, Attach, 
AttachForSuspendedLaunch };
 /// Page size used for reporting addtional frames in the 'stackTrace' request.
 constexpr int StackPageSize = 20;
 
+void RegisterRequestCallbacks(DAP &dap);

vogelsgesang wrote:

seems to be never implemented and never called?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits

https://github.com/vogelsgesang edited 
https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -137,42 +141,232 @@ lldb::SBValueList *GetTopLevelScope(DAP &dap, int64_t 
variablesReference) {
   }
 }
 
-SOCKET AcceptConnection(DAP &dap, int portno) {
-  // Accept a socket connection from any host on "portno".
-  SOCKET newsockfd = -1;
-  struct sockaddr_in serv_addr, cli_addr;
+/// Redirect stdout and stderr fo the IDE's console output.
+///
+/// Errors in this operation will be printed to the log file and the IDE's
+/// console output as well.
+///
+/// \return
+/// A fd pointing to the original stdout.
+void SetupRedirection(DAP &dap, int stdoutfd = -1, int stderrfd = -1) {
+  auto output_callback_stderr = [&dap](llvm::StringRef data) {
+dap.SendOutput(OutputType::Stderr, data);
+  };
+  auto output_callback_stdout = [&dap](llvm::StringRef data) {
+dap.SendOutput(OutputType::Stdout, data);
+  };
+
+  llvm::Expected new_stdout_fd =
+  RedirectFd(stdoutfd, output_callback_stdout);
+  if (auto err = new_stdout_fd.takeError()) {
+std::string error_message = llvm::toString(std::move(err));
+if (dap.log)
+  *dap.log << error_message << std::endl;
+output_callback_stderr(error_message);
+  }
+  dap.out = lldb::SBFile(new_stdout_fd.get(), "w", false);

vogelsgesang wrote:

shouldn't this be in the `else` branch of `takeError`? What is the intended 
behavior here in case the redirection failed?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

github-actions[bot] wrote:




:warning: C/C++ code formatter, clang-format found issues in your code. 
:warning:



You can test this locally with the following command:


``bash
git-clang-format --diff 4d4024e1edf354113e8d0d11661d466ae5b0bee7 
943bad7a8faa41d21651de765858dbb49584547c --extensions cpp,h -- 
lldb/include/lldb/Target/ThreadPlanStack.h 
lldb/source/Target/ThreadPlanStack.cpp
``





View the diff from clang-format here.


``diff
diff --git a/lldb/include/lldb/Target/ThreadPlanStack.h 
b/lldb/include/lldb/Target/ThreadPlanStack.h
index cd606bd0bb..e0f8104de9 100644
--- a/lldb/include/lldb/Target/ThreadPlanStack.h
+++ b/lldb/include/lldb/Target/ThreadPlanStack.h
@@ -98,12 +98,12 @@ public:
   void ClearThreadCache();
 
 private:
-
   lldb::ThreadPlanSP DiscardPlanNoLock();
   lldb::ThreadPlanSP GetCurrentPlanNoLock() const;
   void PrintOneStackNoLock(Stream &s, llvm::StringRef stack_name,
- const PlanStack &stack, lldb::DescriptionLevel desc_level,
- bool include_internal) const;
+   const PlanStack &stack,
+   lldb::DescriptionLevel desc_level,
+   bool include_internal) const;
 
   PlanStack m_plans;   ///< The stack of plans this thread is 
executing.
   PlanStack m_completed_plans; ///< Plans that have been completed by this
diff --git a/lldb/source/Target/ThreadPlanStack.cpp 
b/lldb/source/Target/ThreadPlanStack.cpp
index 81fcb09b56..93a3d41142 100644
--- a/lldb/source/Target/ThreadPlanStack.cpp
+++ b/lldb/source/Target/ThreadPlanStack.cpp
@@ -41,18 +41,19 @@ void ThreadPlanStack::DumpThreadPlans(Stream &s,
   bool include_internal) const {
   llvm::sys::ScopedReader guard(m_stack_mutex);
   s.IndentMore();
-  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level, 
include_internal);
+  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level,
+  include_internal);
   PrintOneStackNoLock(s, "Completed plan stack", m_completed_plans, desc_level,
-include_internal);
+  include_internal);
   PrintOneStackNoLock(s, "Discarded plan stack", m_discarded_plans, desc_level,
-include_internal);
+  include_internal);
   s.IndentLess();
 }
 
 void ThreadPlanStack::PrintOneStackNoLock(Stream &s, llvm::StringRef 
stack_name,
-const PlanStack &stack,
-lldb::DescriptionLevel desc_level,
-bool include_internal) const {
+  const PlanStack &stack,
+  lldb::DescriptionLevel desc_level,
+  bool include_internal) const {
   // If the stack is empty, just exit:
   if (stack.empty())
 return;

``




https://github.com/llvm/llvm-project/pull/116438
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

jimingham wrote:

That is a "resource deadlock detected" error, so presumably we are managing to 
recursively use this ThreadPlanStack lock.  I'm a bit confused that none of the 
stacks printed actually show any ThreadPlanStack functions on the stack???

https://github.com/llvm/llvm-project/pull/116438
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Fix regex support in SBTarget.modules_access (PR #116452)

2024-11-15 Thread Dave Lee via lldb-commits

https://github.com/kastiglione edited 
https://github.com/llvm/llvm-project/pull/116452
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Convert file address to load address when reading memory for DW_OP_piece (PR #116411)

2024-11-15 Thread Adrian Prantl via lldb-commits

https://github.com/adrian-prantl approved this pull request.

This looks plausible. I wish we had just one place where we read from an 
address so this logic isn't duplicated all over the interpreter.

https://github.com/llvm/llvm-project/pull/116411
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits


@@ -179,55 +142,34 @@ Status MainLoopPosix::RunImpl::Poll() {
 read_fds.push_back(pfd);
   }
 
-  if (ppoll(read_fds.data(), read_fds.size(), nullptr, &sigmask) == -1 &&
+  if (ppoll(read_fds.data(), read_fds.size(),
+/*timeout=*/nullptr,

labath wrote:

I don't see what that would solve. The goal is to sleep until one of the FDs is 
readable. If none of them is, the only thing we can do is go back to sleep. 
Sure, we can have a bug where we e.g. somehow fail to notify the pipe about a 
signal, but that can also happen with a spurious wakeup (cause then you have to 
check if the signal really occurred, and maybe the bug is that you forgot to 
set that flag).

FWIW, there will be a timeout here after #112895 (but there is still the 
possibility of an infinite wait if/when there are no scheduled callbacks).

https://github.com/llvm/llvm-project/pull/115197
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits


@@ -384,6 +313,21 @@ void 
MainLoopPosix::ProcessReadObject(IOObject::WaitableHandle handle) {
 it->second(*this); // Do the work
 }
 
+void MainLoopPosix::ProcessSignals() {
+  std::vector signals;

labath wrote:

It's the type that the OS signal APIs use. I think it's best to stick with that 
even though the values would technically fit into a `uint8_t`.

https://github.com/llvm/llvm-project/pull/115197
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Handle an empty SBMemoryRegionInfo from scripted process (PR #115963)

2024-11-15 Thread Jason Molenda via lldb-commits

https://github.com/jasonmolenda updated 
https://github.com/llvm/llvm-project/pull/115963

>From f8f1d70d1d9eac6d36c0fa84e2a94c032385da39 Mon Sep 17 00:00:00 2001
From: Jason Molenda 
Date: Tue, 12 Nov 2024 15:55:15 -0800
Subject: [PATCH 1/6] [lldb] Handle an empty SBMemoryRegionInfo from scripted
 process

A scripted process implementation might return an SBMemoryRegionInfo
object in its implementation of `get_memory_region_containing_address`
which will have an address 0 and size 0, without realizing the
problems this can cause.  One problem happens when an expression
is run, and lldb needs to find part of the target's virtual address
space to store the result (actually stored in lldb's host memory),
it uses IRMemoryMap::FindSpace() to do that.  If the process supports
GetMemoryRegionInfo, FindSpace will step through the allocated
memory ranges looking for an unused one.  But if every request is
a memory region with address 0 + size 0, this loop will never
terminate.  Detect this kind of response from a scripted process
plugin and return an error, so callers iterating over the address
space can exit.

Added a test where I copied dummy_scripted_process.py from the
TestScriptedProcess.py existing test, and added a bad
`get_memory_region_containing_address` implementation.

rdar://139678032
---
 .../Process/scripted/ScriptedProcess.cpp  |   9 +-
 .../Makefile  |   3 +
 .../TestScriptedProcessEmptyMemoryRegion.py   |  33 +
 .../dummy_scripted_process.py | 137 ++
 .../main.c|   1 +
 5 files changed, 182 insertions(+), 1 deletion(-)
 create mode 100644 
lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile
 create mode 100644 
lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
 create mode 100644 
lldb/test/API/functionalities/scripted_process_empty_memory_region/dummy_scripted_process.py
 create mode 100644 
lldb/test/API/functionalities/scripted_process_empty_memory_region/main.c

diff --git a/lldb/source/Plugins/Process/scripted/ScriptedProcess.cpp 
b/lldb/source/Plugins/Process/scripted/ScriptedProcess.cpp
index d2111ce877ce55..c56e24a4ebd188 100644
--- a/lldb/source/Plugins/Process/scripted/ScriptedProcess.cpp
+++ b/lldb/source/Plugins/Process/scripted/ScriptedProcess.cpp
@@ -288,8 +288,15 @@ Status ScriptedProcess::DoGetMemoryRegionInfo(lldb::addr_t 
load_addr,
   MemoryRegionInfo ®ion) {
   Status error;
   if (auto region_or_err =
-  GetInterface().GetMemoryRegionContainingAddress(load_addr, error))
+  GetInterface().GetMemoryRegionContainingAddress(load_addr, error)) {
 region = *region_or_err;
+if (region.GetRange().GetRangeBase() == 0 &&
+(region.GetRange().GetByteSize() == 0 ||
+ region.GetRange().GetByteSize() == LLDB_INVALID_ADDRESS)) {
+  error = Status::FromErrorString(
+  "Invalid memory region from scripted process");
+}
+  }
 
   return error;
 }
diff --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile
new file mode 100644
index 00..10495940055b63
--- /dev/null
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/Makefile
@@ -0,0 +1,3 @@
+C_SOURCES := main.c
+
+include Makefile.rules
diff --git 
a/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
new file mode 100644
index 00..1ff084cfb0278e
--- /dev/null
+++ 
b/lldb/test/API/functionalities/scripted_process_empty_memory_region/TestScriptedProcessEmptyMemoryRegion.py
@@ -0,0 +1,33 @@
+"""
+Test python scripted process which returns an empty SBMemoryRegionInfo
+"""
+
+import os, shutil
+
+import lldb
+from lldbsuite.test.decorators import *
+from lldbsuite.test.lldbtest import *
+from lldbsuite.test import lldbutil
+from lldbsuite.test import lldbtest
+
+
+class ScriptedProcessEmptyMemoryRegion(TestBase):
+NO_DEBUG_INFO_TESTCASE = True
+
+def test_scripted_process_empty_memory_region(self):
+"""Test that lldb handles an empty SBMemoryRegionInfo object from
+a scripted process plugin."""
+self.build()
+
+target = self.dbg.CreateTarget(self.getBuildArtifact("a.out"))
+self.assertTrue(target, VALID_TARGET)
+
+scripted_process_example_relpath = "dummy_scripted_process.py"
+self.runCmd(
+"command script import "
++ os.path.join(self.getSourceDir(), 
scripted_process_example_relpath)
+)
+
+self.expect("memory region 0", error=True, substrs=["Invalid memory 
region"])
+
+self.expect("expr -- 5", substrs=["5"])
diff --git 
a/lldb/test/API/f

[Lldb-commits] [lldb] 10b048c - [lldb] Make CompilerDecl::GetName (always) return template args (#116068)

2024-11-15 Thread via lldb-commits

Author: Pavel Labath
Date: 2024-11-15T12:24:12+01:00
New Revision: 10b048c8922d746b14e991f468e00b3ca67c9d95

URL: 
https://github.com/llvm/llvm-project/commit/10b048c8922d746b14e991f468e00b3ca67c9d95
DIFF: 
https://github.com/llvm/llvm-project/commit/10b048c8922d746b14e991f468e00b3ca67c9d95.diff

LOG: [lldb] Make CompilerDecl::GetName (always) return template args (#116068)

I ran into this while look at a different bug (patch coming soon). This
function has only two callers. The first is SBTypeStaticField::GetName
(which doesn't care about templates), and the other is
CompilerDecl::GetCompilerContext (in the TypeQuery constructor), which
does want template arguments.

This function was (normally) returning the name without template args.
Since this code is only used when looking up a type in another shared
library, the odds of running into this bug are relatively low, but I add
a test to demonstrate the scenario and the fix for it nonetheless.

Amazingly (and scarily), this test actually passes without this change
in the default configuration -- and only fails with
-gsimple-template-names. The reason for that is that in the
non-simplified case we create a regular CXXRecordDecl whose name is
"bar" (instead of a template record "foo" with an argument of
"int"). When evaluating the expression, we are somehow able to replace
this with a proper template specialization decl.

Added: 
lldb/test/API/lang/cpp/forward/Makefile
lldb/test/API/lang/cpp/forward/TestCPPForwardDeclaration.py
lldb/test/API/lang/cpp/forward/foo.cpp
lldb/test/API/lang/cpp/forward/foo.h
lldb/test/API/lang/cpp/forward/main.cpp

Modified: 
lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp

Removed: 




diff  --git a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp 
b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp
index f5063175d6e070..c5249088a291b8 100644
--- a/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp
+++ b/lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp
@@ -9116,7 +9116,7 @@ ConstString TypeSystemClang::DeclGetName(void 
*opaque_decl) {
 clang::NamedDecl *nd =
 llvm::dyn_cast((clang::Decl *)opaque_decl);
 if (nd != nullptr)
-  return ConstString(nd->getDeclName().getAsString());
+  return ConstString(GetTypeNameForDecl(nd, /*qualified=*/false));
   }
   return ConstString();
 }

diff  --git a/lldb/test/API/lang/cpp/forward/Makefile 
b/lldb/test/API/lang/cpp/forward/Makefile
new file mode 100644
index 00..0b806b314397c5
--- /dev/null
+++ b/lldb/test/API/lang/cpp/forward/Makefile
@@ -0,0 +1,5 @@
+CXX_SOURCES := main.cpp
+DYLIB_CXX_SOURCES := foo.cpp
+DYLIB_NAME := foo
+
+include Makefile.rules

diff  --git a/lldb/test/API/lang/cpp/forward/TestCPPForwardDeclaration.py 
b/lldb/test/API/lang/cpp/forward/TestCPPForwardDeclaration.py
new file mode 100644
index 00..5e9dd9c2227dd5
--- /dev/null
+++ b/lldb/test/API/lang/cpp/forward/TestCPPForwardDeclaration.py
@@ -0,0 +1,61 @@
+"""Test that forward declaration of a c++ template gets resolved correctly."""
+
+import lldb
+from lldbsuite.test.lldbtest import *
+from lldbsuite.test.decorators import *
+import lldbsuite.test.lldbutil as lldbutil
+
+
+class ForwardDeclarationTestCase(TestBase):
+def do_test(self, dictionary=None):
+"""Display *bar_ptr when stopped on a function with forward 
declaration of struct bar."""
+self.build(dictionary=dictionary)
+exe = self.getBuildArtifact("a.out")
+target = self.dbg.CreateTarget(exe)
+self.assertTrue(target, VALID_TARGET)
+
+environment = self.registerSharedLibrariesWithTarget(target, ["foo"])
+
+# Break inside the foo function which takes a bar_ptr argument.
+lldbutil.run_break_set_by_symbol(self, "foo", num_expected_locations=1)
+
+process = target.LaunchSimple(
+None, environment, self.get_process_working_directory()
+)
+self.assertTrue(process, PROCESS_IS_VALID)
+
+# The stop reason of the thread should be breakpoint.
+self.expect(
+"thread list",
+STOPPED_DUE_TO_BREAKPOINT,
+substrs=["stopped", "stop reason = breakpoint"],
+)
+
+# The breakpoint should have a hit count of 1.
+lldbutil.check_breakpoint(self, bpno=1, expected_hit_count=1)
+
+self.expect_expr(
+"*bar_ptr",
+result_type="bar",
+result_children=[ValueCheck(value="47", name="a", type="int")],
+)
+
+def test(self):
+self.do_test()
+
+@no_debug_info_test
+@skipIfDarwin
+@skipIf(compiler=no_match("clang"))
+@skipIf(compiler_version=["<", "8.0"])
+@expectedFailureAll(oslist=["windows"])
+def test_debug_names(self):
+"""Test that we are able to find complete types when using DWARF v5
+accelerator tables"""
+se

[Lldb-commits] [lldb] [lldb] Make CompilerDecl::GetName (always) return template args (PR #116068)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath closed 
https://github.com/llvm/llvm-project/pull/116068
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits

labath wrote:

> I'm not expert, but everything looks rigorous and you've added a lot of 
> comments.
> 
> I left a few nits and a singular question. I would encourage comments on some 
> file descriptors for the less knowledgeable of us (namely me!)

That you for the review. Making sure the code is understandable to the 
uninitiated is an important part of it.

https://github.com/llvm/llvm-project/pull/115197
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath commented:

Do you actually need to parse the headers yourself? The reason for using the 
llvm implementation was so that we can avoid that. FWICS, all of this data 
should be available through the `(file|auxiliary)Header(32|64)` APIs.

BTW, this is exactly the kind of granularity I was looking for.

https://github.com/llvm/llvm-project/pull/116338
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] rm DWARFDebugRanges (PR #116379)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath created 
https://github.com/llvm/llvm-project/pull/116379

The class is only used from one place, which is trivial to implement using the 
llvm class.

The main difference is that in the new implementation, the ranges are parsed 
each time anew (instead of being parsed at startup and cached). I believe this 
is fine because:
- this is already how things work with DWARF v5 debug_rnglists
- parsing debug_ranges is fairly fast (definitely faster than rnglists)
- generally, this result will be cached at a higher level anyway. Browsing the 
code I did find one instance where that is not the case -- 
SymbolFileDWARF::ResolveFunctionAndBlock -- which is called each time we 
resolve an address (to the block level). However, this function is already 
pretty suboptimal: it first traverses the DIE tree (which involves parsing all 
the DIE attributes) to find the correct block, then it parses them again to 
construct the `lldb_private::Block` representation, and *then* it uses the ID 
of the block DIE it found in the first step to look up the `Block` object. If 
this turns out to be a bottleneck, I think there are better ways to optimize it 
than caching the debug_ranges parse.

The motiviation for this is that DWARFDebugRanges sorts the block ranges, even 
though the order of the ranges is load-bearing (in the absence of DW_AT_low_pc, 
the "base address" of a scope is determined by the first range entry). Delaying 
the parsing (and sorting) step makes it easier to access the first entry.

>From 64053f9e0549cf5401d2a4e82a1fd3822031346e Mon Sep 17 00:00:00 2001
From: Pavel Labath 
Date: Fri, 15 Nov 2024 12:55:17 +0100
Subject: [PATCH] [lldb] rm DWARFDebugRanges

The class is only used from one place, which is trivial to implement
using the llvm class.

The main difference is that in the new implementation, the ranges are
parsed each time anew (instead of being parsed at startup and cached). I
believe this is fine because:
- this is already how things work with DWARF v5 debug_rnglists
- parsing debug_ranges is fairly fast (definitely faster than rnglists)
- generally, this result will be cached at a higher level anyway.
  Browsing the code I did find one instance where that is not the case
  -- SymbolFileDWARF::ResolveFunctionAndBlock -- which is called each
  time we resolve an address (to the block level). However, this
  function is already pretty suboptimal: it first traverses the DIE tree
  (which involves parsing all the DIE attributes) to find the correct
  block, then it parses them again to construct the
  `lldb_private::Block` representation, and *then* it uses the ID of the
  block DIE it found in the first step to look up the `Block` object. If
  this turns out to be a bottleneck, I think there are better ways to
  optimize it than caching the debug_ranges parse.

The motiviation for this is that DWARFDebugRanges sorts the block
ranges, even though the order of the ranges is load-bearing (in the
absence of DW_AT_low_pc, the "base address" of a scope is determined by
the first range entry). Delaying the parsing (and sorting) step makes it
easier to access the first entry.
---
 .../Plugins/SymbolFile/DWARF/CMakeLists.txt   |  1 -
 .../SymbolFile/DWARF/DWARFDebugInfoEntry.cpp  |  1 -
 .../SymbolFile/DWARF/DWARFDebugInfoEntry.h|  1 -
 .../SymbolFile/DWARF/DWARFDebugRanges.cpp | 56 --
 .../SymbolFile/DWARF/DWARFDebugRanges.h   | 34 -
 .../Plugins/SymbolFile/DWARF/DWARFUnit.cpp| 74 ++-
 .../SymbolFile/DWARF/SymbolFileDWARF.cpp  | 14 
 .../SymbolFile/DWARF/SymbolFileDWARF.h|  4 -
 .../DWARF/x86/debug_ranges-missing-section.s  |  2 +-
 9 files changed, 42 insertions(+), 145 deletions(-)
 delete mode 100644 lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
 delete mode 100644 lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h

diff --git a/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt 
b/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
index ea644a61b1bdaa..e87194dfe74cb3 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
+++ b/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
@@ -21,7 +21,6 @@ add_lldb_library(lldbPluginSymbolFileDWARF PLUGIN
   DWARFDebugInfo.cpp
   DWARFDebugInfoEntry.cpp
   DWARFDebugMacro.cpp
-  DWARFDebugRanges.cpp
   DWARFDeclContext.cpp
   DWARFDefines.cpp
   DWARFDIE.cpp
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp 
b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
index c0a2066f8239e5..4ecb2ed616a128 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
@@ -25,7 +25,6 @@
 #include "DWARFCompileUnit.h"
 #include "DWARFDebugAranges.h"
 #include "DWARFDebugInfo.h"
-#include "DWARFDebugRanges.h"
 #include "DWARFDeclContext.h"
 #include "DWARFFormValue.h"
 #include "DWARFUnit.h"
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebug

[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath updated 
https://github.com/llvm/llvm-project/pull/115197

>From 2627a1fc1c0722c72793a3f3e4e9520a65897c20 Mon Sep 17 00:00:00 2001
From: Pavel Labath 
Date: Tue, 29 Oct 2024 16:56:40 +0100
Subject: [PATCH 1/2] [lldb] Unify/improve MainLoop signal handling

Change the signal handler to use a pipe to notify about incoming
signals. This has two benefits:
- the signal no longer has to happen on the MainLoop thread. With the
  previous implementation, this had to be the case as that was the only
  way to ensure that ppoll gets interrupted correctly. In a
  multithreaded process, this would mean that all other threads have
  to have the signal blocked at all times.
- we don't need the android-specific workaround, which was necessary due
  to the syscall being implemented in a non-atomic way

When the MainLoop class was first implemented, we did not have the
interrupt self-pipe, so syscall interruption was the most
straight-forward implementation. Over time, the class gained new
abilities (the pipe being one of them), so we can now piggy-back on
those.

This patch also changes the kevent-based implementation to use the pipe
for signal notification as well. The motivation there is slightly
different:
- it makes the implementations more uniform
- it makes sure we handle all kinds of signals, like we do with the
  linux version (EVFILT_SIGNAL only catches process-directed signals)
---
 lldb/include/lldb/Host/posix/MainLoopPosix.h |   1 +
 lldb/source/Host/posix/MainLoopPosix.cpp | 182 +++
 lldb/unittests/Host/MainLoopTest.cpp |  11 ++
 3 files changed, 75 insertions(+), 119 deletions(-)

diff --git a/lldb/include/lldb/Host/posix/MainLoopPosix.h 
b/lldb/include/lldb/Host/posix/MainLoopPosix.h
index 07497b7b8c259a..1988dde7c65aee 100644
--- a/lldb/include/lldb/Host/posix/MainLoopPosix.h
+++ b/lldb/include/lldb/Host/posix/MainLoopPosix.h
@@ -59,6 +59,7 @@ class MainLoopPosix : public MainLoopBase {
 private:
   void ProcessReadObject(IOObject::WaitableHandle handle);
   void ProcessSignal(int signo);
+  void ProcessSignals();
 
   class SignalHandle {
   public:
diff --git a/lldb/source/Host/posix/MainLoopPosix.cpp 
b/lldb/source/Host/posix/MainLoopPosix.cpp
index 6f8eaa55cfdf09..34c937f8a05d6c 100644
--- a/lldb/source/Host/posix/MainLoopPosix.cpp
+++ b/lldb/source/Host/posix/MainLoopPosix.cpp
@@ -17,17 +17,14 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 
 // Multiplexing is implemented using kqueue on systems that support it (BSD
-// variants including OSX). On linux we use ppoll, while android uses pselect
-// (ppoll is present but not implemented properly). On windows we use WSApoll
-// (which does not support signals).
+// variants including OSX). On linux we use ppoll.
 
 #if HAVE_SYS_EVENT_H
 #include 
-#elif defined(__ANDROID__)
-#include 
 #else
 #include 
 #endif
@@ -35,11 +32,38 @@
 using namespace lldb;
 using namespace lldb_private;
 
-static sig_atomic_t g_signal_flags[NSIG];
+namespace {
+struct GlobalSignalInfo {
+  sig_atomic_t pipe_fd = -1;
+  static_assert(sizeof(sig_atomic_t) >= sizeof(int),
+"Type too small for a file descriptor");
+  sig_atomic_t flag = 0;
+};
+} // namespace
+static GlobalSignalInfo g_signal_info[NSIG];
 
 static void SignalHandler(int signo, siginfo_t *info, void *) {
   assert(signo < NSIG);
-  g_signal_flags[signo] = 1;
+
+  // Set the flag before writing to the pipe!
+  g_signal_info[signo].flag = 1;
+
+  char c = '.';
+  int fd = g_signal_info[signo].pipe_fd;
+  if (fd < 0) {
+// This can happen with the following (unlikely) sequence of events:
+// 1. Thread 1 gets a signal, starts running the signal handler
+// 2. Thread 2 unregisters the signal handler, setting pipe_fd to -1
+// 3. Signal handler on thread 1 reads -1 out of pipe_fd
+// In this case, we can just ignore the signal because we're no longer
+// interested in it.
+return;
+  }
+
+  ssize_t bytes_written = llvm::sys::RetryAfterSignal(-1, ::write, fd, &c, 1);
+  // We're only using the pipe to wake up the reader, so we can safely ignore
+  // EAGAIN (pipe full)
+  assert(bytes_written == 1 || (bytes_written == -1 && errno == EAGAIN));
 }
 
 class MainLoopPosix::RunImpl {
@@ -48,7 +72,7 @@ class MainLoopPosix::RunImpl {
   ~RunImpl() = default;
 
   Status Poll();
-  void ProcessEvents();
+  void ProcessReadEvents();
 
 private:
   MainLoopPosix &loop;
@@ -58,15 +82,9 @@ class MainLoopPosix::RunImpl {
   struct kevent out_events[4];
   int num_events = -1;
 
-#else
-#ifdef __ANDROID__
-  fd_set read_fd_set;
 #else
   std::vector read_fds;
 #endif
-
-  sigset_t get_sigmask();
-#endif
 };
 
 #if HAVE_SYS_EVENT_H
@@ -94,7 +112,7 @@ Status MainLoopPosix::RunImpl::Poll() {
   return Status();
 }
 
-void MainLoopPosix::RunImpl::ProcessEvents() {
+void MainLoopPosix::RunImpl::ProcessReadEvents() {
   assert(num_events >= 0);
   for (int i = 0; i < num_events; ++i) {
 if (loop.m_terminate_request)
@@ -103,9 +

[Lldb-commits] [lldb] [lldb] Handle an empty SBMemoryRegionInfo from scripted process (PR #115963)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath commented:

Thanks Jason. Looks good. (I think the arm failure is due to it being a 32-bit 
machine. Maybe it would be sufficient to use 32-bit values everywhere?)

https://github.com/llvm/llvm-project/pull/115963
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits


@@ -179,55 +142,34 @@ Status MainLoopPosix::RunImpl::Poll() {
 read_fds.push_back(pfd);
   }
 
-  if (ppoll(read_fds.data(), read_fds.size(), nullptr, &sigmask) == -1 &&
+  if (ppoll(read_fds.data(), read_fds.size(),
+/*timeout=*/nullptr,
+/*sigmask=*/nullptr) == -1 &&
   errno != EINTR)
 return Status(errno, eErrorTypePOSIX);
 
   return Status();
 }
-#endif
 
-void MainLoopPosix::RunImpl::ProcessEvents() {
-#ifdef __ANDROID__
-  // Collect first all readable file descriptors into a separate vector and
-  // then iterate over it to invoke callbacks. Iterating directly over
-  // loop.m_read_fds is not possible because the callbacks can modify the
-  // container which could invalidate the iterator.
-  std::vector fds;
-  for (const auto &fd : loop.m_read_fds)
-if (FD_ISSET(fd.first, &read_fd_set))
-  fds.push_back(fd.first);
-
-  for (const auto &handle : fds) {
-#else
+void MainLoopPosix::RunImpl::ProcessReadEvents() {
   for (const auto &fd : read_fds) {
 if ((fd.revents & (POLLIN | POLLHUP)) == 0)
   continue;
 IOObject::WaitableHandle handle = fd.fd;
-#endif
 if (loop.m_terminate_request)
   return;
 
 loop.ProcessReadObject(handle);
   }
-
-  std::vector signals;
-  for (const auto &entry : loop.m_signals)
-if (g_signal_flags[entry.first] != 0)
-  signals.push_back(entry.first);
-
-  for (const auto &signal : signals) {
-if (loop.m_terminate_request)
-  return;
-g_signal_flags[signal] = 0;
-loop.ProcessSignal(signal);
-  }
 }
 #endif
 
 MainLoopPosix::MainLoopPosix() : m_triggering(false) {
   Status error = m_trigger_pipe.CreateNew(/*child_process_inherit=*/false);
   assert(error.Success());
+  assert(fcntl(m_trigger_pipe.GetWriteFileDescriptor(), F_SETFL,

labath wrote:

I'm setting the *flags* on the descriptor. This is essentially `fd->flags |= 
O_NONBLOCK`. I added a comment and fixed the embarrassing mistake of putting a 
load-bearing statement into an assert block.

https://github.com/llvm/llvm-project/pull/115197
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactor lldb-dap.cpp to not use global DAP variable. (PR #116272)

2024-11-15 Thread Pavel Labath via lldb-commits


@@ -5046,30 +5026,48 @@ int main(int argc, char *argv[]) {
 pause();
   }
 #endif
+
+  // Initialize LLDB first before we do anything.
+  lldb::SBDebugger::Initialize();
+
+  // Terminate the debugger before the C++ destructor chain kicks in.
+  auto terminate_debugger =
+  llvm::make_scope_exit([] { lldb::SBDebugger::Terminate(); });
+
+  DAP dap = DAP(program_path.str(), default_repl_mode);

labath wrote:

Should the dap object be copyable? Given that things hold references to it, 
maybe the copy operations should be deleted (and this object constructed in 
place) ?

https://github.com/llvm/llvm-project/pull/116272
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][test] Add test categories for Linux and Darwin tests (PR #116194)

2024-11-15 Thread Vladislav Dzhidzhoev via lldb-commits

https://github.com/dzhidzhoev updated 
https://github.com/llvm/llvm-project/pull/116194

>From 34047d525f1caeda6817142ec0d53ec8129a6adb Mon Sep 17 00:00:00 2001
From: Vladislav Dzhidzhoev 
Date: Thu, 14 Nov 2024 10:21:36 +0100
Subject: [PATCH 1/2] [lldb][test] Add test categories for Linux and Darwin
 tests

Label Linux and Darwin tests with the corresponding categories so that
buildbots could be set up to skip them.

This is to speed up https://lab.llvm.org/staging/#/builders/195/builds/4739 
later.
---
 lldb/packages/Python/lldbsuite/test/test_categories.py | 3 +++
 lldb/test/API/linux/categories | 1 +
 lldb/test/API/macosx/categories| 1 +
 3 files changed, 5 insertions(+)
 create mode 100644 lldb/test/API/linux/categories
 create mode 100644 lldb/test/API/macosx/categories

diff --git a/lldb/packages/Python/lldbsuite/test/test_categories.py 
b/lldb/packages/Python/lldbsuite/test/test_categories.py
index 036bda9c957d11..537a7aa4025d5c 100644
--- a/lldb/packages/Python/lldbsuite/test/test_categories.py
+++ b/lldb/packages/Python/lldbsuite/test/test_categories.py
@@ -17,6 +17,7 @@
 all_categories = {
 "basic_process": "Basic process execution sniff tests.",
 "cmdline": "Tests related to the LLDB command-line interface",
+"darwin": "Darwin-related tests",
 "dataformatters": "Tests related to the type command and the data 
formatters subsystem",
 "debugserver": "Debugserver tests",
 "dsym": "Tests that can be run with DSYM debug information",
@@ -30,6 +31,7 @@
 "instrumentation-runtime": "Tests for the instrumentation runtime plugins",
 "libc++": "Test for libc++ data formatters",
 "libstdcxx": "Test for libstdcxx data formatters",
+"linux": "Linux-related tests",
 "lldb-server": "Tests related to lldb-server",
 "lldb-dap": "Tests for the Debug Adaptor Protocol with lldb-dap",
 "llgs": "Tests for the gdb-server functionality of lldb-server",
@@ -39,6 +41,7 @@
 "std-module": "Tests related to importing the std module",
 "stresstest": "Tests related to stressing lldb limits",
 "watchpoint": "Watchpoint-related tests",
+"windows": "Windows-related tests",
 }
 
 
diff --git a/lldb/test/API/linux/categories b/lldb/test/API/linux/categories
new file mode 100644
index 00..a08e1f35eb7c51
--- /dev/null
+++ b/lldb/test/API/linux/categories
@@ -0,0 +1 @@
+linux
diff --git a/lldb/test/API/macosx/categories b/lldb/test/API/macosx/categories
new file mode 100644
index 00..1498f270fc2b31
--- /dev/null
+++ b/lldb/test/API/macosx/categories
@@ -0,0 +1 @@
+darwin

>From 561798c1a2eddb43b9d559a08bfcd0d38324bee3 Mon Sep 17 00:00:00 2001
From: Vladislav Dzhidzhoev 
Date: Fri, 15 Nov 2024 14:24:30 +0100
Subject: [PATCH 2/2] Removed "windows" decorator

---
 lldb/packages/Python/lldbsuite/test/test_categories.py | 1 -
 1 file changed, 1 deletion(-)

diff --git a/lldb/packages/Python/lldbsuite/test/test_categories.py 
b/lldb/packages/Python/lldbsuite/test/test_categories.py
index 537a7aa4025d5c..a376f110262dd6 100644
--- a/lldb/packages/Python/lldbsuite/test/test_categories.py
+++ b/lldb/packages/Python/lldbsuite/test/test_categories.py
@@ -41,7 +41,6 @@
 "std-module": "Tests related to importing the std module",
 "stresstest": "Tests related to stressing lldb limits",
 "watchpoint": "Watchpoint-related tests",
-"windows": "Windows-related tests",
 }
 
 

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] e0b76ba - [lldb][test] Disable inline_sites_live.cpp for non-Windows targets (#116196)

2024-11-15 Thread via lldb-commits

Author: Vladislav Dzhidzhoev
Date: 2024-11-15T14:15:29+01:00
New Revision: e0b76bafde197c4813aa52dbcfeaf6bd1f9d96da

URL: 
https://github.com/llvm/llvm-project/commit/e0b76bafde197c4813aa52dbcfeaf6bd1f9d96da
DIFF: 
https://github.com/llvm/llvm-project/commit/e0b76bafde197c4813aa52dbcfeaf6bd1f9d96da.diff

LOG: [lldb][test] Disable inline_sites_live.cpp for non-Windows targets 
(#116196)

This is a follow-up for the conversation here
https://github.com/llvm/llvm-project/pull/115722/.

This test is designed for Windows target/PDB format, so it shouldn't be
built and run for DWARF/etc.

Added: 


Modified: 
lldb/test/Shell/SymbolFile/NativePDB/inline_sites_live.cpp

Removed: 




diff  --git a/lldb/test/Shell/SymbolFile/NativePDB/inline_sites_live.cpp 
b/lldb/test/Shell/SymbolFile/NativePDB/inline_sites_live.cpp
index 549bc881b19bb7..906f3d7dff0a56 100644
--- a/lldb/test/Shell/SymbolFile/NativePDB/inline_sites_live.cpp
+++ b/lldb/test/Shell/SymbolFile/NativePDB/inline_sites_live.cpp
@@ -1,5 +1,5 @@
 // clang-format off
-// REQUIRES: system-windows
+// REQUIRES: target-windows
 
 // RUN: %build -o %t.exe -- %s
 // RUN: %lldb -f %t.exe -s \



___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][test] Add test categories for Linux and Darwin tests (PR #116194)

2024-11-15 Thread Vladislav Dzhidzhoev via lldb-commits

dzhidzhoev wrote:

> Is the real, underlying problem that `skipUnlessDarwin` is checking the host 
> platform instead of the target platform? I'm somewhat worried about adding a 
> category that (at first glance) competes with the existing decorators and the 
> associated risk of folks misunderstanding/misusing them.

No, regarding "darwin", it's about these tests from here 
https://lab.llvm.org/staging/#/builders/197/builds/363/steps/17/logs/stdio
```
PASS: lldb-api :: macosx/load-kext/TestLoadKext.py (995 of 1211)
PASS: lldb-api :: macosx/duplicate-archive-members/TestDuplicateMembers.py (996 
of 1211)
PASS: lldb-api :: macosx/version_zero/TestGetVersionZeroVersion.py (1017 of 
1211)
```
There are no decorators in them.

> I'm somewhat worried about adding a category that (at first glance) competes 
> with the existing decorators and the associated risk of folks 
> misunderstanding/misusing them.

I agree with that. Maybe they should be renamed somehow to emphasize that it's 
for builbot purposes, not for failing/unsupported tests? Like `macosx-oriented`?

https://github.com/llvm/llvm-project/pull/116194
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Unify/improve MainLoop signal handling (PR #115197)

2024-11-15 Thread Pavel Labath via lldb-commits


@@ -17,29 +17,53 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 
 // Multiplexing is implemented using kqueue on systems that support it (BSD
-// variants including OSX). On linux we use ppoll, while android uses pselect
-// (ppoll is present but not implemented properly). On windows we use WSApoll
-// (which does not support signals).
+// variants including OSX). On linux we use ppoll.
 
 #if HAVE_SYS_EVENT_H
 #include 
-#elif defined(__ANDROID__)
-#include 
 #else
 #include 
 #endif
 
 using namespace lldb;
 using namespace lldb_private;
 
-static sig_atomic_t g_signal_flags[NSIG];
+namespace {
+struct GlobalSignalInfo {
+  sig_atomic_t pipe_fd = -1;
+  static_assert(sizeof(sig_atomic_t) >= sizeof(int),
+"Type too small for a file descriptor");
+  sig_atomic_t flag = 0;
+};
+} // namespace
+static GlobalSignalInfo g_signal_info[NSIG];
 
 static void SignalHandler(int signo, siginfo_t *info, void *) {
   assert(signo < NSIG);
-  g_signal_flags[signo] = 1;
+
+  // Set the flag before writing to the pipe!
+  g_signal_info[signo].flag = 1;
+
+  char c = '.';

labath wrote:

I added a comment about the intent. I think `c` is a good name for an entity 
with such a short scope. The choice of character is irrelevant -- we only need 
to write something to force `poll` to return.

https://github.com/llvm/llvm-project/pull/115197
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] fix: Target Process may crash or freezes on detaching process on windows (PR #115712)

2024-11-15 Thread Pavel Labath via lldb-commits

https://github.com/labath closed 
https://github.com/llvm/llvm-project/pull/115712
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] 5bbe63e - fix: Target Process may crash or freezes on detaching process on windows (#115712)

2024-11-15 Thread via lldb-commits

Author: anatawa12
Date: 2024-11-15T10:52:36+01:00
New Revision: 5bbe63ec91226c0026c6f1ed726c45bb117544e0

URL: 
https://github.com/llvm/llvm-project/commit/5bbe63ec91226c0026c6f1ed726c45bb117544e0
DIFF: 
https://github.com/llvm/llvm-project/commit/5bbe63ec91226c0026c6f1ed726c45bb117544e0.diff

LOG: fix: Target Process may crash or freezes on detaching process on windows 
(#115712)

Fixes #67825 Fixes #89077

Fixes
[RIDER-99436](https://youtrack.jetbrains.com/issue/RIDER-99436/Unity-Editor-will-be-crashed-when-detaching-LLDB-debugger-in-Rider),
which is upstream issue of #67825.

This PR changes the timing of calling `DebugActiveProcessStop` to after
calling `ContinueDebugEvent` for last debugger exception.

I confirmed the crashing behavior is because we call
`DebugActiveProcessStop` before `ContinueDebugEvent` for last debugger
exception with https://github.com/anatawa12/debug-api-test.

Added: 


Modified: 
lldb/source/Plugins/Process/Windows/Common/DebuggerThread.cpp
lldb/source/Plugins/Process/Windows/Common/DebuggerThread.h
lldb/source/Plugins/Process/Windows/Common/ProcessWindows.cpp
lldb/test/API/commands/process/detach-resumes/TestDetachResumes.py

Removed: 




diff  --git a/lldb/source/Plugins/Process/Windows/Common/DebuggerThread.cpp 
b/lldb/source/Plugins/Process/Windows/Common/DebuggerThread.cpp
index ca8e9c078e1f99..b637238007b882 100644
--- a/lldb/source/Plugins/Process/Windows/Common/DebuggerThread.cpp
+++ b/lldb/source/Plugins/Process/Windows/Common/DebuggerThread.cpp
@@ -239,12 +239,13 @@ void DebuggerThread::DebugLoop() {
 BOOL wait_result = WaitForDebugEvent(&dbe, INFINITE);
 if (wait_result) {
   DWORD continue_status = DBG_CONTINUE;
+  bool shutting_down = m_is_shutting_down;
   switch (dbe.dwDebugEventCode) {
   default:
 llvm_unreachable("Unhandle debug event code!");
   case EXCEPTION_DEBUG_EVENT: {
-ExceptionResult status =
-HandleExceptionEvent(dbe.u.Exception, dbe.dwThreadId);
+ExceptionResult status = HandleExceptionEvent(
+dbe.u.Exception, dbe.dwThreadId, shutting_down);
 
 if (status == ExceptionResult::MaskException)
   continue_status = DBG_CONTINUE;
@@ -292,6 +293,45 @@ void DebuggerThread::DebugLoop() {
 
   ::ContinueDebugEvent(dbe.dwProcessId, dbe.dwThreadId, continue_status);
 
+  // We have to DebugActiveProcessStop after ContinueDebugEvent, otherwise
+  // the target process will crash
+  if (shutting_down) {
+// A breakpoint that occurs while `m_pid_to_detach` is non-zero is a
+// magic exception that we use simply to wake up the DebuggerThread so
+// that we can close out the debug loop.
+if (m_pid_to_detach != 0 &&
+(dbe.u.Exception.ExceptionRecord.ExceptionCode ==
+ EXCEPTION_BREAKPOINT ||
+ dbe.u.Exception.ExceptionRecord.ExceptionCode ==
+ STATUS_WX86_BREAKPOINT)) {
+  LLDB_LOG(log,
+   "Breakpoint exception is cue to detach from process {0:x}",
+   m_pid_to_detach.load());
+
+  // detaching with leaving breakpoint exception event on the queue may
+  // cause target process to crash so process events as possible since
+  // target threads are running at this time, there is possibility to
+  // have some breakpoint exception between last WaitForDebugEvent and
+  // DebugActiveProcessStop but ignore for now.
+  while (WaitForDebugEvent(&dbe, 0)) {
+continue_status = DBG_CONTINUE;
+if (dbe.dwDebugEventCode == EXCEPTION_DEBUG_EVENT &&
+!(dbe.u.Exception.ExceptionRecord.ExceptionCode ==
+  EXCEPTION_BREAKPOINT ||
+  dbe.u.Exception.ExceptionRecord.ExceptionCode ==
+  STATUS_WX86_BREAKPOINT ||
+  dbe.u.Exception.ExceptionRecord.ExceptionCode ==
+  EXCEPTION_SINGLE_STEP))
+  continue_status = DBG_EXCEPTION_NOT_HANDLED;
+::ContinueDebugEvent(dbe.dwProcessId, dbe.dwThreadId,
+ continue_status);
+  }
+
+  ::DebugActiveProcessStop(m_pid_to_detach);
+  m_detached = true;
+}
+  }
+
   if (m_detached) {
 should_debug = false;
   }
@@ -310,25 +350,18 @@ void DebuggerThread::DebugLoop() {
 
 ExceptionResult
 DebuggerThread::HandleExceptionEvent(const EXCEPTION_DEBUG_INFO &info,
- DWORD thread_id) {
+ DWORD thread_id, bool shutting_down) {
   Log *log = GetLog(WindowsLog::Event | WindowsLog::Exception);
-  if (m_is_shutting_down) {
-// A breakpoint that occurs while `m_pid_to_detach` is non-zero is a magic
-// exception that
-// we use simply to wake up the DebuggerThread so tha

[Lldb-commits] [lldb] fix: Target Process may crash or freezes on detaching process on windows (PR #115712)

2024-11-15 Thread via lldb-commits

github-actions[bot] wrote:



@anatawa12 Congratulations on having your first Pull Request (PR) merged into 
the LLVM Project!

Your changes will be combined with recent changes from other authors, then 
tested by our [build bots](https://lab.llvm.org/buildbot/). If there is a 
problem with a build, you may receive a report in an email or a comment on this 
PR.

Please check whether problems have been caused by your change specifically, as 
the builds can include changes from many authors. It is not uncommon for your 
change to be included in a build that fails due to someone else's changes, or 
infrastructure issues.

How to do this, and the rest of the post-merge process, is covered in detail 
[here](https://llvm.org/docs/MyFirstTypoFix.html#myfirsttypofix-issues-after-landing-your-pr).

If your change does cause a problem, it may be reverted, or you can revert it 
yourself. This is a normal part of [LLVM 
development](https://llvm.org/docs/DeveloperPolicy.html#patch-reversion-policy).
 You can fix your changes and open a new PR to merge them again.

If you don't get any reports, no action is required from you. Your changes are 
working as expected, well done!


https://github.com/llvm/llvm-project/pull/115712
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread Pavel Labath via lldb-commits

labath wrote:

> Hi @labath , not sure why the `Labelling new pull requests` check failed. 
> Also, the build check didnt automatically start for this one.

I don't know, but I wouldn't be worried about that. The test failure is more of 
a concern.

https://github.com/llvm/llvm-project/pull/116338
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][test] Disable inline_sites_live.cpp for non-Windows targets (PR #116196)

2024-11-15 Thread Vladislav Dzhidzhoev via lldb-commits

https://github.com/dzhidzhoev closed 
https://github.com/llvm/llvm-project/pull/116196
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Add logging for missing `.dwo` files (PR #116436)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits

https://github.com/vogelsgesang created 
https://github.com/llvm/llvm-project/pull/116436

I had a hard time to debug a `dwo` file whose file was not found. This log 
message would have saved me a lot of time.

>From 042426896e517cf9e424279c2b25bbf655879a47 Mon Sep 17 00:00:00 2001
From: Adrian Vogelsgesang 
Date: Fri, 15 Nov 2024 20:13:15 +
Subject: [PATCH] [lldb] Add logging for missing `.dwo` files

I had a hard time to debug a `dwo` file whose file was not found. This log
message would have saved me a lot of time.
---
 lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp | 8 
 1 file changed, 8 insertions(+)

diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp 
b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
index 666595a6d0635f..2bb41903beb3b4 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
@@ -1963,6 +1963,14 @@ SymbolFileDWARF::GetDwoSymbolFileForCompileUnit(
 "{1:x16}",
 error_dwo_path.GetPath().c_str(), cu_die.GetOffset()));
 
+if (Log *log = GetLog(LLDBLog::Symbols)) {
+  GetObjectFile()->GetModule()->LogMessage(
+  log,
+  "unable to locate .dwo debug file \"{0}\" for skeleton DIE "
+  "{1:x16}",
+  error_dwo_path.GetPath().c_str(), unit.GetOffset());
+}
+
 if (m_dwo_warning_issued.test_and_set(std::memory_order_relaxed) == false) 
{
   GetObjectFile()->GetModule()->ReportWarning(
   "unable to locate separate debug file (dwo, dwp). Debugging will be "

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

https://github.com/jimingham created 
https://github.com/llvm/llvm-project/pull/116438

I have some reports of A/B inversion deadlocks between the ThreadPlanStack and 
the StackFrameList accesses.  There's a fair bit of reasonable code in lldb 
that does "While accessing the ThreadPlanStack, look at that threads's 
StackFrameList", and also plenty of "While accessing the ThreadPlanStack, look 
at the StackFrameList."

In all the cases I've seen so far, there was at most one of the locks taken 
that were trying to mutate the list, the other three were just reading.  So we 
could solve the deadlock by converting the two mutexes over to shared mutexes.

This patch is the easy part, the ThreadPlanStack mutex.  

The tricky part was because these were originally recursive mutexes, and  
recursive access to shared mutexes is undefined behavior according to the C++ 
standard, I had to add a couple NoLock variants to make sure it didn't get used 
recursively.  Then since the only remaining calls are out to ThreadPlans and 
ThreadPlans don't have access to their containing ThreadPlanStack, converting 
this to a non-recursive lock should be safe.

>From 943bad7a8faa41d21651de765858dbb49584547c Mon Sep 17 00:00:00 2001
From: Jim Ingham 
Date: Fri, 15 Nov 2024 12:20:33 -0800
Subject: [PATCH] Convert ThreadPlanStack's mutex to a shared mutex.

Since shared mutexes are not recursive, I had to add a couple
NoLock variants to make sure it didn't get used recursively.
---
 lldb/include/lldb/Target/ThreadPlanStack.h |  9 ++-
 lldb/source/Target/ThreadPlanStack.cpp | 81 --
 2 files changed, 51 insertions(+), 39 deletions(-)

diff --git a/lldb/include/lldb/Target/ThreadPlanStack.h 
b/lldb/include/lldb/Target/ThreadPlanStack.h
index e6a560a509261f..cd606bd0bb1056 100644
--- a/lldb/include/lldb/Target/ThreadPlanStack.h
+++ b/lldb/include/lldb/Target/ThreadPlanStack.h
@@ -14,6 +14,8 @@
 #include 
 #include 
 
+#include "llvm/Support/RWMutex.h"
+
 #include "lldb/Target/Target.h"
 #include "lldb/Target/Thread.h"
 #include "lldb/lldb-private-forward.h"
@@ -96,7 +98,10 @@ class ThreadPlanStack {
   void ClearThreadCache();
 
 private:
-  void PrintOneStack(Stream &s, llvm::StringRef stack_name,
+
+  lldb::ThreadPlanSP DiscardPlanNoLock();
+  lldb::ThreadPlanSP GetCurrentPlanNoLock() const;
+  void PrintOneStackNoLock(Stream &s, llvm::StringRef stack_name,
  const PlanStack &stack, lldb::DescriptionLevel desc_level,
  bool include_internal) const;
 
@@ -110,7 +115,7 @@ class ThreadPlanStack {
   size_t m_completed_plan_checkpoint = 0; // Monotonically increasing token for
   // completed plan checkpoints.
   std::unordered_map m_completed_plan_store;
-  mutable std::recursive_mutex m_stack_mutex;
+  mutable llvm::sys::RWMutex m_stack_mutex;
 };
 
 class ThreadPlanStackMap {
diff --git a/lldb/source/Target/ThreadPlanStack.cpp 
b/lldb/source/Target/ThreadPlanStack.cpp
index 1572931429071d..81fcb09b563668 100644
--- a/lldb/source/Target/ThreadPlanStack.cpp
+++ b/lldb/source/Target/ThreadPlanStack.cpp
@@ -39,21 +39,20 @@ ThreadPlanStack::ThreadPlanStack(const Thread &thread, bool 
make_null) {
 void ThreadPlanStack::DumpThreadPlans(Stream &s,
   lldb::DescriptionLevel desc_level,
   bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedReader guard(m_stack_mutex);
   s.IndentMore();
-  PrintOneStack(s, "Active plan stack", m_plans, desc_level, include_internal);
-  PrintOneStack(s, "Completed plan stack", m_completed_plans, desc_level,
+  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level, 
include_internal);
+  PrintOneStackNoLock(s, "Completed plan stack", m_completed_plans, desc_level,
 include_internal);
-  PrintOneStack(s, "Discarded plan stack", m_discarded_plans, desc_level,
+  PrintOneStackNoLock(s, "Discarded plan stack", m_discarded_plans, desc_level,
 include_internal);
   s.IndentLess();
 }
 
-void ThreadPlanStack::PrintOneStack(Stream &s, llvm::StringRef stack_name,
+void ThreadPlanStack::PrintOneStackNoLock(Stream &s, llvm::StringRef 
stack_name,
 const PlanStack &stack,
 lldb::DescriptionLevel desc_level,
 bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
   // If the stack is empty, just exit:
   if (stack.empty())
 return;
@@ -82,7 +81,7 @@ void ThreadPlanStack::PrintOneStack(Stream &s, 
llvm::StringRef stack_name,
 }
 
 size_t ThreadPlanStack::CheckpointCompletedPlans() {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   m_completed_plan_checkpoint++;
   m_completed_plan_store.insert(
   std::make_pair(m_completed_plan_checkpoint, m_completed_plans));
@@ -90,7 +89,7 @@ size_t ThreadPlanS

[Lldb-commits] [lldb] [lldb] Convert file address to load address when reading memory for DW_OP_piece (PR #116411)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Ilia Kuklin (kuilpd)


Changes

When parsing an optimized value and reading a piece from a file address, LLDB 
tries to read the data from memory using that address.
This patch converts file address to load address before reading the memory.

Fixes #111313 #97484

---
Full diff: https://github.com/llvm/llvm-project/pull/116411.diff


2 Files Affected:

- (modified) lldb/source/Expression/DWARFExpression.cpp (+16-3) 
- (added) lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c (+23) 


``diff
diff --git a/lldb/source/Expression/DWARFExpression.cpp 
b/lldb/source/Expression/DWARFExpression.cpp
index f92f25ed342a9c..a7126b25c1cc38 100644
--- a/lldb/source/Expression/DWARFExpression.cpp
+++ b/lldb/source/Expression/DWARFExpression.cpp
@@ -1853,12 +1853,25 @@ llvm::Expected DWARFExpression::Evaluate(
   const Value::ValueType curr_piece_source_value_type =
   curr_piece_source_value.GetValueType();
   Scalar &scalar = curr_piece_source_value.GetScalar();
-  const lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+  lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
   switch (curr_piece_source_value_type) {
   case Value::ValueType::Invalid:
 return llvm::createStringError("invalid value type");
-  case Value::ValueType::LoadAddress:
-  case Value::ValueType::FileAddress: {
+  case Value::ValueType::FileAddress:
+if (target) {
+  curr_piece_source_value.ConvertToLoadAddress(module_sp.get(),
+   target);
+  addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+} else {
+  return llvm::createStringError(
+  "unable to convert file address 0x%" PRIx64
+  " to load address "
+  "for DW_OP_piece(%" PRIu64 "): "
+  "no target available",
+  addr, piece_byte_size);
+}
+[[fallthrough]];
+  case Value::ValueType::LoadAddress: {
 if (target) {
   if (curr_piece.ResizeData(piece_byte_size) == piece_byte_size) {
 if (target->ReadMemory(addr, curr_piece.GetBuffer().GetBytes(),
diff --git a/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c 
b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
new file mode 100644
index 00..d31250426dc112
--- /dev/null
+++ b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
@@ -0,0 +1,23 @@
+// Check that optimized with -O3 values that have a file address can be read
+// DWARF info:
+// 0x0023:   DW_TAG_variable
+// DW_AT_name  ("array")
+// DW_AT_type  (0x0032 "char[5]")
+// DW_AT_location  (DW_OP_piece 0x2, DW_OP_addrx 0x0, 
DW_OP_piece 0x1)
+
+// RUN: %clang_host -O3 -gdwarf %s -o %t
+// RUN: %lldb %t \
+// RUN:   -o "b 22" \
+// RUN:   -o "r" \
+// RUN:   -o "p/x array[2]" \
+// RUN:   -b | FileCheck %s
+//
+// CHECK: (lldb) p/x array[2]
+// CHECK: (char) 0x03
+
+static char array[5] = {0, 1, 2, 3, 4};
+
+int main(void) {
+  array[2]++;
+  return 0;
+}
\ No newline at end of file

``




https://github.com/llvm/llvm-project/pull/116411
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] Convert file address to load address when reading memory for DW_OP_piece (PR #116411)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-debuginfo

Author: Ilia Kuklin (kuilpd)


Changes

When parsing an optimized value and reading a piece from a file address, LLDB 
tries to read the data from memory using that address.
This patch converts file address to load address before reading the memory.

Fixes #111313 #97484

---
Full diff: https://github.com/llvm/llvm-project/pull/116411.diff


2 Files Affected:

- (modified) lldb/source/Expression/DWARFExpression.cpp (+16-3) 
- (added) lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c (+23) 


``diff
diff --git a/lldb/source/Expression/DWARFExpression.cpp 
b/lldb/source/Expression/DWARFExpression.cpp
index f92f25ed342a9c..a7126b25c1cc38 100644
--- a/lldb/source/Expression/DWARFExpression.cpp
+++ b/lldb/source/Expression/DWARFExpression.cpp
@@ -1853,12 +1853,25 @@ llvm::Expected DWARFExpression::Evaluate(
   const Value::ValueType curr_piece_source_value_type =
   curr_piece_source_value.GetValueType();
   Scalar &scalar = curr_piece_source_value.GetScalar();
-  const lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+  lldb::addr_t addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
   switch (curr_piece_source_value_type) {
   case Value::ValueType::Invalid:
 return llvm::createStringError("invalid value type");
-  case Value::ValueType::LoadAddress:
-  case Value::ValueType::FileAddress: {
+  case Value::ValueType::FileAddress:
+if (target) {
+  curr_piece_source_value.ConvertToLoadAddress(module_sp.get(),
+   target);
+  addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
+} else {
+  return llvm::createStringError(
+  "unable to convert file address 0x%" PRIx64
+  " to load address "
+  "for DW_OP_piece(%" PRIu64 "): "
+  "no target available",
+  addr, piece_byte_size);
+}
+[[fallthrough]];
+  case Value::ValueType::LoadAddress: {
 if (target) {
   if (curr_piece.ResizeData(piece_byte_size) == piece_byte_size) {
 if (target->ReadMemory(addr, curr_piece.GetBuffer().GetBytes(),
diff --git a/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c 
b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
new file mode 100644
index 00..d31250426dc112
--- /dev/null
+++ b/lldb/test/Shell/SymbolFile/DWARF/DW_OP_piece-O3.c
@@ -0,0 +1,23 @@
+// Check that optimized with -O3 values that have a file address can be read
+// DWARF info:
+// 0x0023:   DW_TAG_variable
+// DW_AT_name  ("array")
+// DW_AT_type  (0x0032 "char[5]")
+// DW_AT_location  (DW_OP_piece 0x2, DW_OP_addrx 0x0, 
DW_OP_piece 0x1)
+
+// RUN: %clang_host -O3 -gdwarf %s -o %t
+// RUN: %lldb %t \
+// RUN:   -o "b 22" \
+// RUN:   -o "r" \
+// RUN:   -o "p/x array[2]" \
+// RUN:   -b | FileCheck %s
+//
+// CHECK: (lldb) p/x array[2]
+// CHECK: (char) 0x03
+
+static char array[5] = {0, 1, 2, 3, 4};
+
+int main(void) {
+  array[2]++;
+  return 0;
+}
\ No newline at end of file

``




https://github.com/llvm/llvm-project/pull/116411
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -22,8 +22,17 @@ def port: S<"port">,
   HelpText<"Communicate with the lldb-dap tool over the defined port.">;
 def: Separate<["-"], "p">,
   Alias,
+  MetaVarName<"">,
   HelpText<"Alias for --port">;
 
+def unix_socket: S<"unix-socket">,
+  MetaVarName<"">,
+  HelpText<"Communicate with the lldb-dap tool over the unix socket or named 
pipe.">;
+def: Separate<["-"], "u">,
+  Alias,
+  MetaVarName<"">,
+  HelpText<"Alias for --unix_socket">;

vogelsgesang wrote:

do we even want to have a short-hand option for sockets? I don't think this 
will be commonly used manually, so maybe we should not assign a short-hand to 
it?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb] rm DWARFDebugRanges (PR #116379)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere approved this pull request.

Beautiful. 

https://github.com/llvm/llvm-project/pull/116379
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread Adrian Vogelsgesang via lldb-commits


@@ -250,6 +251,13 @@ def which(program):
 return None
 
 
+def pickrandomport():
+"""Returns a random open port."""
+with socket.socket() as sock:
+sock.bind(("", 0))
+return sock.getsockname()[1]

vogelsgesang wrote:

afaict, this will lead to a race condition? The `return` will exit the `with` 
scope, and we will give up the lock on the port number again?

https://github.com/llvm/llvm-project/pull/116392
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [llvm] [DebugInfo] Add explicit visibility macros to CodeView template functions (PR #113102)

2024-11-15 Thread Vassil Vassilev via lldb-commits

vgvassilev wrote:

@zmodem, ping.

https://github.com/llvm/llvm-project/pull/113102
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

https://github.com/jimingham updated 
https://github.com/llvm/llvm-project/pull/116438

>From 943bad7a8faa41d21651de765858dbb49584547c Mon Sep 17 00:00:00 2001
From: Jim Ingham 
Date: Fri, 15 Nov 2024 12:20:33 -0800
Subject: [PATCH 1/2] Convert ThreadPlanStack's mutex to a shared mutex.

Since shared mutexes are not recursive, I had to add a couple
NoLock variants to make sure it didn't get used recursively.
---
 lldb/include/lldb/Target/ThreadPlanStack.h |  9 ++-
 lldb/source/Target/ThreadPlanStack.cpp | 81 --
 2 files changed, 51 insertions(+), 39 deletions(-)

diff --git a/lldb/include/lldb/Target/ThreadPlanStack.h 
b/lldb/include/lldb/Target/ThreadPlanStack.h
index e6a560a509261f..cd606bd0bb1056 100644
--- a/lldb/include/lldb/Target/ThreadPlanStack.h
+++ b/lldb/include/lldb/Target/ThreadPlanStack.h
@@ -14,6 +14,8 @@
 #include 
 #include 
 
+#include "llvm/Support/RWMutex.h"
+
 #include "lldb/Target/Target.h"
 #include "lldb/Target/Thread.h"
 #include "lldb/lldb-private-forward.h"
@@ -96,7 +98,10 @@ class ThreadPlanStack {
   void ClearThreadCache();
 
 private:
-  void PrintOneStack(Stream &s, llvm::StringRef stack_name,
+
+  lldb::ThreadPlanSP DiscardPlanNoLock();
+  lldb::ThreadPlanSP GetCurrentPlanNoLock() const;
+  void PrintOneStackNoLock(Stream &s, llvm::StringRef stack_name,
  const PlanStack &stack, lldb::DescriptionLevel desc_level,
  bool include_internal) const;
 
@@ -110,7 +115,7 @@ class ThreadPlanStack {
   size_t m_completed_plan_checkpoint = 0; // Monotonically increasing token for
   // completed plan checkpoints.
   std::unordered_map m_completed_plan_store;
-  mutable std::recursive_mutex m_stack_mutex;
+  mutable llvm::sys::RWMutex m_stack_mutex;
 };
 
 class ThreadPlanStackMap {
diff --git a/lldb/source/Target/ThreadPlanStack.cpp 
b/lldb/source/Target/ThreadPlanStack.cpp
index 1572931429071d..81fcb09b563668 100644
--- a/lldb/source/Target/ThreadPlanStack.cpp
+++ b/lldb/source/Target/ThreadPlanStack.cpp
@@ -39,21 +39,20 @@ ThreadPlanStack::ThreadPlanStack(const Thread &thread, bool 
make_null) {
 void ThreadPlanStack::DumpThreadPlans(Stream &s,
   lldb::DescriptionLevel desc_level,
   bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedReader guard(m_stack_mutex);
   s.IndentMore();
-  PrintOneStack(s, "Active plan stack", m_plans, desc_level, include_internal);
-  PrintOneStack(s, "Completed plan stack", m_completed_plans, desc_level,
+  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level, 
include_internal);
+  PrintOneStackNoLock(s, "Completed plan stack", m_completed_plans, desc_level,
 include_internal);
-  PrintOneStack(s, "Discarded plan stack", m_discarded_plans, desc_level,
+  PrintOneStackNoLock(s, "Discarded plan stack", m_discarded_plans, desc_level,
 include_internal);
   s.IndentLess();
 }
 
-void ThreadPlanStack::PrintOneStack(Stream &s, llvm::StringRef stack_name,
+void ThreadPlanStack::PrintOneStackNoLock(Stream &s, llvm::StringRef 
stack_name,
 const PlanStack &stack,
 lldb::DescriptionLevel desc_level,
 bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
   // If the stack is empty, just exit:
   if (stack.empty())
 return;
@@ -82,7 +81,7 @@ void ThreadPlanStack::PrintOneStack(Stream &s, 
llvm::StringRef stack_name,
 }
 
 size_t ThreadPlanStack::CheckpointCompletedPlans() {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   m_completed_plan_checkpoint++;
   m_completed_plan_store.insert(
   std::make_pair(m_completed_plan_checkpoint, m_completed_plans));
@@ -90,7 +89,7 @@ size_t ThreadPlanStack::CheckpointCompletedPlans() {
 }
 
 void ThreadPlanStack::RestoreCompletedPlanCheckpoint(size_t checkpoint) {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   auto result = m_completed_plan_store.find(checkpoint);
   assert(result != m_completed_plan_store.end() &&
  "Asked for a checkpoint that didn't exist");
@@ -99,13 +98,13 @@ void ThreadPlanStack::RestoreCompletedPlanCheckpoint(size_t 
checkpoint) {
 }
 
 void ThreadPlanStack::DiscardCompletedPlanCheckpoint(size_t checkpoint) {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   m_completed_plan_store.erase(checkpoint);
 }
 
 void ThreadPlanStack::ThreadDestroyed(Thread *thread) {
   // Tell the plan stacks that this thread is going away:
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   for (ThreadPlanSP plan : m_plans)
 plan->ThreadDestroyed();
 
@@ -134,7 +133,7 @@ void ThreadPlanStack::PushPlan(lldb::ThreadPlanSP 
new_plan_sp) {
   // If the threa

[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere commented:

Mechanically this change looks good, plus I'm always happy to see another 
recursive mutex go. 

One side-effect of this change is that previously, the ThreadPlanStack mutex 
was indirectly protecting some operations on ThreadPlans too. For example, 
`ThreadPlan::ClearThreadCache` isn't protected by a mutex, but 
`ThreadPlanStack::ClearThreadCache` used to be. Assuming the only way multiple 
threads would interact with this function is through the `ThreadPlanStack`, we 
now have a potential race because of the reader-lock, while previously this was 
indirectly protected by the unique lock. I don't know the ThreadPlans enough to 
determine if that's a problem or not. 

https://github.com/llvm/llvm-project/pull/116438
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][sbapi][NFC] Remove commented out typedef from SBBreakpointName (PR #116434)

2024-11-15 Thread Chelsea Cassanova via lldb-commits

https://github.com/chelcassanova created 
https://github.com/llvm/llvm-project/pull/116434

SBBreakpointName has a typedef for BreakpointHitCallback used in SetCallback(), 
but this typedef has been commented out in SBBreakpointName and added instead 
to SBDefines. Since SB API callbacks are placed in SBDefines, this commit 
removes this commented out portion.

>From 1e1301c3ef833763e168d1462065bee588b759df Mon Sep 17 00:00:00 2001
From: Chelsea Cassanova 
Date: Fri, 15 Nov 2024 12:00:47 -0800
Subject: [PATCH] [lldb][sbapi] Remove commented out typedef from
 SBBreakpointName

SBBreakpointName has a typedef for BreakpointHitCallback used in
SetCallback(), but this typedef has been commented out in
SBBreakpointName and added instead to SBDefines. Since SB API callbacks
are placed in SBDefines, this commit removes this commented out portion.
---
 lldb/include/lldb/API/SBBreakpointName.h | 4 
 1 file changed, 4 deletions(-)

diff --git a/lldb/include/lldb/API/SBBreakpointName.h 
b/lldb/include/lldb/API/SBBreakpointName.h
index 838c66385bd121..4b7ad0cce345e5 100644
--- a/lldb/include/lldb/API/SBBreakpointName.h
+++ b/lldb/include/lldb/API/SBBreakpointName.h
@@ -17,10 +17,6 @@ namespace lldb {
 
 class LLDB_API SBBreakpointName {
 public:
-//  typedef bool (*BreakpointHitCallback)(void *baton, SBProcess &process,
-//SBThread &thread,
-//lldb::SBBreakpointLocation 
&location);
-
   SBBreakpointName();
   
   SBBreakpointName(SBTarget &target, const char *name);

___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

https://github.com/jimingham updated 
https://github.com/llvm/llvm-project/pull/116438

>From 943bad7a8faa41d21651de765858dbb49584547c Mon Sep 17 00:00:00 2001
From: Jim Ingham 
Date: Fri, 15 Nov 2024 12:20:33 -0800
Subject: [PATCH 1/3] Convert ThreadPlanStack's mutex to a shared mutex.

Since shared mutexes are not recursive, I had to add a couple
NoLock variants to make sure it didn't get used recursively.
---
 lldb/include/lldb/Target/ThreadPlanStack.h |  9 ++-
 lldb/source/Target/ThreadPlanStack.cpp | 81 --
 2 files changed, 51 insertions(+), 39 deletions(-)

diff --git a/lldb/include/lldb/Target/ThreadPlanStack.h 
b/lldb/include/lldb/Target/ThreadPlanStack.h
index e6a560a509261f..cd606bd0bb1056 100644
--- a/lldb/include/lldb/Target/ThreadPlanStack.h
+++ b/lldb/include/lldb/Target/ThreadPlanStack.h
@@ -14,6 +14,8 @@
 #include 
 #include 
 
+#include "llvm/Support/RWMutex.h"
+
 #include "lldb/Target/Target.h"
 #include "lldb/Target/Thread.h"
 #include "lldb/lldb-private-forward.h"
@@ -96,7 +98,10 @@ class ThreadPlanStack {
   void ClearThreadCache();
 
 private:
-  void PrintOneStack(Stream &s, llvm::StringRef stack_name,
+
+  lldb::ThreadPlanSP DiscardPlanNoLock();
+  lldb::ThreadPlanSP GetCurrentPlanNoLock() const;
+  void PrintOneStackNoLock(Stream &s, llvm::StringRef stack_name,
  const PlanStack &stack, lldb::DescriptionLevel desc_level,
  bool include_internal) const;
 
@@ -110,7 +115,7 @@ class ThreadPlanStack {
   size_t m_completed_plan_checkpoint = 0; // Monotonically increasing token for
   // completed plan checkpoints.
   std::unordered_map m_completed_plan_store;
-  mutable std::recursive_mutex m_stack_mutex;
+  mutable llvm::sys::RWMutex m_stack_mutex;
 };
 
 class ThreadPlanStackMap {
diff --git a/lldb/source/Target/ThreadPlanStack.cpp 
b/lldb/source/Target/ThreadPlanStack.cpp
index 1572931429071d..81fcb09b563668 100644
--- a/lldb/source/Target/ThreadPlanStack.cpp
+++ b/lldb/source/Target/ThreadPlanStack.cpp
@@ -39,21 +39,20 @@ ThreadPlanStack::ThreadPlanStack(const Thread &thread, bool 
make_null) {
 void ThreadPlanStack::DumpThreadPlans(Stream &s,
   lldb::DescriptionLevel desc_level,
   bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedReader guard(m_stack_mutex);
   s.IndentMore();
-  PrintOneStack(s, "Active plan stack", m_plans, desc_level, include_internal);
-  PrintOneStack(s, "Completed plan stack", m_completed_plans, desc_level,
+  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level, 
include_internal);
+  PrintOneStackNoLock(s, "Completed plan stack", m_completed_plans, desc_level,
 include_internal);
-  PrintOneStack(s, "Discarded plan stack", m_discarded_plans, desc_level,
+  PrintOneStackNoLock(s, "Discarded plan stack", m_discarded_plans, desc_level,
 include_internal);
   s.IndentLess();
 }
 
-void ThreadPlanStack::PrintOneStack(Stream &s, llvm::StringRef stack_name,
+void ThreadPlanStack::PrintOneStackNoLock(Stream &s, llvm::StringRef 
stack_name,
 const PlanStack &stack,
 lldb::DescriptionLevel desc_level,
 bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
   // If the stack is empty, just exit:
   if (stack.empty())
 return;
@@ -82,7 +81,7 @@ void ThreadPlanStack::PrintOneStack(Stream &s, 
llvm::StringRef stack_name,
 }
 
 size_t ThreadPlanStack::CheckpointCompletedPlans() {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   m_completed_plan_checkpoint++;
   m_completed_plan_store.insert(
   std::make_pair(m_completed_plan_checkpoint, m_completed_plans));
@@ -90,7 +89,7 @@ size_t ThreadPlanStack::CheckpointCompletedPlans() {
 }
 
 void ThreadPlanStack::RestoreCompletedPlanCheckpoint(size_t checkpoint) {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   auto result = m_completed_plan_store.find(checkpoint);
   assert(result != m_completed_plan_store.end() &&
  "Asked for a checkpoint that didn't exist");
@@ -99,13 +98,13 @@ void ThreadPlanStack::RestoreCompletedPlanCheckpoint(size_t 
checkpoint) {
 }
 
 void ThreadPlanStack::DiscardCompletedPlanCheckpoint(size_t checkpoint) {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   m_completed_plan_store.erase(checkpoint);
 }
 
 void ThreadPlanStack::ThreadDestroyed(Thread *thread) {
   // Tell the plan stacks that this thread is going away:
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedWriter guard(m_stack_mutex);
   for (ThreadPlanSP plan : m_plans)
 plan->ThreadDestroyed();
 
@@ -134,7 +133,7 @@ void ThreadPlanStack::PushPlan(lldb::ThreadPlanSP 
new_plan_sp) {
   // If the threa

[Lldb-commits] [lldb] Convert ThreadPlanStack's mutex to a shared mutex. (PR #116438)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: None (jimingham)


Changes

I have some reports of A/B inversion deadlocks between the ThreadPlanStack and 
the StackFrameList accesses.  There's a fair bit of reasonable code in lldb 
that does "While accessing the ThreadPlanStack, look at that threads's 
StackFrameList", and also plenty of "While accessing the ThreadPlanStack, look 
at the StackFrameList."

In all the cases I've seen so far, there was at most one of the locks taken 
that were trying to mutate the list, the other three were just reading.  So we 
could solve the deadlock by converting the two mutexes over to shared mutexes.

This patch is the easy part, the ThreadPlanStack mutex.  

The tricky part was because these were originally recursive mutexes, and  
recursive access to shared mutexes is undefined behavior according to the C++ 
standard, I had to add a couple NoLock variants to make sure it didn't get used 
recursively.  Then since the only remaining calls are out to ThreadPlans and 
ThreadPlans don't have access to their containing ThreadPlanStack, converting 
this to a non-recursive lock should be safe.

---
Full diff: https://github.com/llvm/llvm-project/pull/116438.diff


2 Files Affected:

- (modified) lldb/include/lldb/Target/ThreadPlanStack.h (+9-4) 
- (modified) lldb/source/Target/ThreadPlanStack.cpp (+59-49) 


``diff
diff --git a/lldb/include/lldb/Target/ThreadPlanStack.h 
b/lldb/include/lldb/Target/ThreadPlanStack.h
index e6a560a509261f..e0f8104de9a4d1 100644
--- a/lldb/include/lldb/Target/ThreadPlanStack.h
+++ b/lldb/include/lldb/Target/ThreadPlanStack.h
@@ -14,6 +14,8 @@
 #include 
 #include 
 
+#include "llvm/Support/RWMutex.h"
+
 #include "lldb/Target/Target.h"
 #include "lldb/Target/Thread.h"
 #include "lldb/lldb-private-forward.h"
@@ -96,9 +98,12 @@ class ThreadPlanStack {
   void ClearThreadCache();
 
 private:
-  void PrintOneStack(Stream &s, llvm::StringRef stack_name,
- const PlanStack &stack, lldb::DescriptionLevel desc_level,
- bool include_internal) const;
+  lldb::ThreadPlanSP DiscardPlanNoLock();
+  lldb::ThreadPlanSP GetCurrentPlanNoLock() const;
+  void PrintOneStackNoLock(Stream &s, llvm::StringRef stack_name,
+   const PlanStack &stack,
+   lldb::DescriptionLevel desc_level,
+   bool include_internal) const;
 
   PlanStack m_plans;   ///< The stack of plans this thread is 
executing.
   PlanStack m_completed_plans; ///< Plans that have been completed by this
@@ -110,7 +115,7 @@ class ThreadPlanStack {
   size_t m_completed_plan_checkpoint = 0; // Monotonically increasing token for
   // completed plan checkpoints.
   std::unordered_map m_completed_plan_store;
-  mutable std::recursive_mutex m_stack_mutex;
+  mutable llvm::sys::RWMutex m_stack_mutex;
 };
 
 class ThreadPlanStackMap {
diff --git a/lldb/source/Target/ThreadPlanStack.cpp 
b/lldb/source/Target/ThreadPlanStack.cpp
index 1572931429071d..d5d600dda47a3f 100644
--- a/lldb/source/Target/ThreadPlanStack.cpp
+++ b/lldb/source/Target/ThreadPlanStack.cpp
@@ -39,21 +39,21 @@ ThreadPlanStack::ThreadPlanStack(const Thread &thread, bool 
make_null) {
 void ThreadPlanStack::DumpThreadPlans(Stream &s,
   lldb::DescriptionLevel desc_level,
   bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
+  llvm::sys::ScopedReader guard(m_stack_mutex);
   s.IndentMore();
-  PrintOneStack(s, "Active plan stack", m_plans, desc_level, include_internal);
-  PrintOneStack(s, "Completed plan stack", m_completed_plans, desc_level,
-include_internal);
-  PrintOneStack(s, "Discarded plan stack", m_discarded_plans, desc_level,
-include_internal);
+  PrintOneStackNoLock(s, "Active plan stack", m_plans, desc_level,
+  include_internal);
+  PrintOneStackNoLock(s, "Completed plan stack", m_completed_plans, desc_level,
+  include_internal);
+  PrintOneStackNoLock(s, "Discarded plan stack", m_discarded_plans, desc_level,
+  include_internal);
   s.IndentLess();
 }
 
-void ThreadPlanStack::PrintOneStack(Stream &s, llvm::StringRef stack_name,
-const PlanStack &stack,
-lldb::DescriptionLevel desc_level,
-bool include_internal) const {
-  std::lock_guard guard(m_stack_mutex);
+void ThreadPlanStack::PrintOneStackNoLock(Stream &s, llvm::StringRef 
stack_name,
+  const PlanStack &stack,
+  lldb::DescriptionLevel desc_level,
+  bool include_internal) const {
   // If the stack is empty, just exit:
   if (stack.empty())
 return;
@@ -82,7 +82,7 @@ void ThreadPlanStack:

[Lldb-commits] [lldb] [lldb][sbapi][NFC] Remove commented out typedef from SBBreakpointName (PR #116434)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Chelsea Cassanova (chelcassanova)


Changes

SBBreakpointName has a typedef for BreakpointHitCallback used in SetCallback(), 
but this typedef has been commented out in SBBreakpointName and added instead 
to SBDefines. Since SB API callbacks are placed in SBDefines, this commit 
removes this commented out portion.

---
Full diff: https://github.com/llvm/llvm-project/pull/116434.diff


1 Files Affected:

- (modified) lldb/include/lldb/API/SBBreakpointName.h (-4) 


``diff
diff --git a/lldb/include/lldb/API/SBBreakpointName.h 
b/lldb/include/lldb/API/SBBreakpointName.h
index 838c66385bd121..4b7ad0cce345e5 100644
--- a/lldb/include/lldb/API/SBBreakpointName.h
+++ b/lldb/include/lldb/API/SBBreakpointName.h
@@ -17,10 +17,6 @@ namespace lldb {
 
 class LLDB_API SBBreakpointName {
 public:
-//  typedef bool (*BreakpointHitCallback)(void *baton, SBProcess &process,
-//SBThread &thread,
-//lldb::SBBreakpointLocation 
&location);
-
   SBBreakpointName();
   
   SBBreakpointName(SBTarget &target, const char *name);

``




https://github.com/llvm/llvm-project/pull/116434
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][AIX] Added XCOFF Object File Header Parsing (PR #116337)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Dhruv Srivastava (DhruvSrivastavaX)


Changes

This PR is in reference to porting LLDB on AIX.

Link to discussions on llvm discourse and github:

1. https://discourse.llvm.org/t/port-lldb-to-ibm-aix/80640
2. https://github.com/llvm/llvm-project/issues/101657
The complete changes for porting are present in this draft PR:
https://github.com/llvm/llvm-project/pull/102601

Added XCOFF Object File Header Parsing for AIX.
This PR is an incremental PR to the base: 

-  #111814 

Details about XCOFF file format on AIX: 
[XCOFF](https://www.ibm.com/docs/en/aix/7.3?topic=formats-xcoff-object-file-format)

Review Request: @labath @DavidSpickett

---
Full diff: https://github.com/llvm/llvm-project/pull/116337.diff


2 Files Affected:

- (modified) lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp (+123-3) 
- (modified) lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.h (+58) 


``diff
diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..c06ece4347822d 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,92 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfData = data.GetU16(o

[Lldb-commits] [lldb] [lldb] Improve editline completion formatting (PR #116456)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

JDevlieghere wrote:

I've made this a draft because this still needs a test. 

https://github.com/llvm/llvm-project/pull/116456
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb][sbapi][NFC] Remove commented out typedef from SBBreakpointName (PR #116434)

2024-11-15 Thread Jonas Devlieghere via lldb-commits

https://github.com/JDevlieghere approved this pull request.


https://github.com/llvm/llvm-project/pull/116434
___
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits


[Lldb-commits] [lldb] [lldb-dap] Refactoring lldb-dap port listening mode to allow multiple connections. (PR #116392)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: John Harrison (ashgti)


Changes

This refactors the port listening mode to allocate a new DAP object for each 
connection, allowing multiple connections to run concurrently.

---

Patch is 32.80 KiB, truncated to 20.00 KiB below, full version: 
https://github.com/llvm/llvm-project/pull/116392.diff


12 Files Affected:

- (modified) lldb/packages/Python/lldbsuite/test/lldbtest.py (+8) 
- (modified) lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py 
(+56-19) 
- (modified) 
lldb/packages/Python/lldbsuite/test/tools/lldb-dap/lldbdap_testcase.py (+27-5) 
- (added) lldb/test/API/tools/lldb-dap/server/Makefile (+3) 
- (added) lldb/test/API/tools/lldb-dap/server/TestDAP_server.py (+66) 
- (added) lldb/test/API/tools/lldb-dap/server/main.c (+6) 
- (modified) lldb/tools/lldb-dap/DAP.cpp (+5-18) 
- (modified) lldb/tools/lldb-dap/DAP.h (+27-23) 
- (modified) lldb/tools/lldb-dap/Options.td (+9) 
- (modified) lldb/tools/lldb-dap/OutputRedirector.cpp (+4-3) 
- (modified) lldb/tools/lldb-dap/OutputRedirector.h (+9-3) 
- (modified) lldb/tools/lldb-dap/lldb-dap.cpp (+286-80) 


``diff
diff --git a/lldb/packages/Python/lldbsuite/test/lldbtest.py 
b/lldb/packages/Python/lldbsuite/test/lldbtest.py
index 8884ef5933ada8..a899854bb5ae14 100644
--- a/lldb/packages/Python/lldbsuite/test/lldbtest.py
+++ b/lldb/packages/Python/lldbsuite/test/lldbtest.py
@@ -39,6 +39,7 @@
 import signal
 from subprocess import *
 import sys
+import socket
 import time
 import traceback
 
@@ -250,6 +251,13 @@ def which(program):
 return None
 
 
+def pickrandomport():
+"""Returns a random open port."""
+with socket.socket() as sock:
+sock.bind(("", 0))
+return sock.getsockname()[1]
+
+
 class ValueCheck:
 def __init__(
 self,
diff --git a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py 
b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
index c29992ce9c7848..e4a53fe0d45907 100644
--- a/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
+++ b/lldb/packages/Python/lldbsuite/test/tools/lldb-dap/dap_server.py
@@ -903,7 +903,7 @@ def request_setBreakpoints(self, file_path, line_array, 
data=None):
 "sourceModified": False,
 }
 if line_array is not None:
-args_dict["lines"] = "%s" % line_array
+args_dict["lines"] = line_array
 breakpoints = []
 for i, line in enumerate(line_array):
 breakpoint_data = None
@@ -1154,34 +1154,38 @@ class DebugAdaptorServer(DebugCommunication):
 def __init__(
 self,
 executable=None,
+launch=True,
 port=None,
+unix_socket=None,
 init_commands=[],
 log_file=None,
 env=None,
 ):
 self.process = None
-if executable is not None:
-adaptor_env = os.environ.copy()
-if env is not None:
-adaptor_env.update(env)
-
-if log_file:
-adaptor_env["LLDBDAP_LOG"] = log_file
-self.process = subprocess.Popen(
-[executable],
-stdin=subprocess.PIPE,
-stdout=subprocess.PIPE,
-stderr=subprocess.PIPE,
-env=adaptor_env,
+if launch:
+self.process = DebugAdaptorServer.launch(
+executable,
+port=port,
+unix_socket=unix_socket,
+log_file=log_file,
+env=env,
 )
-DebugCommunication.__init__(
-self, self.process.stdout, self.process.stdin, init_commands, 
log_file
-)
-elif port is not None:
+
+if port:
 s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
 s.connect(("127.0.0.1", port))
 DebugCommunication.__init__(
-self, s.makefile("r"), s.makefile("w"), init_commands
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+elif unix_socket:
+s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
+s.connect(unix_socket)
+DebugCommunication.__init__(
+self, s.makefile("rb"), s.makefile("wb"), init_commands, 
log_file
+)
+else:
+DebugCommunication.__init__(
+self, self.process.stdout, self.process.stdin, init_commands, 
log_file
 )
 
 def get_pid(self):
@@ -1196,6 +1200,39 @@ def terminate(self):
 self.process.wait()
 self.process = None
 
+@classmethod
+def launch(
+cls, executable: str, /, port=None, unix_socket=None, log_file=None, 
env=None
+) -> subprocess.Popen:
+adaptor_env = os.environ.copy()
+if env:
+adaptor_env.update(env)
+
+if log_file:
+adaptor_env["LLDBDAP_LOG"] = log_file
+
+

[Lldb-commits] [lldb] [lldb] rm DWARFDebugRanges (PR #116379)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Pavel Labath (labath)


Changes

The class is only used from one place, which is trivial to implement using the 
llvm class.

The main difference is that in the new implementation, the ranges are parsed 
each time anew (instead of being parsed at startup and cached). I believe this 
is fine because:
- this is already how things work with DWARF v5 debug_rnglists
- parsing debug_ranges is fairly fast (definitely faster than rnglists)
- generally, this result will be cached at a higher level anyway. Browsing the 
code I did find one instance where that is not the case -- 
SymbolFileDWARF::ResolveFunctionAndBlock -- which is called each time we 
resolve an address (to the block level). However, this function is already 
pretty suboptimal: it first traverses the DIE tree (which involves parsing all 
the DIE attributes) to find the correct block, then it parses them again to 
construct the `lldb_private::Block` representation, and *then* it uses the ID 
of the block DIE it found in the first step to look up the `Block` object. If 
this turns out to be a bottleneck, I think there are better ways to optimize it 
than caching the debug_ranges parse.

The motiviation for this is that DWARFDebugRanges sorts the block ranges, even 
though the order of the ranges is load-bearing (in the absence of DW_AT_low_pc, 
the "base address" of a scope is determined by the first range entry). Delaying 
the parsing (and sorting) step makes it easier to access the first entry.

---
Full diff: https://github.com/llvm/llvm-project/pull/116379.diff


9 Files Affected:

- (modified) lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt (-1) 
- (modified) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp (-1) 
- (modified) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.h (-1) 
- (removed) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp (-56) 
- (removed) lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h (-34) 
- (modified) lldb/source/Plugins/SymbolFile/DWARF/DWARFUnit.cpp (+41-33) 
- (modified) lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp (-14) 
- (modified) lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h (-4) 
- (modified) 
lldb/test/Shell/SymbolFile/DWARF/x86/debug_ranges-missing-section.s (+1-1) 


``diff
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt 
b/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
index ea644a61b1bdaa..e87194dfe74cb3 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
+++ b/lldb/source/Plugins/SymbolFile/DWARF/CMakeLists.txt
@@ -21,7 +21,6 @@ add_lldb_library(lldbPluginSymbolFileDWARF PLUGIN
   DWARFDebugInfo.cpp
   DWARFDebugInfoEntry.cpp
   DWARFDebugMacro.cpp
-  DWARFDebugRanges.cpp
   DWARFDeclContext.cpp
   DWARFDefines.cpp
   DWARFDIE.cpp
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp 
b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
index c0a2066f8239e5..4ecb2ed616a128 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
@@ -25,7 +25,6 @@
 #include "DWARFCompileUnit.h"
 #include "DWARFDebugAranges.h"
 #include "DWARFDebugInfo.h"
-#include "DWARFDebugRanges.h"
 #include "DWARFDeclContext.h"
 #include "DWARFFormValue.h"
 #include "DWARFUnit.h"
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.h 
b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.h
index 20c07c95ec47b5..0e50aab3292ae6 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.h
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.h
@@ -14,7 +14,6 @@
 
 #include "DWARFAttribute.h"
 #include "DWARFBaseDIE.h"
-#include "DWARFDebugRanges.h"
 #include 
 #include 
 #include 
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp 
b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
deleted file mode 100644
index fd8f4e12ff770c..00
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
+++ /dev/null
@@ -1,56 +0,0 @@
-//===-- DWARFDebugRanges.cpp 
--===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===--===//
-
-#include "DWARFDebugRanges.h"
-#include "DWARFUnit.h"
-#include "llvm/DebugInfo/DWARF/DWARFDebugRangeList.h"
-
-using namespace lldb_private;
-using namespace lldb_private::plugin::dwarf;
-
-DWARFDebugRanges::DWARFDebugRanges() : m_range_map() {}
-
-void DWARFDebugRanges::Extract(DWARFContext &context) {
-  llvm::DWARFDataExtractor extractor =
-  context.getOrLoadRangesData().GetAsLLVMDWARF();
-  llvm::DWARFDebugRangeList extracted_list;
-  uint64_t current_offset = 0;
-  auto extract_next_li

[Lldb-commits] [lldb] [lldb][AIX] Header Parsing for XCOFF Object File in AIX (PR #116338)

2024-11-15 Thread via lldb-commits

llvmbot wrote:




@llvm/pr-subscribers-lldb

Author: Dhruv Srivastava (DhruvSrivastavaX)


Changes

This PR is in reference to porting LLDB on AIX.

Link to discussions on llvm discourse and github:

1. https://discourse.llvm.org/t/port-lldb-to-ibm-aix/80640
2. https://github.com/llvm/llvm-project/issues/101657
The complete changes for porting are present in this draft PR:
https://github.com/llvm/llvm-project/pull/102601

Added XCOFF Object File Header Parsing for AIX.
This PR is an incremental PR to the base:
- https://github.com/llvm/llvm-project/pull/111814

Details about XCOFF file format on AIX: 
[XCOFF](https://www.ibm.com/docs/en/aix/7.3?topic=formats-xcoff-object-file-format)

Review Request: @labath @DavidSpickett

---
Full diff: https://github.com/llvm/llvm-project/pull/116338.diff


2 Files Affected:

- (modified) lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp (+125-3) 
- (modified) lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.h (+58) 


``diff
diff --git a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp 
b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
index 3be900f9a4bc9f..255171997db399 100644
--- a/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
+++ b/lldb/source/Plugins/ObjectFile/XCOFF/ObjectFileXCOFF.cpp
@@ -81,9 +81,44 @@ ObjectFile *ObjectFileXCOFF::CreateInstance(const 
lldb::ModuleSP &module_sp,
   if (!objfile_up)
 return nullptr;
 
+  // Cache xcoff binary.
+  if (!objfile_up->CreateBinary())
+return nullptr;
+
+  if (!objfile_up->ParseHeader())
+return nullptr;
+
   return objfile_up.release();
 }
 
+bool ObjectFileXCOFF::CreateBinary() {
+  if (m_binary)
+return true;
+
+  Log *log = GetLog(LLDBLog::Object);
+
+  auto binary = llvm::object::XCOFFObjectFile::createObjectFile(
+  llvm::MemoryBufferRef(toStringRef(m_data.GetData()),
+m_file.GetFilename().GetStringRef()),
+  file_magic::xcoff_object_64);
+  if (!binary) {
+LLDB_LOG_ERROR(log, binary.takeError(),
+   "Failed to create binary for file ({1}): {0}", m_file);
+return false;
+  }
+
+  // Make sure we only handle XCOFF format.
+  m_binary =
+  llvm::unique_dyn_cast(std::move(*binary));
+  if (!m_binary)
+return false;
+
+  LLDB_LOG(log, "this = {0}, module = {1} ({2}), file = {3}, binary = {4}",
+   this, GetModule().get(), GetModule()->GetSpecificationDescription(),
+   m_file.GetPath(), m_binary.get());
+  return true;
+}
+
 ObjectFile *ObjectFileXCOFF::CreateMemoryInstance(
 const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp,
 const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) {
@@ -136,13 +171,94 @@ bool ObjectFileXCOFF::MagicBytesMatch(DataBufferSP 
&data_sp,
   return XCOFFHeaderSizeFromMagic(magic) != 0;
 }
 
-bool ObjectFileXCOFF::ParseHeader() { return false; }
+bool ObjectFileXCOFF::ParseHeader() {
+  ModuleSP module_sp(GetModule());
+  if (module_sp) {
+std::lock_guard guard(module_sp->GetMutex());
+lldb::offset_t offset = 0;
+
+if (ParseXCOFFHeader(m_data, &offset, m_xcoff_header)) {
+  m_data.SetAddressByteSize(GetAddressByteSize());
+  if (m_xcoff_header.auxhdrsize > 0)
+ParseXCOFFOptionalHeader(m_data, &offset);
+}
+return true;
+  }
+
+  return false;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFHeader(lldb_private::DataExtractor &data,
+   lldb::offset_t *offset_ptr,
+   xcoff_header_t &xcoff_header) {
+
+  // FIXME: data.ValidOffsetForDataOfSize
+  xcoff_header.magic = data.GetU16(offset_ptr);
+  xcoff_header.nsects = data.GetU16(offset_ptr);
+  xcoff_header.modtime = data.GetU32(offset_ptr);
+  xcoff_header.symoff = data.GetU64(offset_ptr);
+  xcoff_header.auxhdrsize = data.GetU16(offset_ptr);
+  xcoff_header.flags = data.GetU16(offset_ptr);
+  xcoff_header.nsyms = data.GetU32(offset_ptr);
+  return true;
+}
+
+bool ObjectFileXCOFF::ParseXCOFFOptionalHeader(
+lldb_private::DataExtractor &data, lldb::offset_t *offset_ptr) {
+  lldb::offset_t init_offset = *offset_ptr;
+
+  // FIXME: data.ValidOffsetForDataOfSize
+  m_xcoff_aux_header.AuxMagic = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.Version = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.ReservedForDebugger = data.GetU32(offset_ptr);
+  m_xcoff_aux_header.TextStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.DataStartAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.TOCAnchorAddr = data.GetU64(offset_ptr);
+  m_xcoff_aux_header.SecNumOfEntryPoint = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfText = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfData = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfTOC = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfLoader = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.SecNumOfBSS = data.GetU16(offset_ptr);
+  m_xcoff_aux_header.MaxAlignOfText = data.GetU16(offset_ptr);
+  m_xcoff_