Index: minidump/minidump_context_writer.cc |
diff --git a/minidump/minidump_context_writer.cc b/minidump/minidump_context_writer.cc |
index 6b46eeb33df9758c4e236764bd2a306443bbb8d8..9b30997d4e89ad5986ccf704bd690d8a74ff2dda 100644 |
--- a/minidump/minidump_context_writer.cc |
+++ b/minidump/minidump_context_writer.cc |
@@ -14,7 +14,10 @@ |
#include "minidump/minidump_context_writer.h" |
+#include <string.h> |
+ |
#include "base/logging.h" |
+#include "snapshot/cpu_context.h" |
#include "util/file/file_writer.h" |
namespace crashpad { |
@@ -22,6 +25,37 @@ namespace crashpad { |
MinidumpContextWriter::~MinidumpContextWriter() { |
} |
+// static |
+scoped_ptr<MinidumpContextWriter> MinidumpContextWriter::CreateFromSnapshot( |
+ const CPUContext* context_snapshot) { |
+ scoped_ptr<MinidumpContextWriter> context; |
+ |
+ switch (context_snapshot->architecture) { |
+ case kCPUArchitectureX86: { |
+ MinidumpContextX86Writer* context_x86 = new MinidumpContextX86Writer(); |
+ context.reset(context_x86); |
+ context_x86->InitializeFromSnapshot(context_snapshot->x86); |
+ break; |
+ } |
+ |
+ case kCPUArchitectureX86_64: { |
+ MinidumpContextAMD64Writer* context_amd64 = |
+ new MinidumpContextAMD64Writer(); |
+ context.reset(context_amd64); |
+ context_amd64->InitializeFromSnapshot(context_snapshot->x86_64); |
+ break; |
+ } |
+ |
+ default: { |
+ LOG(ERROR) << "unknown context architecture " |
+ << context_snapshot->architecture; |
+ break; |
+ } |
+ } |
+ |
+ return context; |
+} |
+ |
size_t MinidumpContextWriter::SizeOfObject() { |
DCHECK_GE(state(), kStateFrozen); |
@@ -36,6 +70,65 @@ MinidumpContextX86Writer::MinidumpContextX86Writer() |
MinidumpContextX86Writer::~MinidumpContextX86Writer() { |
} |
+ |
+void MinidumpContextX86Writer::InitializeFromSnapshot( |
+ const CPUContextX86* context_snapshot) { |
+ DCHECK_EQ(state(), kStateMutable); |
+ DCHECK_EQ(context_.context_flags, kMinidumpContextX86); |
+ |
+ context_.context_flags = kMinidumpContextX86All; |
+ |
+ context_.dr0 = context_snapshot->dr0; |
+ context_.dr1 = context_snapshot->dr1; |
+ context_.dr2 = context_snapshot->dr2; |
+ context_.dr3 = context_snapshot->dr3; |
+ context_.dr6 = context_snapshot->dr6; |
+ context_.dr7 = context_snapshot->dr7; |
+ |
+ // The contents of context_.float_save effectively alias everything in |
+ // context_.fxsave that’s related to x87 FPU state. context_.float_save |
+ // doesn’t carry state specific to SSE (or later), such as mxcsr and the xmm |
+ // registers. |
+ context_.float_save.control_word = context_snapshot->fxsave.fcw; |
+ context_.float_save.status_word = context_snapshot->fxsave.fsw; |
+ context_.float_save.tag_word = |
+ CPUContextX86::FxsaveToFsaveTagWord(context_snapshot->fxsave.fsw, |
+ context_snapshot->fxsave.ftw, |
+ context_snapshot->fxsave.st_mm); |
+ context_.float_save.error_offset = context_snapshot->fxsave.fpu_ip; |
+ context_.float_save.error_selector = context_snapshot->fxsave.fpu_cs; |
+ context_.float_save.data_offset = context_snapshot->fxsave.fpu_dp; |
+ context_.float_save.data_selector = context_snapshot->fxsave.fpu_ds; |
+ |
+ for (size_t index = 0, offset = 0; |
+ index < arraysize(context_snapshot->fxsave.st_mm); |
+ offset += sizeof(context_snapshot->fxsave.st_mm[index].st), ++index) { |
+ memcpy(&context_.float_save.register_area[offset], |
+ &context_snapshot->fxsave.st_mm[index].st, |
+ sizeof(context_snapshot->fxsave.st_mm[index].st)); |
+ } |
+ |
+ context_.gs = context_snapshot->gs; |
+ context_.fs = context_snapshot->fs; |
+ context_.es = context_snapshot->es; |
+ context_.ds = context_snapshot->ds; |
+ context_.edi = context_snapshot->edi; |
+ context_.esi = context_snapshot->esi; |
+ context_.ebx = context_snapshot->ebx; |
+ context_.edx = context_snapshot->edx; |
+ context_.ecx = context_snapshot->ecx; |
+ context_.eax = context_snapshot->eax; |
+ context_.ebp = context_snapshot->ebp; |
+ context_.eip = context_snapshot->eip; |
+ context_.cs = context_snapshot->cs; |
+ context_.eflags = context_snapshot->eflags; |
+ context_.esp = context_snapshot->esp; |
+ context_.ss = context_snapshot->ss; |
+ |
+ // This is effectively a memcpy() of a big structure. |
+ context_.fxsave = context_snapshot->fxsave; |
+} |
+ |
bool MinidumpContextX86Writer::WriteObject(FileWriterInterface* file_writer) { |
DCHECK_EQ(state(), kStateWritable); |
@@ -56,6 +149,46 @@ MinidumpContextAMD64Writer::MinidumpContextAMD64Writer() |
MinidumpContextAMD64Writer::~MinidumpContextAMD64Writer() { |
} |
+void MinidumpContextAMD64Writer::InitializeFromSnapshot( |
+ const CPUContextX86_64* context_snapshot) { |
+ DCHECK_EQ(state(), kStateMutable); |
+ DCHECK_EQ(context_.context_flags, kMinidumpContextAMD64); |
+ |
+ context_.context_flags = kMinidumpContextAMD64All; |
+ |
+ context_.mx_csr = context_snapshot->fxsave.mxcsr; |
+ context_.cs = context_snapshot->cs; |
+ context_.fs = context_snapshot->fs; |
+ context_.gs = context_snapshot->gs; |
+ context_.eflags = context_snapshot->rflags; |
+ context_.dr0 = context_snapshot->dr0; |
+ context_.dr1 = context_snapshot->dr1; |
+ context_.dr2 = context_snapshot->dr2; |
+ context_.dr3 = context_snapshot->dr3; |
+ context_.dr6 = context_snapshot->dr6; |
+ context_.dr7 = context_snapshot->dr7; |
+ context_.rax = context_snapshot->rax; |
+ context_.rcx = context_snapshot->rcx; |
+ context_.rdx = context_snapshot->rdx; |
+ context_.rbx = context_snapshot->rbx; |
+ context_.rsp = context_snapshot->rsp; |
+ context_.rbp = context_snapshot->rbp; |
+ context_.rsi = context_snapshot->rsi; |
+ context_.rdi = context_snapshot->rdi; |
+ context_.r8 = context_snapshot->r8; |
+ context_.r9 = context_snapshot->r9; |
+ context_.r10 = context_snapshot->r10; |
+ context_.r11 = context_snapshot->r11; |
+ context_.r12 = context_snapshot->r12; |
+ context_.r13 = context_snapshot->r13; |
+ context_.r14 = context_snapshot->r14; |
+ context_.r15 = context_snapshot->r15; |
+ context_.rip = context_snapshot->rip; |
+ |
+ // This is effectively a memcpy() of a big structure. |
+ context_.fxsave = context_snapshot->fxsave; |
+} |
+ |
size_t MinidumpContextAMD64Writer::Alignment() { |
DCHECK_GE(state(), kStateFrozen); |