Skip to content

Cp/r145014653 add support for riscv32 macho corefiles #10540

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
152 changes: 152 additions & 0 deletions lldb/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include "Plugins/Process/Utility/RegisterContextDarwin_arm.h"
#include "Plugins/Process/Utility/RegisterContextDarwin_arm64.h"
#include "Plugins/Process/Utility/RegisterContextDarwin_i386.h"
#include "Plugins/Process/Utility/RegisterContextDarwin_riscv32.h"
#include "Plugins/Process/Utility/RegisterContextDarwin_x86_64.h"
#include "lldb/Core/Debugger.h"
#include "lldb/Core/Module.h"
Expand Down Expand Up @@ -772,6 +773,147 @@ class RegisterContextDarwin_arm64_Mach : public RegisterContextDarwin_arm64 {
}
};

class RegisterContextDarwin_riscv32_Mach
: public RegisterContextDarwin_riscv32 {
public:
RegisterContextDarwin_riscv32_Mach(lldb_private::Thread &thread,
const DataExtractor &data)
: RegisterContextDarwin_riscv32(thread, 0) {
SetRegisterDataFrom_LC_THREAD(data);
}

void InvalidateAllRegisters() override {
// Do nothing... registers are always valid...
}

void SetRegisterDataFrom_LC_THREAD(const DataExtractor &data) {
lldb::offset_t offset = 0;
SetError(GPRRegSet, Read, -1);
SetError(FPURegSet, Read, -1);
SetError(EXCRegSet, Read, -1);
SetError(CSRRegSet, Read, -1);
bool done = false;
while (!done) {
int flavor = data.GetU32(&offset);
uint32_t count = data.GetU32(&offset);
lldb::offset_t next_thread_state = offset + (count * 4);
switch (flavor) {
case GPRRegSet:
// x0-x31 + pc
if (count >= 32) {
for (uint32_t i = 0; i < 32; ++i)
((uint32_t *)&gpr.x0)[i] = data.GetU32(&offset);
gpr.pc = data.GetU32(&offset);
SetError(GPRRegSet, Read, 0);
}
offset = next_thread_state;
break;
case FPURegSet: {
// f0-f31 + fcsr
if (count >= 32) {
for (uint32_t i = 0; i < 32; ++i)
((uint32_t *)&fpr.f0)[i] = data.GetU32(&offset);
fpr.fcsr = data.GetU32(&offset);
SetError(FPURegSet, Read, 0);
}
}
offset = next_thread_state;
break;
case EXCRegSet:
if (count == 3) {
exc.exception = data.GetU32(&offset);
exc.fsr = data.GetU32(&offset);
exc.far = data.GetU32(&offset);
SetError(EXCRegSet, Read, 0);
}
offset = next_thread_state;
break;
default:
done = true;
break;
}
}
}

static bool Create_LC_THREAD(Thread *thread, Stream &data) {
RegisterContextSP reg_ctx_sp(thread->GetRegisterContext());
if (reg_ctx_sp) {
RegisterContext *reg_ctx = reg_ctx_sp.get();

data.PutHex32(GPRRegSet); // Flavor
data.PutHex32(GPRWordCount);
PrintRegisterValue(reg_ctx, "x0", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x1", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x2", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x3", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x4", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x5", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x6", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x7", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x8", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x9", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x10", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x11", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x12", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x13", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x14", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x15", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x16", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x17", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x18", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x19", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x20", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x21", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x22", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x23", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x24", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x25", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x26", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x27", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x28", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x29", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x30", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "x31", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "pc", nullptr, 4, data);
data.PutHex32(0); // uint32_t pad at the end

// Write out the EXC registers
data.PutHex32(EXCRegSet);
data.PutHex32(EXCWordCount);
PrintRegisterValue(reg_ctx, "exception", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "fsr", nullptr, 4, data);
PrintRegisterValue(reg_ctx, "far", nullptr, 4, data);
return true;
}
return false;
}

protected:
int DoReadGPR(lldb::tid_t tid, int flavor, GPR &gpr) override { return -1; }

int DoReadFPU(lldb::tid_t tid, int flavor, FPU &fpu) override { return -1; }

int DoReadEXC(lldb::tid_t tid, int flavor, EXC &exc) override { return -1; }

int DoReadCSR(lldb::tid_t tid, int flavor, CSR &csr) override { return -1; }

int DoWriteGPR(lldb::tid_t tid, int flavor, const GPR &gpr) override {
return 0;
}

int DoWriteFPU(lldb::tid_t tid, int flavor, const FPU &fpu) override {
return 0;
}

int DoWriteEXC(lldb::tid_t tid, int flavor, const EXC &exc) override {
return 0;
}

int DoWriteCSR(lldb::tid_t tid, int flavor, const CSR &csr) override {
return 0;
}
};

static uint32_t MachHeaderSizeFromMagic(uint32_t magic) {
switch (magic) {
case MH_MAGIC:
Expand Down Expand Up @@ -5853,6 +5995,11 @@ ObjectFileMachO::GetThreadContextAtIndex(uint32_t idx,
reg_ctx_sp =
std::make_shared<RegisterContextDarwin_x86_64_Mach>(thread, data);
break;

case llvm::MachO::CPU_TYPE_RISCV:
reg_ctx_sp =
std::make_shared<RegisterContextDarwin_riscv32_Mach>(thread, data);
break;
}
}
}
Expand Down Expand Up @@ -6720,6 +6867,11 @@ bool ObjectFileMachO::SaveCore(const lldb::ProcessSP &process_sp,
RegisterContextDarwin_x86_64_Mach::Create_LC_THREAD(
thread_sp.get(), LC_THREAD_datas[thread_idx]);
break;

case llvm::MachO::CPU_TYPE_RISCV:
RegisterContextDarwin_riscv32_Mach::Create_LC_THREAD(
thread_sp.get(), LC_THREAD_datas[thread_idx]);
break;
}
}
}
Expand Down
1 change: 1 addition & 0 deletions lldb/source/Plugins/Process/Utility/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ add_lldb_library(lldbPluginProcessUtility
RegisterContextDarwin_arm.cpp
RegisterContextDarwin_arm64.cpp
RegisterContextDarwin_i386.cpp
RegisterContextDarwin_riscv32.cpp
RegisterContextDarwin_x86_64.cpp
RegisterContextDummy.cpp
RegisterContextFreeBSD_i386.cpp
Expand Down
Loading