mirror of
https://github.com/rizinorg/cutter.git
synced 2025-01-31 08:37:26 +00:00
Added new graph view (WIP)
* This known unstable just a PoC
This commit is contained in:
parent
97ee9f17b6
commit
25a4d06697
@ -18,7 +18,7 @@ QT += core gui widgets webengine webenginewidgets
|
||||
|
||||
QT_CONFIG -= no-pkg-config
|
||||
|
||||
CONFIG += c++11
|
||||
CONFIG += debug c++11
|
||||
|
||||
# Define the preprocessor macro to get the application version in our application.
|
||||
DEFINES += APP_VERSION=\\\"$$VERSION\\\"
|
||||
@ -56,7 +56,6 @@ SOURCES += \
|
||||
widgets/commentswidget.cpp \
|
||||
widgets/stringswidget.cpp \
|
||||
widgets/flagswidget.cpp \
|
||||
widgets/memorywidget.cpp \
|
||||
widgets/exportswidget.cpp \
|
||||
widgets/sdbdock.cpp \
|
||||
analthread.cpp \
|
||||
@ -71,7 +70,10 @@ SOURCES += \
|
||||
widgets/consolewidget.cpp \
|
||||
radarewebserver.cpp \
|
||||
widgets/entrypointwidget.cpp \
|
||||
dialogs/flagdialog.cpp
|
||||
dialogs/flagdialog.cpp \
|
||||
widgets/DisassemblerGraphView.cpp \
|
||||
widgets/MemoryWidget.cpp \
|
||||
utils/RichTextPainter.cpp
|
||||
|
||||
HEADERS += \
|
||||
mainwindow.h \
|
||||
@ -94,7 +96,6 @@ HEADERS += \
|
||||
widgets/commentswidget.h \
|
||||
widgets/stringswidget.h \
|
||||
widgets/flagswidget.h \
|
||||
widgets/memorywidget.h \
|
||||
widgets/exportswidget.h \
|
||||
widgets/sdbdock.h \
|
||||
analthread.h \
|
||||
@ -112,7 +113,11 @@ HEADERS += \
|
||||
settings.h \
|
||||
widgets/entrypointwidget.h \
|
||||
cutter.h \
|
||||
dialogs/flagdialog.h
|
||||
dialogs/flagdialog.h \
|
||||
widgets/DisassemblerGraphView.h \
|
||||
widgets/MemoryWidget.h \
|
||||
utils/RichTextPainter.h \
|
||||
utils/CachedFontMetrics.h
|
||||
FORMS += \
|
||||
mainwindow.ui \
|
||||
newfiledialog.ui \
|
||||
@ -128,7 +133,6 @@ FORMS += \
|
||||
widgets/commentswidget.ui \
|
||||
widgets/stringswidget.ui \
|
||||
widgets/flagswidget.ui \
|
||||
widgets/memorywidget.ui \
|
||||
widgets/exportswidget.ui \
|
||||
widgets/sdbdock.ui \
|
||||
dialogs/commentsdialog.ui \
|
||||
@ -138,7 +142,8 @@ FORMS += \
|
||||
widgets/sectionsdock.ui \
|
||||
widgets/consolewidget.ui \
|
||||
widgets/entrypointwidget.ui \
|
||||
dialogs/flagdialog.ui
|
||||
dialogs/flagdialog.ui \
|
||||
widgets/MemoryWidget.ui
|
||||
|
||||
RESOURCES += \
|
||||
resources.qrc
|
||||
|
@ -39,7 +39,7 @@
|
||||
#include "newfiledialog.h"
|
||||
#include "helpers.h"
|
||||
|
||||
#include "widgets/memorywidget.h"
|
||||
#include "widgets/MemoryWidget.h"
|
||||
#include "widgets/functionswidget.h"
|
||||
#include "widgets/sectionswidget.h"
|
||||
#include "widgets/commentswidget.h"
|
||||
@ -60,6 +60,7 @@
|
||||
#include "settings.h"
|
||||
#include "optionsdialog.h"
|
||||
#include "widgets/entrypointwidget.h"
|
||||
#include "widgets/DisassemblerGraphView.h"
|
||||
|
||||
// graphics
|
||||
#include <QGraphicsEllipseItem>
|
||||
@ -204,7 +205,7 @@ void MainWindow::initUI()
|
||||
/*
|
||||
* Dock Widgets
|
||||
*/
|
||||
dockWidgets.reserve(11);
|
||||
dockWidgets.reserve(12);
|
||||
|
||||
// Add Memory DockWidget
|
||||
this->memoryDock = new MemoryWidget(this);
|
||||
|
@ -5,7 +5,7 @@
|
||||
#include "helpers.h"
|
||||
|
||||
// TODO: remove us
|
||||
#include "widgets/memorywidget.h"
|
||||
#include "widgets/MemoryWidget.h"
|
||||
#include "widgets/notepad.h"
|
||||
#include "settings.h"
|
||||
|
||||
|
63
src/utils/CachedFontMetrics.h
Normal file
63
src/utils/CachedFontMetrics.h
Normal file
@ -0,0 +1,63 @@
|
||||
#ifndef CACHEDFONTMETRICS_H
|
||||
#define CACHEDFONTMETRICS_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QFont>
|
||||
#include <QFontMetrics>
|
||||
|
||||
class CachedFontMetrics : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit CachedFontMetrics(QObject* parent, const QFont & font)
|
||||
: QObject(parent),
|
||||
mFontMetrics(font)
|
||||
{
|
||||
memset(mWidths, 0, sizeof(mWidths));
|
||||
mHeight = mFontMetrics.height();
|
||||
}
|
||||
|
||||
int width(const QChar & ch)
|
||||
{
|
||||
auto unicode = ch.unicode();
|
||||
if(unicode >= 0xD800)
|
||||
{
|
||||
if(unicode >= 0xE000)
|
||||
unicode -= 0xE000 - 0xD800;
|
||||
else
|
||||
// is lonely surrogate
|
||||
return mFontMetrics.width(ch);
|
||||
}
|
||||
if(!mWidths[unicode])
|
||||
return mWidths[unicode] = mFontMetrics.width(ch);
|
||||
return mWidths[unicode];
|
||||
}
|
||||
|
||||
int width(const QString & text)
|
||||
{
|
||||
int result = 0;
|
||||
QChar temp;
|
||||
for(const QChar & ch : text)
|
||||
{
|
||||
if(ch.isHighSurrogate())
|
||||
temp = ch;
|
||||
else if(ch.isLowSurrogate())
|
||||
result += mFontMetrics.width(QString(temp) + ch);
|
||||
else
|
||||
result += width(ch);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
int height()
|
||||
{
|
||||
return mHeight;
|
||||
}
|
||||
|
||||
private:
|
||||
QFontMetrics mFontMetrics;
|
||||
uchar mWidths[0x10000 - 0xE000 + 0xD800];
|
||||
int mHeight;
|
||||
};
|
||||
|
||||
#endif // CACHEDFONTMETRICS_H
|
103
src/utils/RichTextPainter.cpp
Normal file
103
src/utils/RichTextPainter.cpp
Normal file
@ -0,0 +1,103 @@
|
||||
/* x64dbg RichTextPainter */
|
||||
#include "RichTextPainter.h"
|
||||
#include "CachedFontMetrics.h"
|
||||
#include <QPainter>
|
||||
|
||||
//TODO: fix performance (possibly use QTextLayout?)
|
||||
void RichTextPainter::paintRichText(QPainter* painter, int x, int y, int w, int h, int xinc, const List & richText, CachedFontMetrics* fontMetrics)
|
||||
{
|
||||
QPen pen;
|
||||
QPen highlightPen;
|
||||
QBrush brush(Qt::cyan);
|
||||
for(const CustomRichText_t & curRichText : richText)
|
||||
{
|
||||
int textWidth = fontMetrics->width(curRichText.text);
|
||||
int backgroundWidth = textWidth;
|
||||
if(backgroundWidth + xinc > w)
|
||||
backgroundWidth = w - xinc;
|
||||
if(backgroundWidth <= 0) //stop drawing when going outside the specified width
|
||||
break;
|
||||
switch(curRichText.flags)
|
||||
{
|
||||
case FlagNone: //defaults
|
||||
break;
|
||||
case FlagColor: //color only
|
||||
pen.setColor(curRichText.textColor);
|
||||
painter->setPen(pen);
|
||||
break;
|
||||
case FlagBackground: //background only
|
||||
if(backgroundWidth > 0 && curRichText.textBackground.alpha())
|
||||
{
|
||||
brush.setColor(curRichText.textBackground);
|
||||
painter->fillRect(QRect(x + xinc, y, backgroundWidth, h), brush);
|
||||
}
|
||||
break;
|
||||
case FlagAll: //color+background
|
||||
if(backgroundWidth > 0 && curRichText.textBackground.alpha())
|
||||
{
|
||||
brush.setColor(curRichText.textBackground);
|
||||
painter->fillRect(QRect(x + xinc, y, backgroundWidth, h), brush);
|
||||
}
|
||||
pen.setColor(curRichText.textColor);
|
||||
painter->setPen(pen);
|
||||
break;
|
||||
}
|
||||
painter->drawText(QRect(x + xinc, y, w - xinc, h), Qt::TextBypassShaping, curRichText.text);
|
||||
if(curRichText.highlight && curRichText.highlightColor.alpha())
|
||||
{
|
||||
highlightPen.setColor(curRichText.highlightColor);
|
||||
highlightPen.setWidth(curRichText.highlightWidth);
|
||||
painter->setPen(highlightPen);
|
||||
int highlightOffsetX = curRichText.highlightConnectPrev ? -1 : 1;
|
||||
painter->drawLine(x + xinc + highlightOffsetX, y + h - 1, x + xinc + backgroundWidth - 1, y + h - 1);
|
||||
}
|
||||
xinc += textWidth;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief RichTextPainter::htmlRichText Convert rich text in x64dbg to HTML, for use by other applications
|
||||
* @param richText The rich text to be converted to HTML format
|
||||
* @param textHtml The HTML source. Any previous content will be preserved and new content will be appended at the end.
|
||||
* @param textPlain The plain text. Any previous content will be preserved and new content will be appended at the end.
|
||||
*/
|
||||
void RichTextPainter::htmlRichText(const List & richText, QString & textHtml, QString & textPlain)
|
||||
{
|
||||
for(const CustomRichText_t & curRichText : richText)
|
||||
{
|
||||
if(curRichText.text == " ") //blank
|
||||
{
|
||||
textHtml += " ";
|
||||
textPlain += " ";
|
||||
continue;
|
||||
}
|
||||
switch(curRichText.flags)
|
||||
{
|
||||
case FlagNone: //defaults
|
||||
textHtml += "<span>";
|
||||
break;
|
||||
case FlagColor: //color only
|
||||
textHtml += QString("<span style=\"color:%1\">").arg(curRichText.textColor.name());
|
||||
break;
|
||||
case FlagBackground: //background only
|
||||
if(curRichText.textBackground != Qt::transparent) // QColor::name() returns "#000000" for transparent color. That's not desired. Leave it blank.
|
||||
textHtml += QString("<span style=\"background-color:%1\">").arg(curRichText.textBackground.name());
|
||||
else
|
||||
textHtml += QString("<span>");
|
||||
break;
|
||||
case FlagAll: //color+background
|
||||
if(curRichText.textBackground != Qt::transparent) // QColor::name() returns "#000000" for transparent color. That's not desired. Leave it blank.
|
||||
textHtml += QString("<span style=\"color:%1; background-color:%2\">").arg(curRichText.textColor.name(), curRichText.textBackground.name());
|
||||
else
|
||||
textHtml += QString("<span style=\"color:%1\">").arg(curRichText.textColor.name());
|
||||
break;
|
||||
}
|
||||
if(curRichText.highlight) //Underline highlighted token
|
||||
textHtml += "<u>";
|
||||
textHtml += curRichText.text.toHtmlEscaped();
|
||||
if(curRichText.highlight)
|
||||
textHtml += "</u>";
|
||||
textHtml += "</span>"; //Close the tag
|
||||
textPlain += curRichText.text;
|
||||
}
|
||||
}
|
43
src/utils/RichTextPainter.h
Normal file
43
src/utils/RichTextPainter.h
Normal file
@ -0,0 +1,43 @@
|
||||
/* x64dbg RichTextPainter */
|
||||
#ifndef RICHTEXTPAINTER_H
|
||||
#define RICHTEXTPAINTER_H
|
||||
|
||||
#include <QString>
|
||||
#include <QColor>
|
||||
#include <vector>
|
||||
|
||||
class CachedFontMetrics;
|
||||
class QPainter;
|
||||
|
||||
class RichTextPainter
|
||||
{
|
||||
public:
|
||||
//structures
|
||||
enum CustomRichTextFlags
|
||||
{
|
||||
FlagNone,
|
||||
FlagColor,
|
||||
FlagBackground,
|
||||
FlagAll
|
||||
};
|
||||
|
||||
struct CustomRichText_t
|
||||
{
|
||||
QString text;
|
||||
QColor textColor;
|
||||
QColor textBackground;
|
||||
CustomRichTextFlags flags;
|
||||
bool highlight;
|
||||
QColor highlightColor;
|
||||
int highlightWidth = 2;
|
||||
bool highlightConnectPrev = false;
|
||||
};
|
||||
|
||||
typedef std::vector<CustomRichText_t> List;
|
||||
|
||||
//functions
|
||||
static void paintRichText(QPainter* painter, int x, int y, int w, int h, int xinc, const List & richText, CachedFontMetrics* fontMetrics);
|
||||
static void htmlRichText(const List & richText, QString & textHtml, QString & textPlain);
|
||||
};
|
||||
|
||||
#endif // RICHTEXTPAINTER_H
|
2142
src/widgets/DisassemblerGraphView.cpp
Normal file
2142
src/widgets/DisassemblerGraphView.cpp
Normal file
File diff suppressed because it is too large
Load Diff
363
src/widgets/DisassemblerGraphView.h
Normal file
363
src/widgets/DisassemblerGraphView.h
Normal file
@ -0,0 +1,363 @@
|
||||
/* x64dbg DisassemblerGraphView */
|
||||
#ifndef DISASSEMBLERGRAPHVIEW_H
|
||||
#define DISASSEMBLERGRAPHVIEW_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QWidget>
|
||||
#include <QAbstractScrollArea>
|
||||
#include <QPaintEvent>
|
||||
#include <QTimer>
|
||||
#include <QSize>
|
||||
#include <QResizeEvent>
|
||||
#include <tuple>
|
||||
#include <unordered_map>
|
||||
#include <unordered_set>
|
||||
#include <queue>
|
||||
#include <QMutex>
|
||||
#include <QMenu>
|
||||
#include <QJsonDocument>
|
||||
#include <QJsonArray>
|
||||
#include <QJsonObject>
|
||||
#include "cutter.h"
|
||||
#include "utils/RichTextPainter.h"
|
||||
#include "utils/CachedFontMetrics.h"
|
||||
|
||||
#define duint ut64
|
||||
|
||||
class MenuBuilder;
|
||||
class CachedFontMetrics;
|
||||
class GotoDialog;
|
||||
class XrefBrowseDialog;
|
||||
|
||||
class DisassemblerGraphView : public QAbstractScrollArea
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
struct DisassemblerBlock;
|
||||
|
||||
struct Point
|
||||
{
|
||||
int row; //point[0]
|
||||
int col; //point[1]
|
||||
int index; //point[2]
|
||||
};
|
||||
|
||||
struct DisassemblerEdge
|
||||
{
|
||||
QColor color;
|
||||
DisassemblerBlock* dest;
|
||||
std::vector<Point> points;
|
||||
int start_index = 0;
|
||||
|
||||
QPolygonF polyline;
|
||||
QPolygonF arrow;
|
||||
|
||||
void addPoint(int row, int col, int index = 0)
|
||||
{
|
||||
Point point = {row, col, 0};
|
||||
this->points.push_back(point);
|
||||
if(int(this->points.size()) > 1)
|
||||
this->points[this->points.size() - 2].index = index;
|
||||
}
|
||||
};
|
||||
|
||||
struct Token
|
||||
{
|
||||
int start; //token[0]
|
||||
int length; //token[1]
|
||||
QString type; //token[2]
|
||||
duint addr; //token[3]
|
||||
QString name; //token[4]
|
||||
};
|
||||
|
||||
struct HighlightToken
|
||||
{
|
||||
QString type; //highlight_token[0]
|
||||
duint addr; //highlight_token[1]
|
||||
QString name; //highlight_token[2]
|
||||
|
||||
bool equalsToken(const Token & token)
|
||||
{
|
||||
return this->type == token.type &&
|
||||
this->addr == token.addr &&
|
||||
this->name == token.name;
|
||||
}
|
||||
|
||||
static HighlightToken* fromToken(const Token & token)
|
||||
{
|
||||
//TODO: memory leaks
|
||||
auto result = new HighlightToken();
|
||||
result->type = token.type;
|
||||
result->addr = token.addr;
|
||||
result->name = token.name;
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
struct Text
|
||||
{
|
||||
std::vector<RichTextPainter::List> lines;
|
||||
|
||||
Text() {}
|
||||
|
||||
Text(const QString & text, QColor color, QColor background)
|
||||
{
|
||||
RichTextPainter::List richText;
|
||||
RichTextPainter::CustomRichText_t rt;
|
||||
rt.highlight = false;
|
||||
rt.text = text;
|
||||
rt.textColor = color;
|
||||
rt.textBackground = background;
|
||||
rt.flags = rt.textBackground.alpha() ? RichTextPainter::FlagAll : RichTextPainter::FlagColor;
|
||||
richText.push_back(rt);
|
||||
lines.push_back(richText);
|
||||
}
|
||||
|
||||
Text(const RichTextPainter::List & richText)
|
||||
{
|
||||
lines.push_back(richText);
|
||||
}
|
||||
|
||||
QString ToQString() const
|
||||
{
|
||||
QString result;
|
||||
for(auto & line : lines)
|
||||
{
|
||||
for(auto & t : line)
|
||||
{
|
||||
result += t.text;
|
||||
}
|
||||
}
|
||||
return std::move(result);
|
||||
}
|
||||
};
|
||||
|
||||
struct Instr
|
||||
{
|
||||
duint addr = 0;
|
||||
Text text;
|
||||
std::vector<unsigned char> opcode; //instruction bytes
|
||||
};
|
||||
|
||||
struct Block
|
||||
{
|
||||
Text header_text;
|
||||
std::vector<Instr> instrs;
|
||||
std::vector<duint> exits;
|
||||
duint entry = 0;
|
||||
duint true_path = 0;
|
||||
duint false_path = 0;
|
||||
bool terminal = false;
|
||||
bool indirectcall = false;
|
||||
};
|
||||
|
||||
struct DisassemblerBlock
|
||||
{
|
||||
DisassemblerBlock() {}
|
||||
explicit DisassemblerBlock(Block & block)
|
||||
: block(block) {}
|
||||
|
||||
Block block;
|
||||
std::vector<DisassemblerEdge> edges;
|
||||
std::vector<duint> incoming;
|
||||
std::vector<duint> new_exits;
|
||||
|
||||
qreal x = 0.0;
|
||||
qreal y = 0.0;
|
||||
int width = 0;
|
||||
int height = 0;
|
||||
int col = 0;
|
||||
int col_count = 0;
|
||||
int row = 0;
|
||||
int row_count = 0;
|
||||
};
|
||||
|
||||
struct Function
|
||||
{
|
||||
bool ready;
|
||||
duint entry;
|
||||
duint update_id;
|
||||
std::vector<Block> blocks;
|
||||
};
|
||||
|
||||
struct Analysis
|
||||
{
|
||||
duint entry = 0;
|
||||
std::unordered_map<duint, Function> functions;
|
||||
bool ready = false;
|
||||
duint update_id = 0;
|
||||
QString status = "Analyzing...";
|
||||
|
||||
bool find_instr(duint addr, duint & func, duint & instr)
|
||||
{
|
||||
//TODO implement
|
||||
Q_UNUSED(addr);
|
||||
Q_UNUSED(func);
|
||||
Q_UNUSED(instr);
|
||||
return false;
|
||||
}
|
||||
|
||||
//dummy class
|
||||
};
|
||||
|
||||
enum class LayoutType
|
||||
{
|
||||
Wide,
|
||||
Medium,
|
||||
Narrow,
|
||||
};
|
||||
|
||||
DisassemblerGraphView(QWidget *parent, CutterCore *core);
|
||||
~DisassemblerGraphView();
|
||||
void initFont();
|
||||
void adjustSize(int width, int height);
|
||||
void resizeEvent(QResizeEvent* event);
|
||||
duint get_cursor_pos();
|
||||
void set_cursor_pos(duint addr);
|
||||
std::tuple<duint, duint> get_selection_range();
|
||||
void set_selection_range(std::tuple<duint, duint> range);
|
||||
void copy_address();
|
||||
//void analysis_thread_proc();
|
||||
//void closeRequest();
|
||||
void paintNormal(QPainter & p, QRect & viewportRect, int xofs, int yofs);
|
||||
void paintOverview(QPainter & p, QRect & viewportRect, int xofs, int yofs);
|
||||
void paintEvent(QPaintEvent* event);
|
||||
bool isMouseEventInBlock(QMouseEvent* event);
|
||||
duint getInstrForMouseEvent(QMouseEvent* event);
|
||||
bool getTokenForMouseEvent(QMouseEvent* event, Token & token);
|
||||
bool find_instr(duint addr, Instr & instr);
|
||||
void mousePressEvent(QMouseEvent* event);
|
||||
void mouseMoveEvent(QMouseEvent* event);
|
||||
void mouseReleaseEvent(QMouseEvent* event);
|
||||
void mouseDoubleClickEvent(QMouseEvent* event);
|
||||
void prepareGraphNode(DisassemblerBlock & block);
|
||||
void adjustGraphLayout(DisassemblerBlock & block, int col, int row);
|
||||
void computeGraphLayout(DisassemblerBlock & block);
|
||||
void setupContextMenu();
|
||||
void keyPressEvent(QKeyEvent* event);
|
||||
|
||||
template<typename T>
|
||||
using Matrix = std::vector<std::vector<T>>;
|
||||
using EdgesVector = Matrix<std::vector<bool>>;
|
||||
bool isEdgeMarked(EdgesVector & edges, int row, int col, int index);
|
||||
void markEdge(EdgesVector & edges, int row, int col, int index, bool used = true);
|
||||
int findHorizEdgeIndex(EdgesVector & edges, int row, int min_col, int max_col);
|
||||
int findVertEdgeIndex(EdgesVector & edges, int col, int min_row, int max_row);
|
||||
DisassemblerEdge routeEdge(EdgesVector & horiz_edges, EdgesVector & vert_edges, Matrix<bool> & edge_valid, DisassemblerBlock & start, DisassemblerBlock & end, QColor color);
|
||||
void renderFunction(Function & func);
|
||||
void show_cur_instr(bool force = false);
|
||||
bool navigate(duint addr);
|
||||
void fontChanged();
|
||||
void setGraphLayout(LayoutType layout);
|
||||
|
||||
//VaHistory mHistory;
|
||||
|
||||
signals:
|
||||
void displaySnowmanWidget();
|
||||
|
||||
public slots:
|
||||
void updateTimerEvent();
|
||||
//void loadGraphSlot(BridgeCFGraphList* graph, duint addr);
|
||||
void graphAtSlot(duint addr);
|
||||
void updateGraphSlot();
|
||||
void followDisassemblerSlot();
|
||||
void colorsUpdatedSlot();
|
||||
void fontsUpdatedSlot();
|
||||
void shortcutsUpdatedSlot();
|
||||
void toggleOverviewSlot();
|
||||
void toggleSummarySlot();
|
||||
//void selectionGetSlot(SELECTIONDATA* selection);
|
||||
void tokenizerConfigUpdatedSlot();
|
||||
void loadCurrentGraph();
|
||||
//void disassembleAtSlot(dsint va, dsint cip);
|
||||
void gotoExpressionSlot();
|
||||
void gotoOriginSlot();
|
||||
void gotoPreviousSlot();
|
||||
void gotoNextSlot();
|
||||
void toggleSyncOriginSlot();
|
||||
void followActionSlot();
|
||||
void refreshSlot();
|
||||
void saveImageSlot();
|
||||
void setCommentSlot();
|
||||
void setLabelSlot();
|
||||
void xrefSlot();
|
||||
void decompileSlot();
|
||||
|
||||
private:
|
||||
CutterCore *mCore;
|
||||
QString status;
|
||||
Analysis analysis;
|
||||
duint function;
|
||||
QTimer* updateTimer;
|
||||
int baseline;
|
||||
qreal charWidth;
|
||||
int charHeight;
|
||||
int charOffset;
|
||||
int width;
|
||||
int height;
|
||||
int renderWidth;
|
||||
int renderHeight;
|
||||
int renderXOfs;
|
||||
int renderYOfs;
|
||||
duint cur_instr;
|
||||
int scroll_base_x;
|
||||
int scroll_base_y;
|
||||
duint update_id;
|
||||
bool scroll_mode;
|
||||
bool ready;
|
||||
int* desired_pos;
|
||||
std::unordered_map<duint, DisassemblerBlock> blocks;
|
||||
HighlightToken* highlight_token;
|
||||
std::vector<int> col_edge_x;
|
||||
std::vector<int> row_edge_y;
|
||||
CachedFontMetrics* mFontMetrics;
|
||||
MenuBuilder* mMenuBuilder;
|
||||
bool drawOverview;
|
||||
bool onlySummary;
|
||||
bool syncOrigin;
|
||||
int overviewXOfs;
|
||||
int overviewYOfs;
|
||||
qreal overviewScale;
|
||||
duint mCip;
|
||||
bool forceCenter;
|
||||
bool saveGraph;
|
||||
bool mHistoryLock; //Don't add a history while going to previous/next
|
||||
LayoutType layoutType;
|
||||
|
||||
QAction* mToggleOverview;
|
||||
QAction* mToggleSummary;
|
||||
QAction* mToggleSyncOrigin;
|
||||
|
||||
QColor disassemblyBackgroundColor;
|
||||
QColor disassemblySelectionColor;
|
||||
QColor disassemblyTracedColor;
|
||||
QColor disassemblyTracedSelectionColor;
|
||||
QColor jmpColor;
|
||||
QColor brtrueColor;
|
||||
QColor brfalseColor;
|
||||
QColor retShadowColor;
|
||||
QColor indirectcallShadowColor;
|
||||
QColor backgroundColor;
|
||||
QColor mAutoCommentColor;
|
||||
QColor mAutoCommentBackgroundColor;
|
||||
QColor mCommentColor;
|
||||
QColor mCommentBackgroundColor;
|
||||
QColor mLabelColor;
|
||||
QColor mLabelBackgroundColor;
|
||||
QColor graphNodeColor;
|
||||
QColor mAddressColor;
|
||||
QColor mAddressBackgroundColor;
|
||||
QColor mCipColor;
|
||||
QColor mBreakpointColor;
|
||||
QColor mDisabledBreakpointColor;
|
||||
|
||||
//BridgeCFGraph currentGraph;
|
||||
std::unordered_map<duint, duint> currentBlockMap;
|
||||
//QBeaEngine disasm;
|
||||
GotoDialog* mGoto;
|
||||
XrefBrowseDialog* mXrefDlg;
|
||||
|
||||
void addReferenceAction(QMenu* menu, duint addr);
|
||||
};
|
||||
|
||||
#endif // DISASSEMBLERGRAPHVIEW_H
|
@ -1,5 +1,6 @@
|
||||
#include "memorywidget.h"
|
||||
#include "ui_memorywidget.h"
|
||||
#include "MemoryWidget.h"
|
||||
#include "ui_MemoryWidget.h"
|
||||
#include "DisassemblerGraphView.h"
|
||||
|
||||
#include "mainwindow.h"
|
||||
#include "helpers.h"
|
||||
@ -159,6 +160,11 @@ MemoryWidget::MemoryWidget(MainWindow *main) :
|
||||
connect(new QShortcut(Qt::SHIFT + Qt::Key_X, ui->disasTextEdit_2),
|
||||
SIGNAL(activated()), this, SLOT(showXrefsDialog()));
|
||||
|
||||
// Create Graph View
|
||||
ui->tabGraph->setLayout(new QGridLayout);
|
||||
mGraphView = new DisassemblerGraphView(ui->tabGraph, main->core);
|
||||
ui->tabGraph->layout()->addWidget(mGraphView);
|
||||
|
||||
// Space to switch between disassembly and graph
|
||||
QShortcut *graph_shortcut = new QShortcut(QKeySequence(Qt::Key_Space), this->main);
|
||||
connect(graph_shortcut, SIGNAL(activated()), this, SLOT(cycleViews()));
|
||||
@ -1136,7 +1142,7 @@ void MemoryWidget::on_actionSettings_menu_1_triggered()
|
||||
bool ok = true;
|
||||
|
||||
// QFont font = QFont("Monospace", 8);
|
||||
|
||||
// TODO Use global configuration
|
||||
QFont font = QFontDialog::getFont(&ok, ui->disasTextEdit_2->font(), this);
|
||||
|
||||
if (ok)
|
||||
@ -1267,6 +1273,12 @@ void MemoryWidget::on_graphButton_2_clicked()
|
||||
ui->memSideTabWidget_2->setCurrentIndex(0);
|
||||
}
|
||||
|
||||
void MemoryWidget::on_graphButton_clicked()
|
||||
{
|
||||
ui->memTabWidget->setCurrentIndex(3);
|
||||
ui->memSideTabWidget_2->setCurrentIndex(3);
|
||||
}
|
||||
|
||||
void MemoryWidget::on_actionSend_to_Notepad_triggered()
|
||||
{
|
||||
QTextCursor cursor = ui->disasTextEdit_2->textCursor();
|
@ -15,6 +15,7 @@
|
||||
#include "hexascii_highlighter.h"
|
||||
#include "hexhighlighter.h"
|
||||
#include "dashboard.h"
|
||||
#include "widgets/DisassemblerGraphView.h"
|
||||
|
||||
class MainWindow;
|
||||
|
||||
@ -46,6 +47,7 @@ public:
|
||||
QTabWidget *memTabWidget;
|
||||
QWebEngineView *graphWebView;
|
||||
QWebEngineView *histoWebView;
|
||||
DisassemblerGraphView *mGraphView;
|
||||
|
||||
Highlighter *highlighter;
|
||||
Highlighter *highlighter_5;
|
||||
@ -139,6 +141,7 @@ private slots:
|
||||
void on_disButton_2_clicked();
|
||||
void on_hexButton_2_clicked();
|
||||
void on_graphButton_2_clicked();
|
||||
void on_graphButton_clicked();
|
||||
void showDisasContextMenu(const QPoint &pt);
|
||||
void showHexdumpContextMenu(const QPoint &pt);
|
||||
void showHexASCIIContextMenu(const QPoint &pt);
|
@ -178,7 +178,7 @@ QToolTip {
|
||||
}</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
<string>...</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../resources.qrc">
|
||||
@ -255,6 +255,63 @@ QToolTip {
|
||||
</attribute>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QToolButton" name="graphButton">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Graph</string>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">QToolButton { /* all types of tool button */
|
||||
border: 5px solid #333;
|
||||
border-left: 10px solid #333;
|
||||
border-right: 10px solid #333;
|
||||
border-radius: 0px;
|
||||
background-color: #333;
|
||||
}
|
||||
|
||||
QToolButton:hover {
|
||||
border: 5px solid #444;
|
||||
border-radius: 0px;
|
||||
background-color: #444;
|
||||
}
|
||||
|
||||
QToolButton:checked {
|
||||
border: 5px solid #2180a9;
|
||||
border-radius: 0px;
|
||||
background-color: #2180a9;
|
||||
}
|
||||
|
||||
QToolTip {
|
||||
background-color: #444;
|
||||
border: 3px solid #444;
|
||||
color: rgb(232, 232, 232);
|
||||
}</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>...</string>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="../resources.qrc">
|
||||
<normaloff>:/img/icons/graph_light.svg</normaloff>
|
||||
<normalon>:/img/icons/graph_white.svg</normalon>:/img/icons/graph_light.svg</iconset>
|
||||
</property>
|
||||
<property name="checkable">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<attribute name="buttonGroup">
|
||||
<string notr="true">buttonGroup</string>
|
||||
</attribute>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="verticalSpacer_6">
|
||||
<property name="orientation">
|
||||
@ -456,7 +513,7 @@ border-top: 0px;
|
||||
<enum>QTabWidget::South</enum>
|
||||
</property>
|
||||
<property name="currentIndex">
|
||||
<number>0</number>
|
||||
<number>2</number>
|
||||
</property>
|
||||
<property name="documentMode">
|
||||
<bool>false</bool>
|
||||
@ -1249,6 +1306,12 @@ p, li { white-space: pre-wrap; }
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<widget class="QWidget" name="tabGraph">
|
||||
<attribute name="title">
|
||||
<string>Page</string>
|
||||
</attribute>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_19"/>
|
||||
</widget>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
@ -3046,8 +3109,8 @@ QToolTip {
|
||||
</resources>
|
||||
<connections/>
|
||||
<buttongroups>
|
||||
<buttongroup name="buttonGroup_3"/>
|
||||
<buttongroup name="buttonGroup_2"/>
|
||||
<buttongroup name="buttonGroup_3"/>
|
||||
<buttongroup name="buttonGroup"/>
|
||||
</buttongroups>
|
||||
</ui>
|
Loading…
Reference in New Issue
Block a user