⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 excepthandler.cpp

📁 CExceptionLogger
💻 CPP
📖 第 1 页 / 共 3 页
字号:
    else
      bContinue = FALSE;
  }
}

BOOL CExceptionLogger::EnumSymbols(PSYMBOL_INFO pSymbolInfo, ULONG /*SymbolSize*/, PVOID pUserContext)
{
  LogSymbol(pSymbolInfo, (STACKFRAME*) pUserContext);
  Log(_T("\r\n")); //Each symbol gets its own line

  //Continue enumeration
  return TRUE;
}

void CExceptionLogger::LogSymbol(PSYMBOL_INFO pSymbolInfo, STACKFRAME* pStackFrame)
{
  //Display details on the symbols type
  if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_PARAMETER)
    Log(_T("   Parameter: "));
  else if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_FUNCTION)
    Log(_T("   Function:  "));
  else if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_LOCAL)
    Log(_T("   Local:     "));
  else if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_CONSTANT)
    Log(_T("   Constant:  "));

  //Display the symbols name
  Log(_T(" %hs"), pSymbolInfo->Name);

  //Return immediately if the symbol is not for data
  if (pSymbolInfo->Tag != 7) //SymTagData is 7 as taken from the DIA SDK Header file cvconst.h
    return;

  //Display the value if valid
  if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_VALUEPRESENT)
    Log(_T(", Value: %I64d"), pSymbolInfo->Value);

  //Punt on register values
  if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_REGISTER)
  {
    Log(_T(", Register"));
    return;
  } 

  //Work out the address of the variable
  DWORD dwSymbolAddress = 0;
  if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_REGRELATIVE)
  {
    Log(_T(", Register Relative"));
    dwSymbolAddress = pStackFrame->AddrFrame.Offset;
    dwSymbolAddress += ((DWORD) pSymbolInfo->Address);
  }
  else 
  {
    if (pSymbolInfo->Flags & IMAGEHLP_SYMBOL_INFO_FRAMERELATIVE)
    {
      Log(_T(", Frame Relative"));
      return;
    }

    dwSymbolAddress = ((DWORD) pSymbolInfo->Address);
  }
  Log(_T(", Address: %08X"), dwSymbolAddress);

  BOOL bHandled = LogUDTSymbolDetails(pSymbolInfo->TypeIndex, pSymbolInfo->ModBase, dwSymbolAddress, 3);
  if (!bHandled)
  {
    //Get the type of the symbol
    DWORD dwType = GetBasicType(pSymbolInfo->TypeIndex, pSymbolInfo->ModBase);

    //Now that we have the type display the actual symbols value
    Log(_T(", "));
    LogBasicSymbolDetails(dwType, pSymbolInfo->Size, (void*)dwSymbolAddress);
  }
}

BOOL CExceptionLogger::LogUDTSymbolDetails(DWORD dwTypeIndex, DWORD64 modBase, DWORD dwOffset, DWORD dwIndent)
{
  __try
  {
    HANDLE hProcess = GetCurrentProcess();

    //First get the symbol name, which will either be the 
    //type name if a UDT or the member name otherwise
    wchar_t* pszTypeName = NULL;
    if (SymGetTypeInfo(hProcess, modBase, dwTypeIndex, TI_GET_SYMNAME, &pszTypeName))
    {
      Log(_T(" %ls"), pszTypeName);
      LocalFree(pszTypeName);
    }

    //Next we need to find out how many children this symbol has
    DWORD dwChildren = 0;
    SymGetTypeInfo(hProcess, modBase, dwTypeIndex, TI_GET_CHILDRENCOUNT, &dwChildren);

    //No children then return immediately
    if (dwChildren == 0)
      return FALSE;

    //Form the identation correctly
    Log(_T("\r\n"));
    for (DWORD j=0; j<dwIndent; j++)
      Log(_T("\t"));

    //Next get all the type Id's for all the children
    struct myTI_FIND_PARAMS : TI_FINDCHILDREN_PARAMS
    {
      ULONG nOtherChildren[1024];
    } myFindParams;
    myFindParams.Count = dwChildren;
    myFindParams.Start = 0;
    if (!SymGetTypeInfo(hProcess, modBase, dwTypeIndex, TI_FINDCHILDREN, &myFindParams))
      return FALSE;

    //Iterate thro all the children
    for (DWORD i=0; i<dwChildren; i++)
    {
      if (!LogUDTSymbolDetails(myFindParams.ChildId[i], modBase, dwOffset, dwIndent+1))
      {
        //This child item must be a basic type, so log it's info
      
        //First need to get it's offset relative to the parent
        DWORD dwMemberOffset = 0;
        SymGetTypeInfo(hProcess, modBase, myFindParams.ChildId[i], TI_GET_OFFSET, &dwMemberOffset);

        //Get the TypeID of this child
        DWORD dwTypeId = 0;
        SymGetTypeInfo(hProcess, modBase, myFindParams.ChildId[i], TI_GET_TYPEID, &dwTypeId);

        //Get the length of the child
        ULONG64 Length = 0;
        SymGetTypeInfo(hProcess, modBase, dwTypeId, TI_GET_LENGTH, &Length);

        //get the basic type of the child
        DWORD dwBasicType = GetBasicType(myFindParams.ChildId[i], modBase);

        //Now call the helper function to display all the child's details
        DWORD dwSymbolAddress = dwOffset + dwMemberOffset;     
        Log(_T(", "));
        LogBasicSymbolDetails(dwBasicType, Length, (void*)dwSymbolAddress);

        //Each child starts on a new line
        if (i<(dwChildren-1))
        {
          Log(_T("\r\n"));
          for (j=0; j<dwIndent; j++)
            Log(_T("\t"));
        }
      }
    }
  }
  __except(1)
  {
  }

  return TRUE;
}

void CExceptionLogger::LogBasicSymbolDetails(DWORD dwBasicType, DWORD64 dwLength, void* pSymbolAddress)
{
  __try
  {
    switch (dwBasicType)
    {
      case 0: //btNoType is 0 from DIA SDK header file cvconst.h
      {
        Log(_T("No Type"));
        break;
      }
      case 1: //btVoid is 1 from DIA SDK header file cvconst.h
      {
        Log(_T("void, Value: %08X"), *((DWORD*)pSymbolAddress));
        break;
      }
      case 2: //btChar is 2 from DIA SDK header file cvconst.h
      {
        BYTE* pAddr = (BYTE*) pSymbolAddress;
        Log(_T("char, len: %d, value(s): "), dwLength);
        for (DWORD64 i=0; i<dwLength; i++)
          Log(_T("%hc"), pAddr[i]);
        break;
      }
      case 6: //btInt is 6 from DIA SDK header file cvconst.h
      {
        //Handle the special case of a short
        if (dwLength == 2 || dwLength == 6)
        {
          short* pAddr = (short*) pSymbolAddress;
          DWORD64 dwSize = dwLength / sizeof(short);
          Log(_T("short, len: %d, value(s): "), dwSize);
          for (DWORD64 i=0; i<dwSize; i++)
            Log(_T("%d "), pAddr[i]);
        }
        else
        {
          int* pAddr = (int*) pSymbolAddress;
          DWORD64 dwSize = dwLength / sizeof(int);
          Log(_T("int, len: %d, value(s): "), dwSize);
          for (DWORD64 i=0; i<dwSize; i++)
            Log(_T("%d "), pAddr[i]);
        }
        break;
      }
      case 7: //btUInt is 7 from DIA SDK header file cvconst.h
      {
        //Handle the special case of a WORD
        if (dwLength == 2 || dwLength == 6)
        {
          WORD* pAddr = (WORD*) pSymbolAddress;
          DWORD64 dwSize = dwLength / sizeof(WORD);
          Log(_T("WORD, len: %d, value(s): "), dwSize);
          for (DWORD64 i=0; i<dwSize; i++)
            Log(_T("%u "), pAddr[i]);
        }
        else
        {
          unsigned int* pAddr = (unsigned int*) pSymbolAddress;
          DWORD64 dwSize = dwLength / sizeof(unsigned int);
          Log(_T("unsigned int, len: %d, value(s): "), dwSize);
          for (DWORD64 i=0; i<dwSize; i++)
            Log(_T("%u "), pAddr[i]);
        }
        break;
      }
      case 8: //btFloat is 8 from DIA SDK header file cvconst.h
      {
        if (dwLength == 4)
          Log(_T("float, Value: %f"), *((float*)pSymbolAddress));
        else if (dwLength == 8)
          Log(_T("double, Value: %lf"), *((double*)pSymbolAddress));
        else 
        {
          BYTE* pAddr = (BYTE*) pSymbolAddress;
          Log(_T("btFloat, len (bytes): %d, value(s): "), dwLength);
          for (DWORD64 i=0; i<dwLength; i++)
            Log(_T("%02X "), pAddr[i]);
        }
        break;
      }
      case 13: //btLong is 13 from DIA SDK header file cvconst.h
      {
        long* pAddr = (long*) pSymbolAddress;
        DWORD64 dwSize = dwLength / sizeof(long);
        Log(_T("long, len: %d, value(s): "), dwSize);
        for (DWORD64 i=0; i<dwSize; i++)
          Log(_T("%ld "), pAddr[i]);
        break;
      }
      case 14: //btULong is 14 from DIA SDK header file cvconst.h
      {
        unsigned long* pAddr = (unsigned long*) pSymbolAddress;
        DWORD64 dwSize = dwLength / sizeof(unsigned long);
        Log(_T("unsigned long, len: %d, value(s): "), dwSize);
        for (DWORD64 i=0; i<dwSize; i++)
          Log(_T("%lu "), pAddr[i]);
        break;
      }
      default:
      {
        Log(_T("Unknown Type"));
        break;
      }
    }
  }
  __except(1)
  {
    Log(_T("Error displaying symbol"));
  }
}

DWORD CExceptionLogger::GetBasicType(DWORD dwTypeIndex, DWORD64 modBase)
{
  HANDLE hProcess = GetCurrentProcess();

  DWORD dwType;
  if (SymGetTypeInfo(hProcess, modBase, dwTypeIndex, TI_GET_BASETYPE, &dwType))
    return dwType;

  DWORD dwTypeID;
  if (SymGetTypeInfo(hProcess, modBase, dwTypeIndex, TI_GET_TYPEID, &dwTypeID))
  {
    if (SymGetTypeInfo(hProcess, modBase, dwTypeID, TI_GET_BASETYPE, &dwType) )
      return dwType;
  }

  return 0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -