diff --git a/release.bat b/release.bat index 3b6c1c74..2f4df24a 100644 --- a/release.bat +++ b/release.bat @@ -35,6 +35,7 @@ copy bin\x32\lz4.dll %RELEASEDIR%\bin_base\x32\lz4.dll copy bin\x32\TitanEngine.dll %RELEASEDIR%\bin_base\x32\TitanEngine.dll copy bin\x32\XEDParse.dll %RELEASEDIR%\bin_base\x32\XEDParse.dll copy bin\x32\yara.dll %RELEASEDIR%\bin_base\x32\yara.dll +copy bin\x32\snowman.dll %RELEASEDIR%\bin_base\x32\snowman.dll copy bin\x64\x64_bridge.dll %RELEASEDIR%\bin_base\x64\x64_bridge.dll copy bin\x64\x64_dbg.dll %RELEASEDIR%\bin_base\x64\x64_dbg.dll copy bin\x64\BeaEngine.dll %RELEASEDIR%\bin_base\x64\BeaEngine.dll @@ -48,6 +49,7 @@ copy bin\x64\lz4.dll %RELEASEDIR%\bin_base\x64\lz4.dll copy bin\x64\TitanEngine.dll %RELEASEDIR%\bin_base\x64\TitanEngine.dll copy bin\x64\XEDParse.dll %RELEASEDIR%\bin_base\x64\XEDParse.dll copy bin\x64\yara.dll %RELEASEDIR%\bin_base\x64\yara.dll +copy bin\x64\snowman.dll %RELEASEDIR%\bin_base\x64\snowman.dll echo help diff --git a/x64_dbg_gui/Project/Src/Bridge/Bridge.cpp b/x64_dbg_gui/Project/Src/Bridge/Bridge.cpp index c59c629b..4b48e20e 100644 --- a/x64_dbg_gui/Project/Src/Bridge/Bridge.cpp +++ b/x64_dbg_gui/Project/Src/Bridge/Bridge.cpp @@ -405,6 +405,11 @@ void Bridge::emitSetMenuIcon(int hMenu, const ICONDATA* icon) result.Wait(); } +void Bridge::emitShowCpu() +{ + emit showCpu(); +} + /************************************************************************************ Static Functions ************************************************************************************/ @@ -813,6 +818,12 @@ __declspec(dllexport) void* _gui_sendmessage(GUIMSG type, void* param1, void* pa } break; + case GUI_SHOW_CPU: + { + Bridge::getBridge()->emitShowCpu(); + } + break; + default: { diff --git a/x64_dbg_gui/Project/Src/Bridge/Bridge.h b/x64_dbg_gui/Project/Src/Bridge/Bridge.h index f42775b7..f663a9f5 100644 --- a/x64_dbg_gui/Project/Src/Bridge/Bridge.h +++ b/x64_dbg_gui/Project/Src/Bridge/Bridge.h @@ -86,6 +86,7 @@ public: void emitLoadSourceFile(const QString path, int line = 0, int selection = 0); void emitSetMenuEntryIcon(int hEntry, const ICONDATA* icon); void emitSetMenuIcon(int hMenu, const ICONDATA* icon); + void emitShowCpu(); //Public variables void* winId; @@ -154,6 +155,7 @@ signals: void loadSourceFile(const QString path, int line, int selection); void setIconMenuEntry(int hEntry, QIcon icon); void setIconMenu(int hMenu, QIcon icon); + void showCpu(); private: QMutex* mBridgeMutex; diff --git a/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.cpp b/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.cpp index c5ecc6db..991eec5c 100644 --- a/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.cpp +++ b/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.cpp @@ -246,6 +246,13 @@ void CPUDisassembly::contextMenuEvent(QContextMenuEvent* event) setupFollowReferenceMenu(wVA, mFollowMenu, false); if(DbgFunctions()->GetSourceFromAddr(wVA, 0, 0)) wMenu->addAction(mOpenSource); + + mDecompileMenu->clear(); + if(DbgFunctionGet(wVA, 0, 0)) + mDecompileMenu->addAction(mDecompileFunction); + mDecompileMenu->addAction(mDecompileSelection); + wMenu->addMenu(mDecompileMenu); + wMenu->addAction(mEnableHighlightingMode); wMenu->addSeparator(); @@ -524,6 +531,20 @@ void CPUDisassembly::setupRightClickContextMenu() mOpenSource = new QAction(QIcon(":/icons/images/source.png"), "Open Source File", this); connect(mOpenSource, SIGNAL(triggered()), this, SLOT(openSource())); + // Decompile menu + mDecompileMenu = new QMenu("Decompile"); + mDecompileMenu->setIcon(QIcon(":/icons/images/snowman.png")); + + // Decompile selection + mDecompileSelection = new QAction("Selection", this); + mDecompileSelection->setShortcutContext(Qt::WidgetShortcut); + this->addAction(mDecompileSelection); + connect(mDecompileSelection, SIGNAL(triggered()), this, SLOT(decompileSelection())); + + mDecompileFunction = new QAction("Function", this); + mDecompileFunction->setShortcutContext(Qt::WidgetShortcut); + this->addAction(mDecompileFunction); + connect(mDecompileFunction, SIGNAL(triggered()), this, SLOT(decompileFunction())); //-------------------- Find references to ----------------------- // Menu @@ -615,6 +636,8 @@ void CPUDisassembly::refreshShortcutsSlot() mCopySelection->setShortcut(ConfigShortcut("ActionCopy")); mCopyAddress->setShortcut(ConfigShortcut("ActionCopyAddress")); mSearchCommand->setShortcut(ConfigShortcut("ActionFind")); + mDecompileFunction->setShortcut(ConfigShortcut("ActionDecompileFunction")); + mDecompileSelection->setShortcut(ConfigShortcut("ActionDecompileSelection")); } void CPUDisassembly::gotoOrigin() @@ -1362,3 +1385,23 @@ void CPUDisassembly::openSource() Bridge::getBridge()->emitLoadSourceFile(szSourceFile, 0, line); emit displaySourceManagerWidget(); } + +void CPUDisassembly::decompileSelection() +{ + int_t addr = rvaToVa(getSelectionStart()); + int_t size = getSelectionSize(); + emit displaySnowmanWidget(); + emit decompileAt(addr, addr + size); +} + +void CPUDisassembly::decompileFunction() +{ + int_t addr = rvaToVa(getInitialSelection()); + duint start; + duint end; + if(DbgFunctionGet(addr, &start, &end)) + { + emit displaySnowmanWidget(); + emit decompileAt(start, end); + } +} diff --git a/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.h b/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.h index bb8f6e95..5ca0ac52 100644 --- a/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.h +++ b/x64_dbg_gui/Project/Src/Gui/CPUDisassembly.h @@ -28,6 +28,8 @@ signals: void displayReferencesWidget(); void displaySourceManagerWidget(); void showPatches(); + void decompileAt(int_t start, int_t end); + void displaySnowmanWidget(); public slots: void refreshShortcutsSlot(); @@ -74,6 +76,8 @@ public slots: void copyDisassembly(); void findCommand(); void openSource(); + void decompileSelection(); + void decompileFunction(); private: // Menus @@ -129,6 +133,10 @@ private: QAction* mCopyDisassembly; QAction* mOpenSource; + QMenu* mDecompileMenu; + QAction* mDecompileSelection; + QAction* mDecompileFunction; + GotoDialog* mGoto; }; diff --git a/x64_dbg_gui/Project/Src/Gui/MainWindow.cpp b/x64_dbg_gui/Project/Src/Gui/MainWindow.cpp index 120b5c79..4eb019ed 100644 --- a/x64_dbg_gui/Project/Src/Gui/MainWindow.cpp +++ b/x64_dbg_gui/Project/Src/Gui/MainWindow.cpp @@ -30,6 +30,7 @@ MainWindow::MainWindow(QWidget* parent) : QMainWindow(parent), ui(new Ui::MainWi connect(Bridge::getBridge(), SIGNAL(getStrWindow(QString, QString*)), this, SLOT(getStrWindow(QString, QString*))); connect(Bridge::getBridge(), SIGNAL(setIconMenu(int, QIcon)), this, SLOT(setIconMenu(int, QIcon))); connect(Bridge::getBridge(), SIGNAL(setIconMenuEntry(int, QIcon)), this, SLOT(setIconMenuEntry(int, QIcon))); + connect(Bridge::getBridge(), SIGNAL(showCpu()), this, SLOT(displayCpuWidget())); //setup menu api initMenuApi(); @@ -109,7 +110,7 @@ MainWindow::MainWindow(QWidget* parent) : QMainWindow(parent), ui(new Ui::MainWi mCpuWidget->setWindowIcon(QIcon(":/icons/images/processor-cpu.png")); // Reference Manager - mReferenceManager = new ReferenceManager(); + mReferenceManager = new ReferenceManager(this); Bridge::getBridge()->referenceManager = mReferenceManager; mReferenceManager->setWindowTitle("References"); mReferenceManager->setWindowIcon(QIcon(":/icons/images/search.png")); @@ -120,6 +121,11 @@ MainWindow::MainWindow(QWidget* parent) : QMainWindow(parent), ui(new Ui::MainWi mThreadView->setWindowTitle("Threads"); mThreadView->setWindowIcon(QIcon(":/icons/images/arrow-threads.png")); + // Snowman View (decompiler) + mSnowmanView = CreateSnowman(this); + mSnowmanView->setWindowTitle("Snowman"); + mSnowmanView->setWindowIcon(QIcon(":/icons/images/snowman.png")); + //Create the tab widget mTabWidget = new MHTabWidget(NULL); @@ -134,6 +140,7 @@ MainWindow::MainWindow(QWidget* parent) : QMainWindow(parent), ui(new Ui::MainWi mTabWidget->addTab(mSourceViewManager, mSourceViewManager->windowIcon(), mSourceViewManager->windowTitle()); mTabWidget->addTab(mReferenceManager, mReferenceManager->windowIcon(), mReferenceManager->windowTitle()); mTabWidget->addTab(mThreadView, mThreadView->windowIcon(), mThreadView->windowTitle()); + mTabWidget->addTab(mSnowmanView, mSnowmanView->windowIcon(), mSnowmanView->windowTitle()); setCentralWidget(mTabWidget); @@ -206,7 +213,9 @@ MainWindow::MainWindow(QWidget* parent) : QMainWindow(parent), ui(new Ui::MainWi connect(mCpuWidget->mDisas, SIGNAL(displayReferencesWidget()), this, SLOT(displayReferencesWidget())); connect(mCpuWidget->mDisas, SIGNAL(displaySourceManagerWidget()), this, SLOT(displaySourceViewWidget())); + connect(mCpuWidget->mDisas, SIGNAL(displaySnowmanWidget()), this, SLOT(displaySnowmanWidget())); connect(mCpuWidget->mDisas, SIGNAL(showPatches()), this, SLOT(patchWindow())); + connect(mCpuWidget->mDisas, SIGNAL(decompileAt(int_t, int_t)), this, SLOT(decompileAt(int_t, int_t))); connect(mCpuWidget->mDump, SIGNAL(displayReferencesWidget()), this, SLOT(displayReferencesWidget())); connect(mCpuWidget->mStack, SIGNAL(displayReferencesWidget()), this, SLOT(displayReferencesWidget())); connect(Config(), SIGNAL(shortcutsUpdated()), this, SLOT(refreshShortcuts())); @@ -244,6 +253,8 @@ void MainWindow::closeEvent(QCloseEvent* event) static bool bExecuteThread = true; if(bExecuteThread) { + CloseSnowman(mSnowmanView); + Sleep(100); bExecuteThread = false; CloseHandle(CreateThread(0, 0, closeThread, this, 0, 0)); } @@ -692,6 +703,13 @@ void MainWindow::displayThreadsWidget() setTab(mThreadView); } +void MainWindow::displaySnowmanWidget() +{ + mSnowmanView->show(); + mSnowmanView->setFocus(); + setTab(mSnowmanView); +} + void MainWindow::openSettings() { SettingsDialog settings(this); @@ -1096,3 +1114,8 @@ void MainWindow::changeCommandLine() GuiAddStatusBarMessage(QString("New command line: " + mLineEdit.editText + "\n").toUtf8().constData()); } } + +void MainWindow::decompileAt(int_t start, int_t end) +{ + DecompileAt(mSnowmanView, start, end); +} diff --git a/x64_dbg_gui/Project/Src/Gui/MainWindow.h b/x64_dbg_gui/Project/Src/Gui/MainWindow.h index 889fb74e..5c079a93 100644 --- a/x64_dbg_gui/Project/Src/Gui/MainWindow.h +++ b/x64_dbg_gui/Project/Src/Gui/MainWindow.h @@ -20,6 +20,7 @@ #include "StatusLabel.h" #include "UpdateChecker.h" #include "SourceViewerManager.h" +#include "SnowmanView.h" namespace Ui { @@ -66,6 +67,7 @@ public slots: void displaySourceViewWidget(); void displayReferencesWidget(); void displayThreadsWidget(); + void displaySnowmanWidget(); void openSettings(); void openAppearance(); void openCalculator(); @@ -100,6 +102,7 @@ public slots: void displayAttach(); void detach(); void changeCommandLine(); + void decompileAt(int_t start, int_t end); private: Ui::MainWindow* ui; @@ -118,6 +121,7 @@ private: ThreadView* mThreadView; PatchDialog* mPatchDialog; CalculatorDialog* mCalculatorDialog; + SnowmanView* mSnowmanView; StatusLabel* mStatusLabel; StatusLabel* mLastLogLabel; diff --git a/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/SnowmanView.h b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/SnowmanView.h new file mode 100644 index 00000000..c483cd1c --- /dev/null +++ b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/SnowmanView.h @@ -0,0 +1,15 @@ +#ifndef SNOWMANVIEW_H +#define SNOWMANVIEW_H + +#include + +class SnowmanView : public QWidget +{ + Q_OBJECT +}; + +extern "C" __declspec(dllexport) SnowmanView* CreateSnowman(QWidget* parent); +extern "C" __declspec(dllexport) void DecompileAt(SnowmanView* snowman, int_t start, int_t end); +extern "C" __declspec(dllexport) void CloseSnowman(SnowmanView* snowman); + +#endif // SNOWMANVIEW_H diff --git a/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x64.lib b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x64.lib new file mode 100644 index 00000000..1fa6fce9 Binary files /dev/null and b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x64.lib differ diff --git a/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x86.lib b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x86.lib new file mode 100644 index 00000000..f3e16a83 Binary files /dev/null and b/x64_dbg_gui/Project/Src/ThirdPartyLibs/snowman/snowman_x86.lib differ diff --git a/x64_dbg_gui/Project/Src/Utils/Configuration.cpp b/x64_dbg_gui/Project/Src/Utils/Configuration.cpp index adbdb7ff..a779aecd 100644 --- a/x64_dbg_gui/Project/Src/Utils/Configuration.cpp +++ b/x64_dbg_gui/Project/Src/Utils/Configuration.cpp @@ -259,6 +259,8 @@ Configuration::Configuration() : QObject() defaultShortcuts.insert("ActionFindReferences", Shortcut(tr("Actions -> Find References"), "Ctrl+R")); defaultShortcuts.insert("ActionHighlightingMode", Shortcut(tr("Actions -> Highlighting Mode"), "Ctrl+H")); defaultShortcuts.insert("ActionFind", Shortcut(tr("Actions -> Find"), "Ctrl+F")); + defaultShortcuts.insert("ActionDecompileFunction", Shortcut(tr("Actions -> Decompile Function"), "F5")); + defaultShortcuts.insert("ActionDecompileSelection", Shortcut(tr("Actions -> Decompile Selection"), "Shift+F5")); defaultShortcuts.insert("ActionIncreaseRegister", Shortcut(tr("Actions -> Increase Register"), "+")); defaultShortcuts.insert("ActionDecreaseRegister", Shortcut(tr("Actions -> Decrease Register"), "-")); diff --git a/x64_dbg_gui/Project/images/snowman.png b/x64_dbg_gui/Project/images/snowman.png new file mode 100644 index 00000000..01da03fb Binary files /dev/null and b/x64_dbg_gui/Project/images/snowman.png differ diff --git a/x64_dbg_gui/Project/resource.qrc b/x64_dbg_gui/Project/resource.qrc index 7366e7fc..9863433f 100644 --- a/x64_dbg_gui/Project/resource.qrc +++ b/x64_dbg_gui/Project/resource.qrc @@ -61,5 +61,6 @@ images/search-for.png images/highlight.png images/label.png + images/snowman.png diff --git a/x64_dbg_gui/Project/x64_dbg.pro b/x64_dbg_gui/Project/x64_dbg.pro index 89998924..add25103 100644 --- a/x64_dbg_gui/Project/x64_dbg.pro +++ b/x64_dbg_gui/Project/x64_dbg.pro @@ -200,30 +200,25 @@ FORMS += \ Src/Gui/DataCopyDialog.ui INCLUDEPATH += $$PWD/Src/Bridge +INCLUDEPATH += $$PWD/Src/ThirdPartyLibs/snowman LIBS += -luser32 - DEFINES += NOMINMAX +DEFINES += NOMINMAX !contains(QMAKE_HOST.arch, x86_64) { #message("x86 build") + ## Windows x86 (32bit) specific build here LIBS += -L"$$PWD/Src/ThirdPartyLibs/BeaEngine/" -lBeaEngine LIBS += -L"$$PWD/Src/Bridge/" -lx32bridge - ## Windows x86 (32bit) specific build here + LIBS += -L"$$PWD/Src/ThirdPartyLibs/snowman/" -lsnowman_x86 } else { #message("x86_64 build") + ## Windows x64 (64bit) specific build here LIBS += -L"$$PWD/Src/ThirdPartyLibs/BeaEngine/" -lBeaEngine_64 LIBS += -L"$$PWD/Src/Bridge/" -lx64bridge - ## Windows x64 (64bit) specific build here + LIBS += -L"$$PWD/Src/ThirdPartyLibs/snowman/" -lsnowman_x64 } RESOURCES += \ resource.qrc - - - - - - - -