Commit ce27e9b5 authored by Arvid Ephraim Picciani's avatar Arvid Ephraim Picciani
Browse files

Import lldb guest engine code

parent e4443ef6
LLDB Guest Engine
You can use the LLDB debugger from the LLVM project with the Qt Creator debugger
plugin on Mac OS.
For the Qt Creator build to pick up the LLDB Guest Engine,
you must download the LLDB debugger and configure it
to be included in the Qt Creator build.
To debug an application, Qt Creator must access the memory of the application.
On Mac OS X, this requires code signing.
To enable LLDB debugger support in Qt Creator:
1. Change to the directory this readme is located in.
2. To download the LLDB debugger, enter the following command:
svn co lldb
3. To sign the code, follow the instructions in lldb/docs/code-signing.txt.
4. To open LLDB in Xcode for building, enter the following command:
open lldb.xcodeproj
then select the Release target and press the build button.
5. In Xcode, press the build button.
6. To rebuild Qt Creator, change back to the top level directory of
the Qt Creator source, and enter the following command:
qmake -r && make
This diff is collapsed.
** This file is part of Qt Creator
** Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
** Contact: Nokia Corporation (
** Commercial Usage
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met:
** If you are unsure which license is appropriate for your use, please
** contact the sales department at
#include "ipcengineguest.h"
#include <QtCore/QQueue>
#include <QtCore/QVariant>
#include <QtCore/QThread>
#include <QtCore/QMutex>
#include <QtCore/QStringList>
#include <lldb/API/LLDB.h>
#if defined(HAVE_LLDB_PRIVATE)
#include "pygdbmiemu.h"
Q_DECLARE_METATYPE (lldb::SBListener *)
namespace Debugger {
namespace Internal {
class LLDBEventListener : public QObject
public slots:
void listen(lldb::SBListener *listener);
// lldb API uses non thread safe implicit sharing with no explicit copy feature
// additionally the scope is undefined, hence this signal needs to be connected BlockingQueued
// whutever, works for now.
void lldbEvent(lldb::SBEvent *ev);
class LLDBEngineGuest : public IPCEngineGuest
explicit LLDBEngineGuest();
void setupEngine();
void setupInferior(const QString &executable, const QStringList &arguments,
const QStringList &environment);
void runEngine();
void shutdownInferior();
void shutdownEngine();
void detachDebugger();
void executeStep();
void executeStepOut() ;
void executeNext();
void executeStepI();
void executeNextI();
void continueInferior();
void interruptInferior();
void executeRunToLine(const QString &fileName, int lineNumber);
void executeRunToFunction(const QString &functionName);
void executeJumpToLine(const QString &fileName, int lineNumber);
void activateFrame(qint64);
void selectThread(qint64);
void disassemble(quint64 pc);
void addBreakpoint(BreakpointId id, const BreakpointParameters &bp);
void removeBreakpoint(BreakpointId id);
void changeBreakpoint(BreakpointId id, const BreakpointParameters &bp);
void requestUpdateWatchData(const Internal::WatchData &data,
const Internal::WatchUpdateFlags & flags = Internal::WatchUpdateFlags());
QMutex m_runLock;
bool m_running;
QList<QByteArray> m_arguments;
QList<QByteArray> m_environment;
QThread m_wThread;
LLDBEventListener *m_worker;
lldb::SBDebugger *m_lldb;
lldb::SBTarget *m_target;
lldb::SBProcess *m_process;
lldb::SBListener *m_listener;
lldb::SBFrame m_currentFrame;
lldb::SBThread m_currentThread;
bool m_relistFrames;
QHash<QString, lldb::SBValue> m_localesCache;
QHash<BreakpointId, lldb::SBBreakpoint> m_breakpoints;
void updateThreads();
void getWatchDataR(lldb::SBValue v, int level,
const QByteArray &p_iname, QList<WatchData> &wd);
#if defined(HAVE_LLDB_PRIVATE)
PythonLLDBToGdbMiHack * py;
private slots:
void lldbEvent(lldb::SBEvent *ev);
} // namespace Internal
} // namespace Debugger
#include <QtCore/QCoreApplication>
#include <QtNetwork/QLocalSocket>
#include "lldbengineguest.h"
class DiePlease: public QThread
virtual void run()
int main(int argc, char **argv)
QCoreApplication app(argc, argv);
Debugger::Internal::LLDBEngineGuest lldb;
QLocalSocket s;
if (argc > 1) {
// Pure test code. This is not intended for end users.
// TODO: maybe some day we can have real unit tests for debugger engines?
setenv("LLDB_DEBUGSERVER_PATH", "/Users/aep/qt-creator/src/plugins/debugger/lldb/lldb/build/Release/LLDB.framework/Resources/debugserver", 0);
QStringList env;
lldb.setupInferior(argv[1], QStringList(), env);
Debugger::Internal::BreakpointParameters bp;
bp.ignoreCount = 0;
bp.lineNumber = 64;
bp.fileName = QLatin1String("main.cpp");
lldb.addBreakpoint(0, bp);
}else {
app.connect(&s, SIGNAL(disconnected ()), &app, SLOT(quit()));
DiePlease bla;
return app.exec();
extern "C" {
extern const unsigned char lldbVersionString[] __attribute__ ((used)) = "@(#)PROGRAM:lldb PROJECT:lldb-26" "\n";
extern const double lldbVersionNumber __attribute__ ((used)) = (double)26.;
extern const double LLDBVersionNumber __attribute__ ((used)) = (double)26.;
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "">
<plist version="1.0">
<string>Qt Creator LLDB Guest</string>
macx: exists($$PWD/lldb) : SUBDIRS += $$PWD/
!macx: error (This can only be built on mac)
!exists($$PWD/lldb): error(please see the README for build instructions)
CONFIG -= app_bundle
CONFIG += debug
TARGET = qtcreator-lldb
DEPENDPATH += . .. ../.. ../../.. ../../../../libs
INCLUDEPATH += . .. ../.. ../../.. ../../../../libs
QT = core network
HEADERS += ../ipcengineguest.h \
../debuggerstreamops.h \
../breakpoint.h \
../watchdata.h \
../stackframe.h \
SOURCES += ../ipcengineguest.cpp \
../debuggerstreamops.cpp \
../breakpoint.cpp \
../watchdata.cpp \
../stackframe.cpp \
lldbengineguest.cpp \
LIBS += -sectcreate __TEXT __info_plist ./qtcreator-lldb.plist
POSTL = rm -rf \'$${IDE_LIBEXEC_PATH}/LLDB.framework\' $$escape_expand(\\n\\t) \
$$QMAKE_COPY_DIR lldb/build/Release/* \'$$IDE_LIBEXEC_PATH\' $$escape_expand(\\n\\t) \
install_name_tool -change '@rpath/LLDB.framework/Versions/A/LLDB' '@executable_path/LLDB.framework/Versions/A/LLDB' $(TARGET) $$escape_expand(\\n\\t) \
codesign -s lldb_codesign $(TARGET)
!isEmpty(QMAKE_POST_LINK):QMAKE_POST_LINK = $$escape_expand(\\n\\t)$$QMAKE_POST_LINK
silent:QMAKE_POST_LINK = @echo signing $@ && $$QMAKE_POST_LINK
LIBS += -framework Security -framework Python
INCLUDEPATH += lldb/include lldb/llvm/include/
LIBS += -Flldb/build/Release -framework LLDB
# include (lldb.pri)
# HEADERS += pygdbmiemu.h
# SOURCES += pygdbmiemu.cpp
......@@ -64,6 +64,8 @@ contains(QT_CONFIG, declarative) {
include (debugger/lldb/guest/qtcreator-lldb.pri)
plugin_coreplugin.subdir = coreplugin
plugin_welcome.subdir = welcome
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment