CDB refactoring, introduce typedefs to remove version numbers.

Log exceptions with stacktrace.
This commit is contained in:
Friedemann Kleint
2009-04-21 12:30:12 +02:00
parent 6e9a237c76
commit 471d31ac9c
19 changed files with 353 additions and 125 deletions

View File

@@ -32,8 +32,12 @@
#include "cdbdebugengine_p.h"
#include "debuggermanager.h"
#include "breakhandler.h"
#include "cdbstacktracecontext.h"
enum { cppExceptionCode = 0xe06d7363 };
#include <QtCore/QDebug>
#include <QtCore/QTextStream>
namespace Debugger {
namespace Internal {
@@ -198,7 +202,7 @@ STDMETHODIMP CdbDebugEventCallbackBase::ChangeSymbolState(
return S_OK;
}
IDebugEventCallbacksWide *CdbDebugEventCallbackBase::getEventCallback(IDebugClient5 *clnt)
IDebugEventCallbacksWide *CdbDebugEventCallbackBase::getEventCallback(CIDebugClient *clnt)
{
IDebugEventCallbacksWide *rc = 0;
if (SUCCEEDED(clnt->GetEventCallbacksWide(&rc)))
@@ -231,26 +235,116 @@ STDMETHODIMP CdbDebugEventCallback::Breakpoint(THIS_ __in PDEBUG_BREAKPOINT2 Bp)
return S_OK;
}
static inline QString msgException(const EXCEPTION_RECORD64 *Exception, ULONG FirstChance)
// Simple exception formatting
void formatException(const EXCEPTION_RECORD64 *e, QTextStream &str)
{
return QString::fromLatin1("An exception occurred: Code=0x%1 FirstChance=%2").
arg(QString::number(Exception->ExceptionCode, 16)).
arg(FirstChance);
str.setIntegerBase(16);
str << "\nException at 0x" << e->ExceptionAddress
<< ", code: 0x" << e->ExceptionCode << ": ";
switch (e->ExceptionCode) {
case cppExceptionCode:
str << "C++ exception";
break;
case EXCEPTION_ACCESS_VIOLATION: {
const bool writeOperation = e->ExceptionInformation[0];
str << (writeOperation ? "write access violation" : "read access violation");
}
break;
case EXCEPTION_ARRAY_BOUNDS_EXCEEDED:
str << "arrary bounds exceeded";
break;
case EXCEPTION_BREAKPOINT:
str << "breakpoint";
break;
case EXCEPTION_DATATYPE_MISALIGNMENT:
str << "datatype misalignment";
break;
case EXCEPTION_FLT_DENORMAL_OPERAND:
str << "floating point exception";
break;
case EXCEPTION_FLT_DIVIDE_BY_ZERO:
str << "division by zero";
break;
case EXCEPTION_FLT_INEXACT_RESULT:
str << " floating-point operation cannot be represented exactly as a decimal fraction";
break;
case EXCEPTION_FLT_INVALID_OPERATION:
str << "invalid floating-point operation";
break;
case EXCEPTION_FLT_OVERFLOW:
str << "floating-point overflow";
break;
case EXCEPTION_FLT_STACK_CHECK:
str << "floating-point operation stack over/underflow";
break;
case EXCEPTION_FLT_UNDERFLOW:
str << "floating-point UNDERFLOW";
break;
case EXCEPTION_ILLEGAL_INSTRUCTION:
str << "invalid instruction";
break;
case EXCEPTION_IN_PAGE_ERROR:
str << "page in error";
break;
case EXCEPTION_INT_DIVIDE_BY_ZERO:
str << "integer division by zero";
break;
case EXCEPTION_INT_OVERFLOW:
str << "integer overflow";
break;
case EXCEPTION_INVALID_DISPOSITION:
str << "invalid disposition to exception dispatcher";
break;
case EXCEPTION_NONCONTINUABLE_EXCEPTION:
str << "attempt to continue execution after noncontinuable exception";
break;
case EXCEPTION_PRIV_INSTRUCTION:
str << "priviledged instruction";
break;
case EXCEPTION_SINGLE_STEP:
str << "single step";
break;
case EXCEPTION_STACK_OVERFLOW:
str << "stack_overflow";
break;
}
str << ", flags=0x" << e->ExceptionFlags;
if (e->ExceptionFlags == EXCEPTION_NONCONTINUABLE) {
str << " (execution cannot be continued)";
}
str << "\n\n";
str.setIntegerBase(10);
}
// Format exception with stacktrace in case of C++ exception
void formatException(const EXCEPTION_RECORD64 *e, CdbComInterfaces &cif, QTextStream &str)
{
formatException(e, str);
if (e->ExceptionCode == cppExceptionCode) {
QString errorMessage;
ULONG currentThreadId = 0;
cif.debugSystemObjects->GetCurrentThreadId(&currentThreadId);
if (CdbStackTraceContext *stc = CdbStackTraceContext::create(&cif, currentThreadId, &errorMessage)) {
str << "at:\n";
stc->format(str);
str <<'\n';
delete stc;
}
}
}
STDMETHODIMP CdbDebugEventCallback::Exception(
THIS_
__in PEXCEPTION_RECORD64 Exception,
__in ULONG FirstChance
__in ULONG /* FirstChance */
)
{
Q_UNUSED(Exception)
if (debugCDB)
qDebug() << Q_FUNC_INFO << msgException(Exception, FirstChance);
// First chance are harmless
if (!FirstChance)
qWarning("%s", qPrintable(msgException(Exception, FirstChance)));
QString msg;
{
QTextStream str(&msg);
formatException(Exception, m_pEngine->m_d->m_cif, str);
}
m_pEngine->m_d->m_debuggerManagerAccess->showApplicationOutput(msg);
return S_OK;
}
@@ -395,7 +489,7 @@ STDMETHODIMP IgnoreDebugEventCallback::GetInterestMask(THIS_ __out PULONG mask)
}
// --------- EventCallbackRedirector
EventCallbackRedirector::EventCallbackRedirector(IDebugClient5 *client, IDebugEventCallbacksWide *cb) :
EventCallbackRedirector::EventCallbackRedirector(CIDebugClient *client, IDebugEventCallbacksWide *cb) :
m_client(client),
m_oldCb(CdbDebugEventCallbackBase::getEventCallback(client))
{