From 76c226dfdbf1449844c457ce8b49035555f7871e Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Wed, 19 Aug 2009 14:41:51 +0200 Subject: [PATCH] Debugger: Fix memory display - Watchwindow: Do not open Address dialog if menu is canceled (act = 0 matching the unitialized unknown memory action) - Actually pass the address of the dialog to the agent - Make the "Open Memory editor..." action always visible to be able to look at const char *x pointing at y - Improve the address dialog with checking and dialog button box - Explicitly pass the quint64 around - Translate & purge --- share/qtcreator/translations/qtcreator_de.ts | 309 +++---------------- src/plugins/debugger/cdb/cdbdebugengine.cpp | 17 + src/plugins/debugger/cdb/cdbdebugengine.h | 1 + src/plugins/debugger/debuggeragents.cpp | 4 +- src/plugins/debugger/debuggeragents.h | 6 +- src/plugins/debugger/debuggerdialogs.cpp | 57 ++++ src/plugins/debugger/debuggerdialogs.h | 22 ++ src/plugins/debugger/watchwindow.cpp | 37 +-- 8 files changed, 151 insertions(+), 302 deletions(-) diff --git a/share/qtcreator/translations/qtcreator_de.ts b/share/qtcreator/translations/qtcreator_de.ts index 684a98a8d6c..f7e854c8c7d 100644 --- a/share/qtcreator/translations/qtcreator_de.ts +++ b/share/qtcreator/translations/qtcreator_de.ts @@ -490,10 +490,6 @@ Qt Creator has detected an <b>in-source-build in %1</b> which prevents shadow builds. Qt Creator will not allow you to change the build directory. If you want a shadow build, clean your source directory and re-open the project. Es wurde ein <b>Build im Quellverzeichnis</b> festgestellt, der Shadow-Builds verhindert. Das Build-Verzeichnis kann nicht in Qt Creator geändert werden. Wenn Sie einen Shadow-Build wünschen, bereinigen Sie bitte das Quellverzeichnis und öffnen Sie das Projekt noch einmal. - - Qt Creator has detected an in-source-build which prevents shadow builds. Qt Creator will not allow you to change the build directory. If you want a shadow build, clean your source directory and re-open the project. - Es wurde ein Build im Quellverzeichnis festgestellt, der Shadow-Builds verhindert. Das Build-Verzeichnis kann nicht in Qt Creator geändert werden. Wenn Sie einen Shadow-Build wünschen, bereinigen Sie bitte das Quellverzeichnis und öffnen Sie das Projekt noch einmal. - CMakeProjectManager::Internal::MakeStepConfigWidget @@ -544,17 +540,6 @@ <keine Symbole> - - CVS::Internal::CVSOutputWindow - - CVS Output - CVS-Ausgabe - - - CVS - CVS - - CVS::Internal::CVSPlugin @@ -769,23 +754,6 @@ Executing in %1: %2 %2 Kommando [%1]: %2 %3 - - - - Executing: %2 %3 - - Kommando: %2 %3 - - - - %1 Executing: %2 %3 - - %1 Kommando: %2 %3 - - - %1 Executing in %2: %3 %4 - - %1 Kommando [%2]: %3 %4 @@ -2670,10 +2638,6 @@ Sollen sie überschrieben werden? Sort alphabetically Alphabetisch sortieren - - Rename '%1' - '%1' Umbenennen - CppEditor::Internal::ClassNamePage @@ -2982,10 +2946,23 @@ Sollen sie überschrieben werden? <Encoding-Fehler> + + Debugger::Internal::AddressDialog + + + Select start address + Startadresse + + + + Enter an address: + Adresse: + + Debugger::Internal::AttachCoreDialog - + Select Executable Ausführbare Datei auswählen @@ -3276,7 +3253,12 @@ Sollen sie überschrieben werden? Der Wert '%1' konnte nicht an '%2' zugewiesen werden: %3 - + + Unable to retrieve %1 bytes of memory at 0x%2: %3 + Die Abfrage des Speichers (%1 bytes ab 0x%2) schlug fehl: %3 + + + Cannot retrieve symbols while the debuggee is running. Die Symbole können nicht bestimmt werden, solange die zu debuggende Anwendung läuft. @@ -3429,14 +3411,6 @@ Sollen sie überschrieben werden? Step Into Einzelschritt herein - - Step Over Instruction - Einzelschritt über Anweisung - - - Step One Instruction - Einzelschritt eine Anweisung - Step Out @@ -3786,30 +3760,6 @@ Sollen sie überschrieben werden? Synchronize breakpoints Haltepunkte synchronisieren - - Hexadecimal - Hexadezimal - - - Decimal - Dezimal - - - Octal - Oktal - - - Binary - Binär - - - Raw - Rohformat - - - Natural - Natürliches Format - Automatically quit debugger @@ -3864,44 +3814,6 @@ Sollen sie überschrieben werden? - - Debugger::Internal::DisassemblerHandler - - Address - Adresse - - - Symbol - Symbol - - - Mnemonic - Kürzel - - - - Debugger::Internal::DisassemblerWindow - - Disassembler - Disassembler - - - Adjust column widths to contents - Spaltenbreite an Inhalt anpassen - - - Always adjust column widths to contents - Spaltenbreite immer an Inhalt anpassen - - - Reload disassembler listing - Dissambler neu laden - - - Always reload disassembler listing - Dissambler immer neu laden - - Debugger::Internal::GdbEngine @@ -4189,10 +4101,6 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Debugger exited. Debugger beendet. - - <could not retreive module information> - <Modulinformation nicht verfügbar> - Unable to run '%1': %2 @@ -4328,6 +4236,14 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Pfad zu Startup-Skript + + Debugger::Internal::MemoryViewAgent + + + Memory $ + Speicher $ + + Debugger::Internal::ModulesModel @@ -4464,10 +4380,6 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Value (base %1) Wert (Basis %1) - - Value - Wert - Debugger::Internal::RegisterWindow @@ -4910,7 +4822,12 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Format für den Ausdruck ändern - + + Open memory editor... + Speicher-Editor öffnen... + + + Adjust column widths to contents Spaltenbreite an Inhalt anpassen @@ -4920,17 +4837,7 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Spaltenbreite immer an Inhalt anpassen - - Enter an address: - Adresse: - - - - Select start address - Startadresse - - - + Insert new watch item Neuen Überwachten Ausdruck einfügen @@ -4941,11 +4848,6 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. - Open memory editor - Speicher-Editor öffnen - - - Open memory editor at %1 Speicher-Editor bei %1 öffnen @@ -5085,17 +4987,6 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Qt-Modulnamen in #include-Direktive verwenden - - Designer::Internal::EditorWidget - - Action editor - Aktionseditor - - - Signals and slots editor - Signale und Slots - - Designer::Internal::FormClassWizardDialog @@ -5157,26 +5048,6 @@ Es wird empfohlen, gdb 6.7 oder später zu benutzen. Designer::Internal::FormEditorW - - Designer widgetbox - Widgetbox - - - Object inspector - Objektanzeige - - - Property editor - Eigenschaften - - - Signals and slots editor - Signale und Slots - - - Action editor - Aktionseditor - @@ -6359,10 +6230,6 @@ Grund: %3 Tool Chain: Toolchain: - - Toolchain: - Werkzeugkette: - Generic Manager @@ -6577,12 +6444,6 @@ Grund: %3 Unable to parse the file output. Die Ausgabe der Datei konnte nicht ausgewertet werden. - - %1 Executing: %2 %3 - - <timestamp> Executing: <executable> <arguments> - %1 Kommando: %2 %3 - Executing: %1 %2 @@ -6721,17 +6582,6 @@ Grund: %3 Es gibt keine geänderten Dateien. - - Git::Internal::GitOutputWindow - - Git Output - Git-Ausgabe - - - Git - Git - - Git::Internal::GitPlugin @@ -6974,10 +6824,6 @@ Grund: %3 Another submit is currently being executed. Another submit is currently being executed. - - Another submit is currently beeing executed. - Es läuft bereits ein Commit. - Cannot create temporary file: %1 @@ -8241,17 +8087,6 @@ p, li { white-space: pre-wrap; } Change %1: %2 - - Perforce::Internal::PerforceOutputWindow - - Perforce Output - Perforce-Ausgabe - - - Perforce - Perforce - - Perforce::Internal::PerforcePlugin @@ -8517,12 +8352,6 @@ p, li { white-space: pre-wrap; } Executing: %1 Kommando: %1 - - - - %1 Executing: %2 - - %1 Kommando: %2 @@ -9059,14 +8888,6 @@ Fehler: %2 ProjectExplorer::EnvironmentWidget - - Show Details - Details anzeigen - - - Hide Details - Details ausblenden - Details @@ -9417,10 +9238,6 @@ Fehler: %2 %1 depends on: %2. %1 hängt von %2 ab. - - , - , - ProjectExplorer::Internal::DetailedModel @@ -9553,10 +9370,6 @@ Fehler: %2 ProjectExplorer::Internal::ProcessStepWidget - - Enable custom process step - Benutzerdefinierten Verarbeitungsschritt aktivieren - Name: @@ -9764,25 +9577,6 @@ Fehler: %2 Zu erzeugende Dateien: - - ProjectExplorer::Internal::ProjetExplorerSettingsPageUi - - Save all files before Build - Alle Dateien vor Erstellen speichern - - - Always build Project before Running - Projekt vor Ausführung stets erstellen - - - Build and Run - Erstellung und Ausführung - - - Show Compiler Output on building - Compiler-Ausgabe beim Erstellen anzeigen - - ProjectExplorer::Internal::RemoveFileDialog @@ -10551,10 +10345,6 @@ unter Versionsverwaltung (%2) gestellt werden? QrcEditor - - Form - Formular - Add @@ -11439,10 +11229,6 @@ unter Versionsverwaltung (%2) gestellt werden? using Qt version: <b>%1</b><br>with tool chain <b>%2</b><br>building in <b>%3</b> verwende Qt-Version: <b>%1</b><br>mit Toolchain <b>%2</b><br>Erstellung in <b>%3</b> - - using Qt Version: <b>%1</b><br>with tool chain <b>%2</b><br>building in <b>%3</b> - benutze - General @@ -11805,19 +11591,11 @@ p, li { white-space: pre-wrap; } Device on Serial Port: Gerät auf serieller Schnittstelle: - - Self-sign - Selbstsigniertes Zertifikat - Choose certificate file (.cer) Geben Sie eine Datei mit einem Zertifikat (.cer) an - - Custom signature: - Signatur: - Choose key file (.key / .pem) @@ -13231,17 +13009,6 @@ Um es abzurufen, tippen Sie das Kürzel im Locator, gefolgt von einem Leerzeich Subversion-Kommando - - Subversion::Internal::SubversionOutputWindow - - Subversion Output - Subversion-Ausgabe - - - Subversion - Subversion - - Subversion::Internal::SubversionPlugin @@ -13443,12 +13210,6 @@ Um es abzurufen, tippen Sie das Kürzel im Locator, gefolgt von einem Leerzeich Es wurde keine ausführbaren Subversion-Datei angegeben! - - %1 Executing: %2 %3 - - <timestamp> Executing: <executable> <arguments> - %1 Kommando: %2 %3 - The process terminated with exit code %1. diff --git a/src/plugins/debugger/cdb/cdbdebugengine.cpp b/src/plugins/debugger/cdb/cdbdebugengine.cpp index fb2f0d7676e..d6660fa0938 100644 --- a/src/plugins/debugger/cdb/cdbdebugengine.cpp +++ b/src/plugins/debugger/cdb/cdbdebugengine.cpp @@ -1337,6 +1337,23 @@ void CdbDebugEngine::fetchDisassembler(DisassemblerViewAgent *agent, } } +void CdbDebugEngine::fetchMemory(MemoryViewAgent *agent, quint64 addr, quint64 length) +{ + if (!m_d->m_hDebuggeeProcess && !length) + return; + ULONG received; + QByteArray data(length, '\0'); + const HRESULT hr = m_d->m_cif.debugDataSpaces->ReadVirtual(addr, data.data(), length, &received); + if (FAILED(hr)) { + warning(tr("Unable to retrieve %1 bytes of memory at 0x%2: %3"). + arg(length).arg(addr, 0, 16).arg(msgComFailed("ReadVirtual", hr))); + return; + } + if (received < length) + data.truncate(received); + agent->addLazyData(addr, data); +} + void CdbDebugEngine::reloadModules() { } diff --git a/src/plugins/debugger/cdb/cdbdebugengine.h b/src/plugins/debugger/cdb/cdbdebugengine.h index 995347e7a95..521b7b17201 100644 --- a/src/plugins/debugger/cdb/cdbdebugengine.h +++ b/src/plugins/debugger/cdb/cdbdebugengine.h @@ -89,6 +89,7 @@ public: virtual void fetchDisassembler(DisassemblerViewAgent *agent, const StackFrame &frame); + virtual void fetchMemory(MemoryViewAgent *, quint64 addr, quint64 length); virtual void reloadModules(); virtual void loadSymbols(const QString &moduleName); diff --git a/src/plugins/debugger/debuggeragents.cpp b/src/plugins/debugger/debuggeragents.cpp index 8234ee65415..ad1b6d67710 100644 --- a/src/plugins/debugger/debuggeragents.cpp +++ b/src/plugins/debugger/debuggeragents.cpp @@ -75,7 +75,7 @@ MemoryViewAgent::MemoryViewAgent(DebuggerManager *manager, const QString &addr) : QObject(manager), m_engine(manager->currentEngine()) { bool ok = true; - init(addr.toUInt(&ok, 0)); + init(addr.toULongLong(&ok, 0)); //qDebug() << " ADDRESS: " << addr << addr.toUInt(&ok, 0); } @@ -87,7 +87,7 @@ MemoryViewAgent::~MemoryViewAgent() void MemoryViewAgent::init(quint64 addr) { Core::EditorManager *editorManager = Core::EditorManager::instance(); - QString titlePattern = "Memory $"; + QString titlePattern = tr("Memory $"); m_editor = editorManager->openEditorWithContents( Core::Constants::K_DEFAULT_BINARY_EDITOR, &titlePattern); diff --git a/src/plugins/debugger/debuggeragents.h b/src/plugins/debugger/debuggeragents.h index c6d4b768c74..2ee788ccedc 100644 --- a/src/plugins/debugger/debuggeragents.h +++ b/src/plugins/debugger/debuggeragents.h @@ -53,8 +53,8 @@ class MemoryViewAgent : public QObject public: // Called from Gui - MemoryViewAgent(DebuggerManager *manager, quint64 startaddr); - MemoryViewAgent(DebuggerManager *manager, const QString &startaddr); + explicit MemoryViewAgent(DebuggerManager *manager, quint64 startaddr); + explicit MemoryViewAgent(DebuggerManager *manager, const QString &startaddr); ~MemoryViewAgent(); enum { BinBlockSize = 1024 }; @@ -79,7 +79,7 @@ class DisassemblerViewAgent : public QObject public: // Called from Gui - DisassemblerViewAgent(DebuggerManager *manager); + explicit DisassemblerViewAgent(DebuggerManager *manager); ~DisassemblerViewAgent(); void setFrame(const StackFrame &frame); diff --git a/src/plugins/debugger/debuggerdialogs.cpp b/src/plugins/debugger/debuggerdialogs.cpp index 1990b161f7f..36128020850 100644 --- a/src/plugins/debugger/debuggerdialogs.cpp +++ b/src/plugins/debugger/debuggerdialogs.cpp @@ -537,5 +537,62 @@ void StartRemoteDialog::updateState() m_ui->serverStartScript->setEnabled(enabled); } +AddressDialog::AddressDialog(QWidget *parent) : + QDialog(parent), + m_lineEdit(new QLineEdit), + m_box(new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel)) +{ + setWindowTitle(tr("Select start address")); + setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint); + QHBoxLayout *hLayout = new QHBoxLayout; + hLayout->addWidget(new QLabel(tr("Enter an address: "))); + hLayout->addWidget(m_lineEdit); + QVBoxLayout *vLayout = new QVBoxLayout; + vLayout->addLayout(hLayout); + vLayout->addWidget(m_box); + setLayout(vLayout); + + connect(m_box, SIGNAL(accepted()), this, SLOT(accept())); + connect(m_box, SIGNAL(rejected()), this, SLOT(reject())); + connect(m_lineEdit, SIGNAL(returnPressed()), this, SLOT(accept())); + connect(m_lineEdit, SIGNAL(textChanged(QString)), this, SLOT(textChanged())); + + setOkButtonEnabled(false); +} + +void AddressDialog::setOkButtonEnabled(bool v) +{ + m_box->button(QDialogButtonBox::Ok)->setEnabled(v); +} + +bool AddressDialog::isOkButtonEnabled() const +{ + return m_box->button(QDialogButtonBox::Ok)->isEnabled(); +} + +quint64 AddressDialog::address() const +{ + return m_lineEdit->text().toULongLong(0, 16); +} + +void AddressDialog::accept() +{ + if (isOkButtonEnabled()) + QDialog::accept(); +} + +void AddressDialog::textChanged() +{ + setOkButtonEnabled(isValid()); +} + +bool AddressDialog::isValid() const +{ + const QString text = m_lineEdit->text(); + bool ok = false; + text.toULongLong(&ok, 16); + return ok; +} + } // namespace Internal } // namespace Debugger diff --git a/src/plugins/debugger/debuggerdialogs.h b/src/plugins/debugger/debuggerdialogs.h index b277b6aabfd..2b63fa3e9e8 100644 --- a/src/plugins/debugger/debuggerdialogs.h +++ b/src/plugins/debugger/debuggerdialogs.h @@ -36,6 +36,8 @@ QT_BEGIN_NAMESPACE class QModelIndex; class QPushButton; +class QLineEdit; +class QDialogButtonBox; namespace Ui { class AttachCoreDialog; @@ -171,6 +173,26 @@ private: Ui::StartRemoteDialog *m_ui; }; +class AddressDialog : public QDialog { + Q_OBJECT +public: + explicit AddressDialog(QWidget *parent = 0); + quint64 address() const; + + virtual void accept(); + +private slots: + void textChanged(); + +private: + void setOkButtonEnabled(bool v); + bool isOkButtonEnabled() const; + + bool isValid() const; + + QLineEdit *m_lineEdit; + QDialogButtonBox *m_box; +}; } // namespace Debugger } // namespace Internal diff --git a/src/plugins/debugger/watchwindow.cpp b/src/plugins/debugger/watchwindow.cpp index 18f02472d0f..b8a687c82db 100644 --- a/src/plugins/debugger/watchwindow.cpp +++ b/src/plugins/debugger/watchwindow.cpp @@ -32,6 +32,7 @@ #include "debuggeractions.h" #include "debuggeragents.h" +#include "debuggerdialogs.h" #include @@ -51,7 +52,6 @@ using namespace Debugger::Internal; - ///////////////////////////////////////////////////////////////////// // // WatchDelegate @@ -249,14 +249,11 @@ void WatchWindow::contextMenuEvent(QContextMenuEvent *ev) QAction *actInsertNewWatchItem = menu.addAction(tr("Insert new watch item")); QAction *actSelectWidgetToWatch = menu.addAction(tr("Select widget to watch")); - QString address = model()->data(mi0, AddressRole).toString(); + const QString address = model()->data(mi0, AddressRole).toString(); QAction *actWatchKnownMemory = 0; - QAction *actWatchUnknownMemory = 0; - if (address.isEmpty()) - actWatchUnknownMemory = new QAction(tr("Open memory editor"), &menu); - else - actWatchKnownMemory = - new QAction(tr("Open memory editor at %1").arg(address), &menu); + QAction *actWatchUnknownMemory = new QAction(tr("Open memory editor..."), &menu);; + if (!address.isEmpty()) + actWatchKnownMemory = new QAction(tr("Open memory editor at %1").arg(address), &menu); menu.addSeparator(); int atype = (m_type == LocalsType) ? WatchExpression : RemoveWatchExpression; @@ -266,8 +263,9 @@ void WatchWindow::contextMenuEvent(QContextMenuEvent *ev) menu.addAction(actSelectWidgetToWatch); menu.addMenu(&typeFormatMenu); menu.addMenu(&individualFormatMenu); - menu.addAction(actWatchKnownMemory ? actWatchKnownMemory : actWatchUnknownMemory); - + if (actWatchKnownMemory) + menu.addAction(actWatchKnownMemory); + menu.addAction(actWatchUnknownMemory); menu.addSeparator(); menu.addAction(theDebuggerAction(RecheckDebuggingHelpers)); menu.addAction(theDebuggerAction(UseDebuggingHelpers)); @@ -292,20 +290,13 @@ void WatchWindow::contextMenuEvent(QContextMenuEvent *ev) } else if (act == actInsertNewWatchItem) { theDebuggerAction(WatchExpression) ->trigger(WatchHandler::watcherEditPlaceHolder()); - } else if (act == actWatchKnownMemory) { + } else if (actWatchKnownMemory != 0 && act == actWatchKnownMemory) { (void) new MemoryViewAgent(m_manager, address); - } else if (act == actWatchUnknownMemory) { - QLabel *label = new QLabel(tr("Enter an address: ")); - QLineEdit *lineEdit = new QLineEdit; - QHBoxLayout *layout = new QHBoxLayout; - layout->addWidget(label); - layout->addWidget(lineEdit); - QDialog dialog(this); - dialog.setWindowTitle(tr("Select start address")); - dialog.setLayout(layout); - connect(lineEdit, SIGNAL(returnPressed()), &dialog, SLOT(accept())); - if (dialog.exec() == QDialog::Accepted) - (void) new MemoryViewAgent(m_manager, address); + } else if (actWatchUnknownMemory != 0 && act == actWatchUnknownMemory) { + AddressDialog dialog; + if (dialog.exec() == QDialog::Accepted) { + (void) new MemoryViewAgent(m_manager, dialog.address()); + } } else if (act == actSelectWidgetToWatch) { grabMouse(Qt::CrossCursor); m_grabbing = true;