Merge remote-tracking branch 'origin/2.6'

Conflicts:
	qtcreator.pri
	qtcreator.qbp
	src/libs/utils/utils.pro

Change-Id: I6f0aba746f915d8c51dcf9372f7d9f593562fc2b
This commit is contained in:
Eike Ziller
2012-09-11 14:02:03 +02:00
156 changed files with 3503 additions and 3134 deletions

201
dist/changes-2.6.0 vendored
View File

@@ -5,48 +5,229 @@ list of changes, see the Git log for the Qt Creator sources that
you can check out from the public Git repository. For example:
git clone git://gitorious.org/qt-creator/qt-creator.git
git log --cherry-pick --pretty=oneline v2.5.0...origin/2.6
git log --cherry-pick --pretty=oneline v2.5.2..origin/2.6
General
* Added a wizard for creating a temporary text file
* Added a menu for showing and hiding the output pane buttons
* Added a visual hint for canceled searches (QTCREATORBUG-6820)
* Fixed the New dialog for dark themes (QTCREATORBUG-7435)
* Added support for jumping to a line in a specific file to Locator
(with "+" or ":" appended to the file name, for example "myfile.cpp:41")
* Fixed that several settings where saved every few seconds
even without changes (QTCREATORBUG-7718)
Editing
* Added a context menu for adding and removing UTF-8 bom
* Added shortcuts for searching for next and previous occurrence
of selected text without opening the find tool bar (QTCREATORBUG-464)
* Made resource files searchable (Ctrl+F)
* Added file type icons to the resource editor
* Added opening of files from the resource editor
* Added highlighting of missing files in the resource editor
* Added support for movies in the image viewer
* Fixed problems when closing documents in a split view (QTCREATORBUG-7361)
Managing Projects
* Introduced "Kits" that supersede the previous "Targets". They bundle
the settings for the target device, compiler, debugger, Qt version and
more into a user definable, reusable setting.
* Moved the debugger setting from tool chains to kits
and renamed tool chains to compilers
* Added experimental support for Android (enable the plugin in Help > About Plugins)
* Added experimental support for QNX (enable the plugin in Help > About Plugins)
* Made it possible to disable deploy configurations
* Added double-clicking of file names in compile errors to open the file
* Added a Cancel Build button to the Compile Output pane
* Added CurrentProject::BuildPath variable for external tools (QTCREATORBUG-4885)
QMake Projects
* Added an action for compiling a single file (QTCREATORBUG-106)
* Added actions for (re)building and cleaning the current subproject
CMake Projects
* Added CMake specific context menu items to the CMakeLists.txt editor
Debugging
* Updated dumpers to internal changes in Qt 5 (structure layout, namespaces)
* Adjusted state engine to changes in GDB/MI notifications
* Made all views searchable (Ctrl+F)
* Made extensive use of HistoryCompleter
* Consolidated the special start options in Debug > Start Debugging
after the Kits changes
* Renamed "Watcher" into "Expression Evaluator"
* Generalized process listing and attaching facilities
* Adjusted to changed code generation in MinGW 4.6
* Added GUI support for temporary breakpoints
* Added a shortcut (F10) for start-and-stop-at-main
* Added direct loading of remote core files
* Added an option to create watch points in the Memory view context menu
* Added GDB pretty-printers for QFiniteStack, QHash::{const_}iterator,
std::{map,set}::iterator
* Added support for IPv6-enabled builds of GDB
* Improved logging and output pane performance
* Improved performance of retrieving large arrays of plain data
* Fixed use of non-xterm terminals (QTCREATORBUG-1633)
* Fixed use of multi-line breakpoint commands
* Fixed off-by-one error in the Address field in the Symbols view
Debugging QML/JS
* Merged the (experimental) QML/JS Inspector plugin into the Debugger:
* Added the QML object tree to the Expressions window
* Added Console window to evaluate JS expressions at runtime
* Added QML specific buttons to the toolbar
Analyzing Code
* Added an option to shorten template names in function profiler output
* Simplified the remote start dialogs
C++ Support
* Fixed lambda formatting issues
* Added support for variadic arguments (__VA_ARGS__)
* Added support for raw string literals (QTCREATORBUG-6722)
* Fixed the display of results when searching for macro usages (QTCREATORBUG-7217)
* Added highlighting of macro usages
* Implemented renaming of macro usages (QTCREATORBUG-413)
* Fixed detection of C++11 features for MSVC
QML/JS Support
* Added support for adding the file to VCS when moving a component into
a separate file (QTCREATORBUG-7246)
GLSL Support
* Fixed a crash on declaration without type (QTCREATORBUG-7548)
* Fixed a freeze when using the conditional operator (QTCREATORBUG-7517)
Qt Quick Designer
Help
* Made hiding the navigation side bar in the Help mode possible (QTCREATORBUG-1533)
Qt Designer
Version control plugins
* Added experimental support for ClearCase (enable the plugin in
Help > About Plugins)
Git
* Added a customizable repository browser command
* Fixed commit and amend when not on a branch
* Added partial support for Gerrit (Tools > Git > Gerrit)
SVN
* Fixed project status command when no document is open
* Fixed completion in the submit editor
FakeVim
* Added support for smartcase searching
* Added support for last selection operations
* Added support for counts in block selections (for example "2vi)", "3da{")
* Added support for special registers "+ and "*
* Added selection commands for strings (for example "di'", "ca`")
* Improved emulation of Vim regexps
* Fixed :!cmd if there is no selection
* Fixed handling of "ci(", "di[", "ca{" inside nested blocks
* Fixed search without matches
* Fixed pasting text [count] times and in selection
* Fixed pasting from clipboard
* Made clipboard data format compatible with Vim
Platform Specific
Mac
* Added support for fullscreen (Lion and later)
* Changed the VCS shortcuts to use the Ctrl modifier instead of the Opt modifier
(the Opt modifier inserts special characters on Mac)
* Made the shortcut modifiers (for example Cmd+...) searchable in the Filter
functionality of the keyboard shortcut settings
Linux (GNOME and KDE)
* Worked around a problem in the KDE file dialog that prevented selecting
qmake (QTCREATORBUG-7771)
Windows
Symbian Target
* Removed support for Symbian development because of missing maintainer
Remote Linux Support
Qt Designer
FakeVim
Version control plugins
Madde
* Remove generic MeeGo support due to complete irrelevance
Additional credits go to:
* Removed generic MeeGo support due to complete irrelevance
Credits go to:
Aleksey Sidorov
Alessandro Portale
Andreas Holzammer
Andre Hartmann
André Pönitz
Aurélien Gâteau
Aurindam Jana
Bill King
BogDan Vatra
Bojan Petrovic
Bradley T. Hughes
Campbell Barton
Casper van Donderen
Christiaan Janssen
Christian Kamm
Christian Kandeler
Christian Stenger
cnavarro
Daniel Molkentin
Daniel Teske
David Schulz
Dmitry Savchenko
Eike Ziller
Erik Verbruggen
Fawzi Mohamed
Flex Ferrum
Francois Ferrand
Friedemann Kleint
hluk
Hugues Delorme
Jarek Kobus
Jędrzej Nowacki
Joerg Bornemann
Jonathan Liu
Juhapekka Piiroinen
Kaffeine
Kai Köhne
kh1
Konstantin Ritt
Konstantin Tokarev
Leandro Melo
Leena Miettinen
Lukas Geyer
Lukas Holecek
Marc Mutz
Marco Bubke
Marius Storm-Olsen
Martin Aumüller
Mathias Hasselmann
Montel Laurent
Morten Johan Sorvig
Nicolas Arnaud-Cormos
Nikolai Kosjar
Orgad Shaneh
Oswald Buddenhagen
Oto Magaldadze
Peter Kuemmel
Pierre Rossi
Robert Loehning
Ryan May
Sergey Belyashov
Sergey Shambir
Simjees Abraham
Takumi Asaki
Theo J.A. de Vries
Thiago Macieira
Thomas Hartmann
Thorbjørn Lindeijer
tjenssen
Tobias Hunger
Tobias Nätterlund
Tommi Asp
Tyler Mandry
Vladislav Navrocky
Yuchen Deng

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.9 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.2 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

View File

@@ -22,9 +22,9 @@
/*!
\contentspage index.html
\previouspage creator-developing-qnx.html
\previouspage creator-connecting-mobile.html
\page creator-developing-android.html
\nextpage creator-build-process-customizing.html
\nextpage creator-developing-generic-linux.html
\title Connecting Android Devices

View File

@@ -22,9 +22,9 @@
/*!
\contentspage index.html
\previouspage creator-deployment-qnx.html
\previouspage creator-deployment.html
\page creator-deploying-android.html
\nextpage creator-connecting-mobile.html
\nextpage creator-deployment-maemo.html
\title Deploying Applications to Android Devices

View File

@@ -25,7 +25,7 @@
/*!
\contentspage index.html
\previouspage creator-deployment.html
\previouspage creator-deploying-android.html
\page creator-deployment-maemo.html
\nextpage creator-deployment-qnx.html

View File

@@ -27,7 +27,7 @@
\contentspage index.html
\previouspage creator-build-process-customizing.html
\page creator-maemo-emulator.html
\nextpage creator-remote-compiler.html
\nextpage creator-testing.html
\title Using Maemo or MeeGo Harmattan Emulator

View File

@@ -10,8 +10,7 @@
\list 1
\o Select \gui {Tools > Options > Linux Devices > Device
Configurations > Generate SSH Key}.
\o Select \gui Tools > \gui Options > \gui Devices > \gui {Create New}.
\image qtcreator-ssh-key-configuration.png "SSH Key Configuration dialog"

View File

@@ -1,13 +1,12 @@
\section2 Managing Device Processes
You can view processes running on devices and kill them. Select
\gui {Tools > Options > Linux Devices > Device Configurations >
Remote Processes}.
\gui Tools > \gui Options > \gui Devices > \gui {Remote Processes}.
You can filter the processes by name in the \gui {List of Remote Processes}
You can filter the processes by name in the \gui {List of Processes}
dialog.
To update the process list, select \gui {Update List}.
To kill a process, select it in the list, and then select \gui {Kill
Selected Process}.
Process}.

View File

@@ -20,7 +20,7 @@
/*!
\contentspage index.html
\previouspage creator-developing-meego.html
\previouspage creator-developing-android.html
\page creator-developing-generic-linux.html
\nextpage creator-developing-maemo.html
@@ -39,7 +39,7 @@
create device configurations and select them in the \QC \l{glossary-buildandrun-kit}{kit}
You use a wizard to create the connections. You can edit the settings later
in \gui {Tools > Options > Devices > Devices}.
in \gui Tools > \gui Options > \gui Devices.
\image qtcreator-linux-device-configurations.png "Devices dialog"
@@ -67,8 +67,8 @@
\list 1
\o Select \gui {Tools > Options > Linux Devices > Devices > Add
> Generic Linux Device > Start Wizard}.
\o Select \gui Tools > \gui Options > \gui Devices > \gui Add
> \gui {Generic Linux Device} > \gui {Start Wizard}.
\image qtcreator-screenshot-devconf-linux.png "Connection Data wizard"
@@ -103,13 +103,12 @@
\o Open a project for an application you want to develop for the
device.
\o Select \gui {Projects > Build & Run Settings > Add Kit}.
\o Select the kit that you added above.
\o Select \gui Projects > \gui {Build & Run} > \gui {Add Kit} to
add the kit that you specified above.
\endlist
\o To specify run settings, select \gui Run.
\o Select \gui Run to specify run settings.
\image qtcreator-run-settings-linux-devices.png "Run settings for embedded Linux devices"

View File

@@ -26,7 +26,7 @@
\previouspage creator-developing-meego.html
\endif
\page creator-developing-maemo.html
\nextpage creator-developing-qnx.html
\nextpage creator-developing-meego.html
\title Connecting Maemo Devices
@@ -48,7 +48,7 @@
or see
\l{http://doc.qt.nokia.com/qt-maemo/platform-notes-maemo5.html}{Platform Notes - Maemo 5}.
\section1 Hardware and Software Requirements for Maemo Target
\section1 Hardware and Software Requirements for Maemo Devices
To build and run Qt applications for Maemo 5, you need the following:
\list
@@ -222,7 +222,7 @@
only need to configure a connection to the device.
You use a wizard to create the connections. You can edit the settings later
in \gui {Tools > Options > Linux Devices > Device Configurations}.
in \gui Tools > \gui Options > \gui Devices.
\image qtcreator-maemo-device-configurations.png "Maemo Device Configurations dialog"
@@ -282,21 +282,15 @@
\note If you experience connection problems due to a USB port issue,
switch to a different port or use WLAN to connect to the device.
\o Select \gui {Tools > Options > Linux Devices > Device
Configurations > Add}.
\o Select \gui Tools > \gui Options > \gui Devices > \gui Add.
\o Select \gui {Device with MADDE support (Fremantle, Harmattan,
MeeGo) > Start Wizard}, and add a new configuration for a
hardware device.
\o Select \gui {Maemo5/Fremantle} > \gui {Start Wizard}.
\image qtcreator-dev-conf-maemo.png "Maemo device configuration"
\o In the \gui {The name to identify this configuration} field,
enter a name for the connection.
\o In the \gui {The system running on the device} field, select
the software platform of the device.
\o In the \gui {The kind of device} field, select
\gui {Hardware device}.
@@ -321,21 +315,11 @@
\list a
\o In \QC, select \gui {Tools > Options > Linux
Devices > Device Configurations > Add} to add a new
configuration.
\image qtcreator-maemo-emulator-connection.png "Maemo emulator configuration"
\o In the \gui {The name to identify this configuration} field,
enter a name for
the connection.
\o In the \gui {The system running on the device} field, select
the software platform to emulate.
\o In \QC, select \gui Tools > \gui Options > \gui Devices >
\gui Add to add a new configuration.
\o In the \gui {The kind of device} field, select
\gui {Emulator (Qemu)}.
\gui Emulator.
\o Click \gui Next.
@@ -345,30 +329,56 @@
\endlist
\endif
\o To specify build and run settings:
\o Select \gui Tools > \gui Options > \gui {Build & Run} >
\gui Kits > \gui Add to add a kit for building for the device:
\list a
\o In the \gui {Device type} field, select
\gui {Maemo5/Fremantle}.
\o In the \gui Device field, select the device that you added
above.
\o In the \gui Sysroot field, specify the path to the sysroot.
By default, the \QSDK installer places sysroot in the
following folder:
\c{QtSDK\Maemo\4.6.2\sysroots\fremantle-arm-sysroot-20.2010.36-2-slim}.
\o In the \gui {Compiler type} field, select GCC.
\o In the \gui Compiler field, specify the path to the GCC
compiler. By default, the \QSDK installer places the
compiler in the following folder:
\c{QtSDK\Maemo\4.6.2\targets\fremantle-pr13\bin\}.
\o In the \gui Debugger field, specify the path to GDB. By
default, the \QSDK installer places the debugger
in the following folder:
\c{QtSDK\Maemo\4.6.2\targets\fremantle-pr13\bin\}.
\o In the \gui {Qt version} field, choose the MADDE Qt version
for Maemo5/Fremantle. By default, the \QSDK installer
places qmake in the following folder:
\c{QtSDK\Maemo\4.6.2\targets\fremantle-pr13\bin\}.
\endlist
You can leave the \gui {Qt mkspec} field empty.
\o Open a project for an application you want to develop for your
device.
\o Click \gui Projects to open the projects mode.
\o Select \gui Projects > \gui {Build & Run} > \gui {Add Kit} to
add the kit that you specified above.
\o In the \gui{Build Settings} section, choose the MADDE Qt version
that was registered by the installation program.
\o Select \gui Run to specify run settings for the project.
\image qtcreator-build-settings-maemo.png "Maemo build settings"
\o In the \gui{Run Settings} section, in the
\gui {Device configuration} field, select the device
connection or the emulator connection.
\image qtcreator-run-settings-maemo.png "Maemo run settings"
\o Click \gui {<no target path set>} in \gui {Remote Directory}
to specify the folder where the file is installed on the device.
For example, \c {/opt/usr/bin}.
\endlist
\o The mobile application wizard automatically sets the folder
where the file is installed on the device in the \gui {Remote
Directory} field. For example, \c {/opt/usr/bin}. If the text
\gui {<no target path set>} is displayed, click it to specify a
folder.
\endlist
@@ -386,8 +396,7 @@
\o To specify the password, enter the following command:
\c{/usr/lib/mad-developer/devrootsh passwd user}
\o In \QC, select \gui {Tools > Options Linux Devices >
Device Configurations}.
\o In \QC, select \gui Tools > \gui Options > \gui Devices.
\o Specify the username \c user and the password in the device
configuration.

View File

@@ -20,10 +20,10 @@
/*!
\contentspage index.html
\previouspage creator-connecting-mobile.html
\previouspage creator-developing-maemo.html
\page creator-developing-meego.html
\if defined(qcmanual)
\nextpage creator-developing-generic-linux.html
\nextpage creator-developing-qnx.html
\else
\nextpage creator-developing-maemo.html
\endif
@@ -235,7 +235,7 @@
device.
You use a wizard to create the connections. You can edit the settings later
in \gui {Tools > Options > Linux Devices > Device Configurations}.
in \gui Tools > \gui Options > \gui Devices.
\image qtcreator-meego-device-configurations.png "MeeGo Device Configurations dialog"
@@ -294,21 +294,16 @@
port issue, switch to a different port or use WLAN to
connect to the device.
\o Select \gui {Tools > Options > Linux Devices > Device
Configurations > Add}.
\o Select \gui Tools > \gui Options > \gui Devices > \gui Add.
\o Select \gui {Device with MADDE support (Fremantle, Harmattan,
MeeGo) > Start Wizard}, and add a new configuration for a
hardware device.
\o Select \gui {MeeGo 1.2 Harmattan} > \gui {Start Wizard} to
add a new configuration for a device.
\image qtcreator-screenshot-devconf.png
\o In the \gui {The name to identify this configuration} field,
enter a name for the connection.
\o In the \gui {The system running on the device} field, select
the software platform of the device.
\o In the \gui {The kind of device} field, select
\gui {Hardware device}.
@@ -322,7 +317,7 @@
\o Click \gui Next.
\o Follow the instructions of the wizard to create the
connection.
configuration.
\endlist
@@ -335,20 +330,16 @@
\list a
\o In \QC, select \gui {Tools > Options > Linux
Devices > Device Configurations > Add} to add a new
configuration.
\o In \QC, select \gui Tools > \gui Options > \gui Devices >
\gui Add to add a new configuration.
\image qtcreator-meego-emulator-connection.png
\o Select \gui {MeeGo 1.2 Harmattan} > \gui {Start Wizard}.
\o In the \gui {The name to identify this configuration} field,
enter a name for the connection.
\o In the \gui {The system running on the device} field, select
the software platform to emulate.
\o In the \gui {The kind of device} field, select
\gui {Emulator (Qemu)}.
\gui Emulator.
\o Click \gui Next.
@@ -356,35 +347,59 @@
connection.
SDK Connectivity is not needed for emulator connections, and
therefore, you do nt need to authenticate the emulator
therefore, you do not need to authenticate the emulator
connection.
\endlist
\endif
\o To specify build and run settings:
\o Select \gui Tools > \gui Options > \gui {Build & Run} >
\gui Kits > \gui Add to add a kit for building for the device:
\list a
\o In the \gui {Device type} field, select
\gui {MeeGo 1.2 Harmattan}.
\o In the \gui Device field, select the device that you added
above.
\o In the \gui Sysroot field, specify the path to the sysroot.
By default, the \QSDK installer places sysroot in the
following folder:
\c{QtSDK\Madde\bin\sysroots\harmattan_sysroot_10.2011.34-1_slim}.
\o In the \gui {Compiler type} field, select GCC.
\o In the \gui Compiler field, specify the path to the GCC
compiler. By default, the \QSDK installer places the
compiler in the following folder:
\c{QtSDK\Madde\targets\harmattan_10.2011.34-1_rt1.2\bin\}.
\o In the \gui Debugger field, specify the path to GDB. By
default, the \QSDK installer places the debugger
in the following folder:
\c{QtSDK\Madde\targets\harmattan_10.2011.34-1_rt1.2\bin\}.
\o In the \gui {Qt version} field, choose the MADDE Qt version
for MeeGo 1.2 Harmattan. By default, the \QSDK installer
places qmake in the following folder:
\c{QtSDK\Madde\targets\harmattan_10.2011.34-1_rt1.2\bin\}.
\endlist
You can leave the \gui {Qt mkspec} field empty.
\o Open a project for an application you want to develop
for your device.
\o Click \gui Projects to open the projects mode.
\o Select \gui Projects > \gui {Build & Run} > \gui {Add Kit} to
add the kit that you specified above.
\o In the \gui{Build Settings} section, choose the MADDE Qt
version that was registered by the installation program.
\o Select \gui Run to specify run settings for the project.
\image qtcreator-screenshot-build-settings.png
\o In the \gui {Run Settings} section,
\gui {Device configuration} field, select the
device connection or the emulator connection.
\image qtcreator-screenshot-run-settings.png
\endlist
\note The new application wizards automatically set the folder
\o The Qt Quick project wizards automatically set the folder
where the file is installed on the device in the \gui {Remote
Directory} field. For example, \c {/opt/usr/bin}. If the text
\gui {<no target path set>} is displayed, click it to specify a
@@ -408,8 +423,7 @@
\o To specify the password, enter the following command:
\c{/usr/lib/mad-developer/devrootsh passwd user}
\o In \QC, select \gui {Tools > Options Linux Devices >
Device Configurations}.
\o In \QC, select \gui Tools > \gui Options > \gui Devices.
\o Specify the username \c user and the password in the device
configuration.

View File

@@ -27,7 +27,7 @@
\contentspage index.html
\previouspage creator-running-targets.html
\page creator-deployment.html
\nextpage creator-deployment-maemo.html
\nextpage creator-deploying-android.html
\title Deploying to Mobile Devices
@@ -38,26 +38,26 @@
\list
\o \l{Deploying Applications to Linux-Based Devices}
When you deploy the application on a Linux-based device, such
as \gui {Embedded Linux}, \gui Harmattan, or \gui{Maemo5}, \QC
copies the application files to the connected device. You
can test and debug the application on the device.
You can create Debian installation packages for MeeGo Harmattan and
Maemo 5 devices.
\o \l{Deploying Applications to QNX Devices}
When you deploy the application on a \gui{QNX} device, depending
on your target device, \QC either generates a BAR package in the
build directory and deploys it to the connected device, or copies
the application files to the connected device. You can test and
debug the application on the device.
\o \l{Deploying Applications to Android Devices}
When you deploy the application on an Android device, \QC copies
the application files to the device. In addition, you can determine
the Qt libraries to use.
\o \l{Deploying Applications to Linux-Based Devices}
When you deploy the application on a Linux-based device, such
as embedded Linux, MeeGo 1.2 Harmattan, or Maemo 5/Fremantle, \QC
copies the application files to the connected device. You
can test and debug the application on the device.
You can create Debian installation packages for MeeGo Harmattan and
Maemo 5/Fremantle devices.
\o \l{Deploying Applications to QNX Devices}
When you deploy the application on a QNX device, depending
on your target device, \QC either generates a BAR package in the
build directory and deploys it to the connected device, or copies
the application files to the connected device. You can test and
debug the application on the device.
\endlist
\section1 Related Topics

View File

@@ -25,9 +25,9 @@
/*!
\contentspage index.html
\previouspage creator-deploying-android.html
\previouspage creator-deployment-qnx.html
\page creator-connecting-mobile.html
\nextpage creator-developing-meego.html
\nextpage creator-developing-android.html
\title Connecting Mobile Targets
@@ -44,36 +44,6 @@
\list
\o \l{Connecting Embedded Linux Devices}
If you have a tool chain for building applications for embedded
Linux devices (with no MADDE support) installed on the development
PC, you can add it to \QC. Create device configurations and select
them in the \QC run settings.
\o \l{Connecting MeeGo Harmattan Devices}
MeeGo Harmattan is a Linux-based software platform developed by
Nokia and preinstalled on Nokia N950 and Nokia N9. It enables
developers to create applications using the Qt framework.
Use the SDK Connectivity tool that is preinstalled on the device to
create the device-side end point for USB and WLAN connections.
\o \l{Connecting Maemo Devices}
Maemo 5 (Fremantle) is a Linux-based software platform developed by
Nokia and delivered on the Nokia N900. Use a connectivity tool (Mad
Developer) to create the device-side end point for USB and WLAN
connections.
\o \l{Connecting QNX Devices}
You can connect QNX devices to the development PC to deploy, run and
debug applications on them from within \QC. This is currently only
supported for BlackBerry Playbook and QNX Neutrino devices, and
requires the BlackBerry NDK or the QNX SDK to be installed on the
development PC.
\o \l{Connecting Android Devices}
Qt applications for Android are compiled as \c {shared objects} that
@@ -83,6 +53,36 @@
Android version 1.6, or later. You must install the Qt for Android
SDK to develop for Android devices.
\o \l{Connecting Embedded Linux Devices}
If you have a tool chain for building applications for embedded
Linux devices (with no MADDE support) installed on the development
PC, you can add it to \QC. Create device configurations and select
them in the \QC run settings.
\o \l{Connecting Maemo Devices}
Maemo 5 (Fremantle) is a Linux-based software platform developed by
Nokia and delivered on the Nokia N900. Use a connectivity tool (Mad
Developer) to create the device-side end point for USB and WLAN
connections.
\o \l{Connecting MeeGo Harmattan Devices}
MeeGo Harmattan is a Linux-based software platform developed by
Nokia and preinstalled on Nokia N950 and Nokia N9. It enables
developers to create applications using the Qt framework.
Use the SDK Connectivity tool that is preinstalled on the device to
create the device-side end point for USB and WLAN connections.
\o \l{Connecting QNX Devices}
You can connect QNX devices to the development PC to deploy, run and
debug applications on them from within \QC. This is currently only
supported for BlackBerry Playbook and QNX Neutrino devices, and
requires the BlackBerry NDK or the QNX SDK to be installed on the
development PC.
\endlist
*/

View File

@@ -25,7 +25,7 @@
/*!
\contentspage index.html
\previouspage creator-remote-compiler.html
\previouspage creator-maemo-emulator.html
\page creator-testing.html
\nextpage creator-debugging.html

View File

@@ -108,15 +108,6 @@
development PC than to use the emulators. The emulator is installed
as part of the \QSDK.
\o \l{Building with Remote Compiler}
You can use a compilation service at Nokia Developer to build Qt
applications and create installation packages for mobile device
targets when you do not have the necessary tool chains and SDKs
installed or they are not supported on the development PC. You can
choose from a set of supported devices. You can install the Remote
Compiler target as part of the \QSDK.
\endlist
*/

View File

@@ -25,7 +25,7 @@
/*!
\contentspage index.html
\previouspage creator-developing-android.html
\previouspage creator-developing-qnx.html
\page creator-build-process-customizing.html
\nextpage creator-maemo-emulator.html

View File

@@ -440,6 +440,12 @@
\o \c {%CppHeaderSuffix%} is replaced by the default header suffix,
which is also defined in \gui {File Naming}.
\o \c {%CurrentDate%} is replaced by the current date in the format
\c {yyyy-MM-dd}.
\o \c {%CurrentTime%} is replaced by the current time in the short
format of the locale.
\endlist
\section1 Validating User Input

View File

@@ -49,8 +49,8 @@
\input projects/creator-projects-running-simulator.qdocinc
\if defined(qcmanual)
\input linux-mobile/creator-projects-running-madde.qdocinc
\input linux-mobile/creator-projects-running-generic-linux.qdocinc
\input linux-mobile/creator-projects-running-madde.qdocinc
\input qnx/creator-projects-running-qnx.qdocinc
\endif

View File

@@ -1,84 +0,0 @@
/****************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2012 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: http://www.qt-project.org/
**
**
** GNU Free Documentation License
**
** Alternatively, this file may be used under the terms of the GNU Free
** Documentation License version 1.3 as published by the Free Software
** Foundation and appearing in the file included in the packaging of this
** file.
**
**
****************************************************************************/
// **********************************************************************
// NOTE: the sections are not ordered by their logical order to avoid
// reshuffling the file each time the index order changes (i.e., often).
// Run the fixnavi.pl script to adjust the links to the index order.
// **********************************************************************
/*!
\contentspage index.html
\previouspage creator-maemo-emulator.html
\page creator-remote-compiler.html
\nextpage creator-testing.html
\title Building with Remote Compiler
The \gui {Remote Compiler} target is an interface to a compilation service
at Nokia Developer. It provides a simple, standardized environment for
building Qt applications and creating installation packages for mobile
device targets when you do not have the necessary tool chains and SDKs
installed or they are not supported on the development PC. You can choose
from a set of supported devices.
You need a Nokia Developer user account to use the Remote Compiler. You can
create an account for free at \l{http://www.developer.nokia.com/}
{Nokia Developer}.
\note Remote Compiler is an experimental component that is installed as
part of \QSDK.
\list 1
\o Select \gui {Start > \QSDK > Maintain \QSDK} to open the
\gui {Maintain \QSDK} tool.
\o In the \gui {Package Manager}, select \gui {Experimental >
Remote Compiler} to install Remote Compiler.
\o In \QC, choose \gui {Tools > Options > Build & Run > Remote Compiler}
to log on to Nokia Developer.
\image remotecompiler-fn-logon.png "Remote Compiler options"
\o Choose \gui {Projects}.
\o Click
\inlineimage qtcreator-qt4-addbutton.png "Add Target button"
and select \gui {Remote Compiler} to add Remote Compiler as a
target.
\o Click \gui Add to add mobile device platforms as build
configurations.
\o Click the \gui {Target Selector} and select a build configuration.
\o Choose \gui {Build > Build All}.
\endlist
The installation package is generated in the \gui {Build directory} on
the development PC.
For more information about Remote Compiler, choose \gui {Help > Contents >
Remote Compiler Manual}. The document is added during the installation of
Remote Compiler.
*/

View File

@@ -28,7 +28,7 @@
\contentspage index.html
\previouspage creator-deployment-maemo.html
\page creator-deployment-qnx.html
\nextpage creator-deploying-android.html
\nextpage creator-connecting-mobile.html
\title Deploying Applications to QNX Devices

View File

@@ -20,9 +20,9 @@
/*!
\contentspage index.html
\previouspage creator-developing-maemo.html
\previouspage creator-developing-meego.html
\page creator-developing-qnx.html
\nextpage creator-developing-android.html
\nextpage creator-build-process-customizing.html
\title Connecting QNX Devices

View File

@@ -235,21 +235,21 @@
\o \l{Running on Multiple Targets}
\o \l{Deploying to Mobile Devices}
\list
\o \l{Deploying Applications to Android Devices}
\o \l{Deploying Applications to Linux-Based Devices}
\o \l{Deploying Applications to QNX Devices}
\o \l{Deploying Applications to Android Devices}
\endlist
\o \l{Connecting Mobile Targets}
\list
\o \l{Connecting MeeGo Harmattan Devices}
\o \l{Connecting Android Devices}
\o \l{Connecting Embedded Linux Devices}
\o \l{Connecting Maemo Devices}
\o \l{Connecting MeeGo Harmattan Devices}
\o \l{Connecting QNX Devices}
\o \l{Connecting Android Devices}
\endlist
\o \l{Customizing the Build Process}
\o \l{Using Maemo or MeeGo Harmattan Emulator}
\o \l{Building with Remote Compiler}
\endlist
\o \l{Debugging and Analyzing}
\list

View File

@@ -63,6 +63,7 @@ Project {
"src/plugins/qmljstools/qmljstools.qbs",
"src/plugins/qmlprofiler/qmlprofiler.qbs",
"src/plugins/qmlprojectmanager/qmlprojectmanager.qbs",
"src/plugins/qnx/qnx.qbs",
"src/plugins/qt4projectmanager/qt4projectmanager.qbs",
"src/plugins/qtsupport/qtsupport.qbs",
"src/plugins/remotelinux/remotelinux.qbs",

View File

@@ -71,9 +71,13 @@ Hex2EncodedInt1, \
Hex2EncodedInt2, \
Hex2EncodedInt4, \
Hex2EncodedInt8, \
Hex2EncodedUInt1, \
Hex2EncodedUInt2, \
Hex2EncodedUInt4, \
Hex2EncodedUInt8, \
Hex2EncodedFloat4, \
Hex2EncodedFloat8 \
= range(23)
= range(27)
# Display modes
StopDisplay, \
@@ -517,6 +521,16 @@ def simpleEncoding(typeobj):
if code == BoolCode or code == CharCode:
return Hex2EncodedInt1
if code == IntCode:
if str(typeobj).find("unsigned") >= 0:
if typeobj.sizeof == 1:
return Hex2EncodedUInt1
if typeobj.sizeof == 2:
return Hex2EncodedUInt2
if typeobj.sizeof == 4:
return Hex2EncodedUInt4
if typeobj.sizeof == 8:
return Hex2EncodedUInt8
else:
if typeobj.sizeof == 1:
return Hex2EncodedInt1
if typeobj.sizeof == 2:

File diff suppressed because it is too large Load Diff

View File

@@ -2098,7 +2098,16 @@ bool Bind::visit(ExceptionDeclarationAST *ast)
}
DeclaratorIdAST *declaratorId = 0;
type = this->declarator(ast->declarator, type, &declaratorId);
const Name *argName = 0;
if (declaratorId && declaratorId->name)
argName = declaratorId->name->name;
Argument *arg = control()->newArgument(location(declaratorId, ast->firstToken()), argName);
arg->setType(type);
_scope->addMember(arg);
// unsigned dot_dot_dot_token = ast->dot_dot_dot_token;
return false;
}

View File

@@ -202,16 +202,20 @@ Aggregate::Aggregate(QObject *parent)
Deleting the aggregate automatically deletes all its components.
*/
Aggregate::~Aggregate()
{
QList<QObject *> components;
{
QWriteLocker locker(&lock());
foreach (QObject *component, m_components) {
disconnect(component, SIGNAL(destroyed(QObject*)), this, SLOT(deleteSelf(QObject*)));
aggregateMap().remove(component);
}
qDeleteAll(m_components);
components = m_components;
m_components.clear();
aggregateMap().remove(this);
}
qDeleteAll(components);
}
void Aggregate::deleteSelf(QObject *obj)
{

View File

@@ -460,6 +460,48 @@ bool ResolveExpression::visit(QualifiedNameAST *ast)
return false;
}
namespace {
class DeduceAutoCheck : public ASTVisitor
{
public:
DeduceAutoCheck(const Identifier *id, TranslationUnit *tu)
: ASTVisitor(tu), _id(id), _block(false)
{
accept(tu->ast());
}
virtual bool preVisit(AST *)
{
if (_block)
return false;
return true;
}
virtual bool visit(SimpleNameAST *ast)
{
if (ast->name
&& ast->name->identifier()
&& strcmp(ast->name->identifier()->chars(), _id->chars()) == 0) {
_block = true;
}
return false;
}
virtual bool visit(MemberAccessAST *ast)
{
accept(ast->base_expression);
return false;
}
const Identifier *_id;
bool _block;
};
} // namespace anonymous
bool ResolveExpression::visit(SimpleNameAST *ast)
{
QList<LookupItem> candidates = _context.lookup(ast->name, _scope);
@@ -473,8 +515,7 @@ bool ResolveExpression::visit(SimpleNameAST *ast)
if (item.declaration() == 0)
continue;
if (item.type().isAuto()
&& _blockedIds.find(ast->name->identifier()) == _blockedIds.end()) {
if (item.type().isAuto()) {
const Declaration *decl = item.declaration()->asDeclaration();
if (!decl)
continue;
@@ -498,13 +539,13 @@ bool ResolveExpression::visit(SimpleNameAST *ast)
Document::Ptr exprDoc =
documentForExpression(exprTyper.preprocessedExpression(initializer));
exprDoc->check();
ExpressionAST *exprAST = extractExpressionAST(exprDoc);
if (!exprAST)
DeduceAutoCheck deduceAuto(ast->name->identifier(), exprDoc->translationUnit());
if (deduceAuto._block)
continue;
_blockedIds.insert(ast->name->identifier());
const QList<LookupItem> &typeItems = resolve(exprAST, decl->enclosingScope());
_blockedIds.erase(ast->name->identifier());
const QList<LookupItem> &typeItems =
exprTyper(extractExpressionAST(exprDoc), exprDoc, decl->enclosingScope());
if (typeItems.empty())
continue;

View File

@@ -121,18 +121,11 @@ protected:
private:
struct IdentifierComp
{
bool operator()(const Identifier *a, const Identifier *b) const
{ return strcmp(a->chars(), b->chars()) < 0; }
};
Scope *_scope;
LookupContext _context;
Bind bind;
QList<LookupItem> _results;
bool _reference;
std::set<const Identifier *, IdentifierComp> _blockedIds; // Replace by a hash impl.
};
} // namespace CPlusPlus

View File

@@ -1542,6 +1542,8 @@ void Preprocessor::handleDefineDirective(PPToken *tk)
previousOffset = tk->offset;
previousLine = tk->lineno;
// Discard comments in macro definitions (keep comments flag doesn't apply here).
if (!tk->isComment())
bodyTokens.push_back(*tk);
lex(tk);

View File

@@ -198,18 +198,18 @@ void CodeFormatter::recalculateStateAfter(const QTextBlock &block)
switch (kind) {
case Colon: enter(binding_assignment); break; // oops, was a binding
case Var:
case Identifier: enter(property_type); break;
case Identifier: enter(property_name); break;
case List: enter(property_list_open); break;
default: leave(true); continue;
} break;
case property_type:
case property_name:
turnInto(property_maybe_initializer);
break;
case property_list_open:
if (m_currentLine.midRef(m_currentToken.begin(), m_currentToken.length) == QLatin1String(">"))
turnInto(property_maybe_initializer);
turnInto(property_name);
break;
case property_maybe_initializer:
@@ -939,7 +939,7 @@ CodeFormatter::TokenKind CodeFormatter::extendedTokenKind(const QmlJS::Token &to
if (text == "on")
return On;
if (text == "list")
return On;
return List;
} else if (kind == Keyword) {
const QChar char1 = text.at(0);
const QChar char2 = text.at(1);

View File

@@ -110,9 +110,9 @@ public: // must be public to make Q_GADGET introspection work
property_start, // after 'property'
default_property_start, // after 'default'
property_type, // after first identifier
property_list_open, // after 'list' as a type
property_maybe_initializer, // after
property_name, // after the type
property_maybe_initializer, // after the identifier
signal_start, // after 'signal'
signal_maybe_arglist, // after identifier

View File

@@ -2122,21 +2122,32 @@ SymbolGroupValue qobjectDerivedPrivate(const SymbolGroupValue &v,
return SymbolGroupValue(qwPrivateNode, v.context());
}
static bool dumpQObjectName(const SymbolGroupValue &qoPrivate, std::wostream &str)
{
// Qt 4: plain member.
if (QtInfo::get(qoPrivate.context()).version < 5) {
if (const SymbolGroupValue oName = qoPrivate["objectName"])
return dumpQString(oName, str);
}
// Qt 5: member of allocated extraData.
if (const SymbolGroupValue extraData = qoPrivate["extraData"])
if (extraData.pointerValue())
if (const SymbolGroupValue oName = extraData["objectName"])
return dumpQString(oName, str);
return false;
}
// Dump the object name
static inline bool dumpQWidget(const SymbolGroupValue &v, std::wostream &str, void **specialInfoIn = 0)
{
const QtInfo &qtInfo = QtInfo::get(v.context());
const SymbolGroupValue qwPrivate =
qobjectDerivedPrivate(v, qtInfo.qWidgetPrivateType, qtInfo);
if (!qwPrivate)
return false;
// QWidgetPrivate inherits QObjectPrivate
const SymbolGroupValue oName = qwPrivate[unsigned(0)]["objectName"];
if (!oName)
if (!qwPrivate || !dumpQObjectName(qwPrivate[unsigned(0)], str))
return false;
if (specialInfoIn)
*specialInfoIn = qwPrivate.node();
dumpQString(oName, str);
return true;
}
@@ -2144,16 +2155,13 @@ static inline bool dumpQWidget(const SymbolGroupValue &v, std::wostream &str, vo
static inline bool dumpQObject(const SymbolGroupValue &v, std::wostream &str, void **specialInfoIn = 0)
{
const std::string &qoPrivateType = QtInfo::get(v.context()).qObjectPrivateType;
if (SymbolGroupValue qoPrivate = v["d_ptr"]["d"].pointerTypeCast(qoPrivateType.c_str())) {
if (SymbolGroupValue oName = qoPrivate["objectName"]) {
const SymbolGroupValue qoPrivate = v["d_ptr"]["d"].pointerTypeCast(qoPrivateType.c_str());
if (!qoPrivate || !dumpQObjectName(qoPrivate, str))
return false;
if (specialInfoIn)
*specialInfoIn = qoPrivate.node();
dumpQString(oName, str);
return true;
}
}
return false;
}
// Dump the object name
static inline bool dumpQWindow(const SymbolGroupValue &v, std::wostream &str, void **specialInfoIn = 0)
@@ -2161,15 +2169,11 @@ static inline bool dumpQWindow(const SymbolGroupValue &v, std::wostream &str, vo
const QtInfo &qtInfo = QtInfo::get(v.context());
const SymbolGroupValue qwPrivate =
qobjectDerivedPrivate(v, qtInfo.qWindowPrivateType, qtInfo);
if (!qwPrivate)
return false;
// QWindowPrivate inherits QObjectPrivate
const SymbolGroupValue oName = qwPrivate[unsigned(0)]["objectName"]; // QWidgetPrivate inherits QObjectPrivate
if (!oName)
if (!qwPrivate || !dumpQObjectName(qwPrivate[unsigned(0)], str))
return false;
if (specialInfoIn)
*specialInfoIn = qwPrivate.node();
dumpQString(oName, str);
return true;
}

View File

@@ -832,6 +832,8 @@ SftpChannelPrivate::JobMap::Iterator SftpChannelPrivate::lookupJob(SftpJobId id)
void SftpChannelPrivate::closeHook()
{
for (JobMap::ConstIterator it = m_jobs.constBegin(); it != m_jobs.constEnd(); ++it)
emit finished(it.key(), tr("SFTP channel closed unexpectedly."));
m_jobs.clear();
m_incomingData.clear();
m_incomingPacket.clear();

View File

@@ -127,7 +127,8 @@ QStringList BuildableHelperLibrary::possibleQMakeCommands()
// On unix some distributions renamed qmake to avoid clashes
QStringList result;
result << QLatin1String("qmake-qt4") << QLatin1String("qmake4") << QLatin1String("qmake");
result << QLatin1String("qmake-qt4") << QLatin1String("qmake4")
<< QLatin1String("qmake-qt5") << QLatin1String("qmake5") << QLatin1String("qmake");
return result;
}

View File

@@ -12,6 +12,6 @@ lessThan(QT_MAJOR_VERSION, 5) {
win32:include(../../private_headers.pri)
}
win32: LIBS += -lUser32
win32: LIBS += -luser32
# PortsGatherer
win32: LIBS += -liphlpapi -lWs2_32
win32: LIBS += -liphlpapi -lws2_32

View File

@@ -68,11 +68,14 @@ bool AnalyzerRunControlFactory::canRun(RunConfiguration *runConfiguration, RunMo
return false;
}
RunControl *AnalyzerRunControlFactory::create(RunConfiguration *runConfiguration, RunMode mode)
RunControl *AnalyzerRunControlFactory::create(RunConfiguration *runConfiguration, RunMode mode, QString *errorMessage)
{
IAnalyzerTool *tool = AnalyzerManager::toolFromRunMode(mode);
if (!tool)
if (!tool) {
if (errorMessage)
*errorMessage = tr("No analyzer tool selected"); // never happens
return 0;
}
QTC_ASSERT(canRun(runConfiguration, mode), return 0);

View File

@@ -51,7 +51,8 @@ public:
QString displayName() const;
bool canRun(RunConfiguration *runConfiguration, ProjectExplorer::RunMode mode) const;
ProjectExplorer::RunControl *create(RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode);
ProjectExplorer::RunMode mode,
QString *errorMessage);
ProjectExplorer::IRunConfigurationAspect *createRunConfigurationAspect();
ProjectExplorer::RunConfigWidget *createConfigurationWidget(RunConfiguration *runConfiguration);

View File

@@ -69,7 +69,7 @@ StartRemoteDialog::StartRemoteDialog(QWidget *parent)
setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint);
setWindowTitle(tr("Start Remote Analysis"));
d->kitChooser = new KitChooser(this, KitChooser::RemoteDebugging);
d->kitChooser = new KitChooser(this);
d->executable = new QLineEdit(this);
d->arguments = new QLineEdit(this);
d->workingDirectory = new QLineEdit(this);
@@ -92,6 +92,7 @@ StartRemoteDialog::StartRemoteDialog(QWidget *parent)
QSettings *settings = Core::ICore::settings();
settings->beginGroup(QLatin1String("AnalyzerStartRemoteDialog"));
QString kit = settings->value(QLatin1String("profile")).toString();
d->kitChooser->populate();
d->kitChooser->setCurrentKitId(Core::Id(kit));
d->executable->setText(settings->value(QLatin1String("executable")).toString());
d->workingDirectory->setText(settings->value(QLatin1String("workingDirectory")).toString());

View File

@@ -81,7 +81,7 @@ static QStringList qtSoPaths(QtSupport::BaseQtVersion *qtVersion)
return paths.toList();
}
RunControl *AndroidDebugSupport::createDebugRunControl(AndroidRunConfiguration *runConfig)
RunControl *AndroidDebugSupport::createDebugRunControl(AndroidRunConfiguration *runConfig, QString *errorMessage)
{
Target *target = runConfig->target();
Qt4Project *project = static_cast<Qt4Project *>(target->project());
@@ -119,7 +119,7 @@ RunControl *AndroidDebugSupport::createDebugRunControl(AndroidRunConfiguration *
}
DebuggerRunControl * const debuggerRunControl
= DebuggerPlugin::createDebugger(params, runConfig);
= DebuggerPlugin::createDebugger(params, runConfig, errorMessage);
new AndroidDebugSupport(runConfig, debuggerRunControl);
return debuggerRunControl;
}

View File

@@ -47,7 +47,8 @@ class AndroidDebugSupport : public QObject
Q_OBJECT
public:
static ProjectExplorer::RunControl *createDebugRunControl(AndroidRunConfiguration *runConfig);
static ProjectExplorer::RunControl *createDebugRunControl(AndroidRunConfiguration *runConfig,
QString *errorMessage);
AndroidDebugSupport(AndroidRunConfiguration *runConfig,
Debugger::DebuggerRunControl *runControl);

View File

@@ -71,14 +71,15 @@ bool AndroidPlugin::initialize(const QStringList &arguments, QString *errorMessa
addAutoReleasedObject(new Internal::AndroidToolChainFactory);
addAutoReleasedObject(new Internal::AndroidDeployConfigurationFactory);
addAutoReleasedObject(new Internal::AndroidDeviceFactory);
ProjectExplorer::DeviceManager *dm = ProjectExplorer::DeviceManager::instance();
if (dm->find(Core::Id(Constants::ANDROID_DEVICE_ID)).isNull())
dm->addDevice(ProjectExplorer::IDevice::Ptr(new Internal::AndroidDevice));
return true;
}
void AndroidPlugin::extensionsInitialized()
{ }
{
ProjectExplorer::DeviceManager *dm = ProjectExplorer::DeviceManager::instance();
if (dm->find(Core::Id(Constants::ANDROID_DEVICE_ID)).isNull())
dm->addDevice(ProjectExplorer::IDevice::Ptr(new Internal::AndroidDevice));
}
} // namespace Android

View File

@@ -171,7 +171,7 @@ bool AndroidRunControlFactory::canRun(RunConfiguration *runConfiguration,
}
RunControl *AndroidRunControlFactory::create(RunConfiguration *runConfig,
ProjectExplorer::RunMode mode)
ProjectExplorer::RunMode mode, QString *errorMessage)
{
Q_ASSERT(canRun(runConfig, mode));
AndroidRunConfiguration *rc = qobject_cast<AndroidRunConfiguration *>(runConfig);
@@ -179,7 +179,7 @@ RunControl *AndroidRunControlFactory::create(RunConfiguration *runConfig,
if (mode == NormalRunMode)
return new AndroidRunControl(rc);
else
return AndroidDebugSupport::createDebugRunControl(rc);
return AndroidDebugSupport::createDebugRunControl(rc, errorMessage);
}
QString AndroidRunControlFactory::displayName() const

View File

@@ -80,7 +80,8 @@ public:
bool canRun(ProjectExplorer::RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode) const;
ProjectExplorer::RunControl *create(ProjectExplorer::RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode);
ProjectExplorer::RunMode mode,
QString *errorMessage);
};
} // namespace Internal

View File

@@ -168,14 +168,23 @@ void MakeStep::setClean(bool clean)
bool MakeStep::init()
{
AutotoolsBuildConfiguration *bc = autotoolsBuildConfiguration();
if (!bc)
bc = static_cast<AutotoolsBuildConfiguration *>(target()->activeBuildConfiguration());
m_tasks.clear();
ToolChain *tc = ToolChainKitInformation::toolChain(target()->kit());
if (!tc) {
m_tasks.append(Task(Task::Error, tr("Qt Creator needs a compiler set up to build. Configure a compiler in the kit options."),
Utils::FileName(), -1,
Core::Id(ProjectExplorer::Constants::TASK_CATEGORY_BUILDSYSTEM)));
return true; // otherwise the tasks will not get reported
}
QString arguments = Utils::QtcProcess::joinArgs(m_buildTargets);
Utils::QtcProcess::addArgs(&arguments, additionalArguments());
setIgnoreReturnValue(m_clean);
ToolChain *tc = ProjectExplorer::ToolChainKitInformation::toolChain(target()->kit());
ProcessParameters *pp = processParameters();
pp->setMacroExpander(bc->macroExpander());
pp->setEnvironment(bc->environment());
@@ -193,6 +202,18 @@ bool MakeStep::init()
void MakeStep::run(QFutureInterface<bool> &interface)
{
// Warn on common error conditions:
bool canContinue = true;
foreach (const Task &t, m_tasks) {
addTask(t);
canContinue = false;
}
if (!canContinue) {
emit addOutput(tr("Configuration is faulty. Check the Issues view for details."), BuildStep::MessageOutput);
interface.reportResult(false);
return;
}
AbstractProcessStep::run(interface);
}

View File

@@ -36,6 +36,7 @@
#define MAKESTEP_H
#include <projectexplorer/abstractprocessstep.h>
#include <projectexplorer/task.h>
QT_BEGIN_NAMESPACE
class QLineEdit;
@@ -124,6 +125,7 @@ private:
QStringList m_buildTargets;
QString m_additionalArguments;
bool m_clean;
QList<ProjectExplorer::Task> m_tasks;
};
///////////////////////////////

View File

@@ -132,12 +132,20 @@ bool MakeStep::init()
if (!bc)
bc = static_cast<CMakeBuildConfiguration *>(target()->activeBuildConfiguration());
m_tasks.clear();
ToolChain *tc = ToolChainKitInformation::toolChain(target()->kit());
if (!tc) {
m_tasks.append(Task(Task::Error, tr("Qt Creator needs a compiler set up to build. Configure a compiler in the kit options."),
Utils::FileName(), -1,
Core::Id(ProjectExplorer::Constants::TASK_CATEGORY_BUILDSYSTEM)));
return true; // otherwise the tasks will not get reported
}
QString arguments = Utils::QtcProcess::joinArgs(m_buildTargets);
Utils::QtcProcess::addArgs(&arguments, additionalArguments());
setIgnoreReturnValue(m_clean);
ProjectExplorer::ToolChain *tc = ProjectExplorer::ToolChainKitInformation::toolChain(target()->kit());
ProcessParameters *pp = processParameters();
pp->setMacroExpander(bc->macroExpander());
pp->setEnvironment(bc->environment());
@@ -158,6 +166,17 @@ bool MakeStep::init()
void MakeStep::run(QFutureInterface<bool> &fi)
{
bool canContinue = true;
foreach (const Task &t, m_tasks) {
addTask(t);
canContinue = false;
}
if (!canContinue) {
emit addOutput(tr("Configuration is faulty. Check the Issues view for details."), BuildStep::MessageOutput);
fi.reportResult(false);
return;
}
m_futureInterface = &fi;
m_futureInterface->setProgressRange(0, 100);
AbstractProcessStep::run(fi);

View File

@@ -94,6 +94,7 @@ private:
QFutureInterface<bool> *m_futureInterface;
QStringList m_buildTargets;
QString m_additionalArguments;
QList<ProjectExplorer::Task> m_tasks;
};
class MakeStepConfigWidget :public ProjectExplorer::BuildStepConfigWidget

View File

@@ -2085,6 +2085,8 @@ QTextCodec *EditorManager::defaultTextCodec() const
if (QTextCodec *candidate = QTextCodec::codecForName(
settings->value(QLatin1String(Constants::SETTINGS_DEFAULTTEXTENCODING)).toByteArray()))
return candidate;
if (QTextCodec *defaultUTF8 = QTextCodec::codecForName("UTF-8"))
return defaultUTF8;
return QTextCodec::codecForLocale();
}

View File

@@ -416,8 +416,8 @@ void CppToolsPlugin::test_codegen_definition_empty_class()
QCOMPARE(loc.fileName(), dst->fileName());
QCOMPARE(loc.prefix(), QLatin1String("\n\n"));
QCOMPARE(loc.suffix(), QString());
QCOMPARE(loc.line(), 1U);
QCOMPARE(loc.column(), 7U);
QCOMPARE(loc.line(), 3U);
QCOMPARE(loc.column(), 1U);
}
void CppToolsPlugin::test_codegen_definition_first_member()

View File

@@ -151,7 +151,7 @@ BreakpointDialog::BreakpointDialog(BreakpointModelId id, QWidget *parent)
: QDialog(parent), m_enabledParts(~0), m_previousType(UnknownType),
m_firstTypeChange(true)
{
setWindowTitle(tr("Edit Breakpoint Properties", 0, QApplication::UnicodeUTF8));
setWindowTitle(tr("Edit Breakpoint Properties"));
QGroupBox *groupBoxBasic = new QGroupBox(tr("Basic"), this);

View File

@@ -159,3 +159,18 @@ include(qml/qml.pri)
include(namedemangler/namedemangler.pri)
include(shared/shared.pri)
equals(TEST, 1):!isEmpty(copydata) {
TEST_DIR = ../../../tests/manual/debugger/simple
INPUT_FILE = $$PWD/$$TEST_DIR/simple.pro
OUTPUT_DIR = $$OUT_PWD/$$TEST_DIR
win32 {
INPUT_FILE ~= s,/,\\\\,g
OUTPUT_DIR ~= s,/,\\\\,g
}
testfile.target = test_resources
testfile.commands = ($$QMAKE_CHK_DIR_EXISTS $$OUTPUT_DIR $$QMAKE_CHK_EXISTS_GLUE $$QMAKE_MKDIR $$OUTPUT_DIR) \
&& $$QMAKE_COPY $$INPUT_FILE $$OUTPUT_DIR
QMAKE_EXTRA_TARGETS += testfile
PRE_TARGETDEPS += $$testfile.target
}

View File

@@ -4,6 +4,7 @@ import "../QtcPlugin.qbs" as QtcPlugin
QtcPlugin {
name: "Debugger"
type: base.concat(["installed_content"])
Depends { name: "Qt"; submodules: ["widgets", "network", "script"] }
Depends { name: "Core" }
@@ -31,6 +32,13 @@ QtcPlugin {
"../../shared/registryaccess/"
]
Group {
condition: qbs.buildVariant === "debug"
qbs.installDir: "tests/manual/debugger/simple/"
fileTags: ["install"]
files: ["../../../tests/manual/debugger/simple/simple.pro"]
}
files: [
"debugger.qrc",
"debuggerkitconfigwidget.cpp",

View File

@@ -39,7 +39,6 @@
#include <coreplugin/icore.h>
#include <projectexplorer/abi.h>
#include <projectexplorer/kitchooser.h>
#include <projectexplorer/kitinformation.h>
#include <utils/historycompleter.h>
#include <utils/pathchooser.h>
@@ -89,6 +88,8 @@ class StartApplicationDialogPrivate
{
public:
KitChooser *kitChooser;
QLabel *serverPortLabel;
QSpinBox *serverPortSpinBox;
PathChooser *localExecutablePathChooser;
FancyLineEdit *arguments;
PathChooser *workingDirectory;
@@ -109,6 +110,36 @@ Q_DECLARE_METATYPE(Debugger::Internal::StartApplicationParameters)
namespace Debugger {
namespace Internal {
///////////////////////////////////////////////////////////////////////
//
// DebuggerKitChooser
//
///////////////////////////////////////////////////////////////////////
DebuggerKitChooser::DebuggerKitChooser(Mode mode, QWidget *parent)
: ProjectExplorer::KitChooser(parent)
, m_hostAbi(ProjectExplorer::Abi::hostAbi())
, m_mode(mode)
{
}
// Match valid debuggers and restrict local debugging to compatible toolchains.
bool DebuggerKitChooser::kitMatches(const ProjectExplorer::Kit *k) const
{
if (!DebuggerKitInformation::isValidDebugger(k))
return false;
if (m_mode == LocalDebugging) {
const ProjectExplorer::ToolChain *tc = ToolChainKitInformation::toolChain(k);
return tc && tc->targetAbi().os() == m_hostAbi.os();
}
return true;
}
QString DebuggerKitChooser::kitToolTip(Kit *k) const
{
return DebuggerKitInformation::userOutput(k);
}
///////////////////////////////////////////////////////////////////////
//
// StartApplicationParameters
@@ -128,6 +159,7 @@ public:
bool operator!=(const StartApplicationParameters &p) const { return !equals(p); }
Id kitId;
uint serverPort;
QString localExecutable;
QString processArgs;
QString workingDirectory;
@@ -145,6 +177,7 @@ StartApplicationParameters::StartApplicationParameters() :
bool StartApplicationParameters::equals(const StartApplicationParameters &rhs) const
{
return localExecutable == rhs.localExecutable
&& serverPort == rhs.serverPort
&& processArgs == rhs.processArgs
&& workingDirectory == rhs.workingDirectory
&& breakAtMain == rhs.breakAtMain
@@ -176,6 +209,7 @@ QString StartApplicationParameters::displayName() const
void StartApplicationParameters::toSettings(QSettings *settings) const
{
settings->setValue(_("LastProfileId"), kitId.toString());
settings->setValue(_("LastServerPort"), serverPort);
settings->setValue(_("LastExternalExecutable"), localExecutable);
settings->setValue(_("LastExternalExecutableArguments"), processArgs);
settings->setValue(_("LastExternalWorkingDirectory"), workingDirectory);
@@ -189,6 +223,7 @@ void StartApplicationParameters::fromSettings(const QSettings *settings)
{
const QString kitIdString = settings->value(_("LastProfileId")).toString();
kitId = kitIdString.isEmpty() ? Id() : Id(kitIdString);
serverPort = settings->value(_("LastServerPort")).toUInt();
localExecutable = settings->value(_("LastExternalExecutable")).toString();
processArgs = settings->value(_("LastExternalExecutableArguments")).toString();
workingDirectory = settings->value(_("LastExternalWorkingDirectory")).toString();
@@ -215,6 +250,11 @@ StartApplicationDialog::StartApplicationDialog(QWidget *parent)
d->localExecutablePathChooser->setPromptDialogTitle(tr("Select Executable"));
d->localExecutablePathChooser->lineEdit()->setHistoryCompleter(QLatin1String("LocalExecutable"));
d->serverPortSpinBox = new QSpinBox(this);
d->serverPortSpinBox->setRange(1, 65535);
d->serverPortLabel = new QLabel(tr("Server port:"), this);
d->arguments = new FancyLineEdit(this);
d->arguments->setHistoryCompleter(QLatin1String("CommandlineArguments"));
@@ -225,7 +265,8 @@ StartApplicationDialog::StartApplicationDialog(QWidget *parent)
d->runInTerminalCheckBox = new QCheckBox(this);
d->kitChooser = new KitChooser(this, KitChooser::LocalDebugging);
d->kitChooser = new DebuggerKitChooser(DebuggerKitChooser::LocalDebugging, this);
d->kitChooser->populate();
d->breakAtMainCheckBox = new QCheckBox(this);
d->breakAtMainCheckBox->setText(QString());
@@ -264,6 +305,7 @@ StartApplicationDialog::StartApplicationDialog(QWidget *parent)
QFormLayout *formLayout = new QFormLayout();
formLayout->setFieldGrowthPolicy(QFormLayout::AllNonFixedFieldsGrow);
formLayout->addRow(tr("&Kit:"), d->kitChooser);
formLayout->addRow(d->serverPortLabel, d->serverPortSpinBox);
formLayout->addRow(tr("Local &executable:"), d->localExecutablePathChooser);
formLayout->addRow(tr("Command line &arguments:"), d->arguments);
formLayout->addRow(tr("&Working directory:"), d->workingDirectory);
@@ -304,12 +346,6 @@ void StartApplicationDialog::setHistory(const QList<StartApplicationParameters>
}
}
void StartApplicationDialog::hideStartScript()
{
d->serverStartScriptPathChooser->setVisible(false);
d->serverStartScriptLabel->setVisible(false);
}
void StartApplicationDialog::historyIndexChanged(int index)
{
if (index < 0)
@@ -319,11 +355,6 @@ void StartApplicationDialog::historyIndexChanged(int index)
setParameters(v.value<StartApplicationParameters>());
}
Id StartApplicationDialog::kitId() const
{
return d->kitChooser->currentKitId();
}
void StartApplicationDialog::updateState()
{
bool okEnabled = d->localExecutablePathChooser->isValid();
@@ -332,6 +363,7 @@ void StartApplicationDialog::updateState()
bool StartApplicationDialog::run(QWidget *parent, QSettings *settings, DebuggerStartParameters *sp)
{
const bool attachRemote = sp->startMode == AttachToRemoteServer;
const QString settingsGroup = QLatin1String("DebugMode");
const QString arrayName = QLatin1String("StartApplication");
@@ -353,8 +385,13 @@ bool StartApplicationDialog::run(QWidget *parent, QSettings *settings, DebuggerS
StartApplicationDialog dialog(parent);
dialog.setHistory(history);
dialog.setParameters(history.back());
if (sp->startMode == AttachToRemoteServer)
dialog.hideStartScript();
if (attachRemote) {
dialog.d->serverStartScriptPathChooser->setVisible(false);
dialog.d->serverStartScriptLabel->setVisible(false);
} else {
dialog.d->serverPortSpinBox->setVisible(false);
dialog.d->serverPortLabel->setVisible(false);
}
if (dialog.exec() != QDialog::Accepted)
return false;
@@ -374,10 +411,10 @@ bool StartApplicationDialog::run(QWidget *parent, QSettings *settings, DebuggerS
}
Kit *kit = dialog.d->kitChooser->currentKit();
QTC_ASSERT(kit, return false);
fillParameters(sp, kit);
QTC_ASSERT(kit && fillParameters(sp, kit), return false);
sp->executable = newParameters.localExecutable;
sp->remoteChannel = sp->connParams.host + QLatin1Char(':') + QString::number(newParameters.serverPort);
sp->displayName = newParameters.displayName();
sp->workingDirectory = newParameters.workingDirectory;
sp->useTerminal = newParameters.runInTerminal;
@@ -389,6 +426,7 @@ bool StartApplicationDialog::run(QWidget *parent, QSettings *settings, DebuggerS
bool isLocal = DeviceKitInformation::device(kit)->type()
== ProjectExplorer::Constants::DESKTOP_DEVICE_TYPE;
if (!attachRemote)
sp->startMode = isLocal ? StartExternal : StartRemoteProcess;
return true;
}
@@ -396,6 +434,7 @@ bool StartApplicationDialog::run(QWidget *parent, QSettings *settings, DebuggerS
StartApplicationParameters StartApplicationDialog::parameters() const
{
StartApplicationParameters result;
result.serverPort = d->serverPortSpinBox->value();
result.localExecutable = d->localExecutablePathChooser->path();
result.serverStartScript = d->serverStartScriptPathChooser->path();
result.kitId = d->kitChooser->currentKitId();
@@ -410,6 +449,7 @@ StartApplicationParameters StartApplicationDialog::parameters() const
void StartApplicationDialog::setParameters(const StartApplicationParameters &p)
{
d->kitChooser->setCurrentKitId(p.kitId);
d->serverPortSpinBox->setValue(p.serverPort);
d->localExecutablePathChooser->setPath(p.localExecutable);
d->serverStartScriptPathChooser->setPath(p.serverStartScript);
d->debuginfoPathChooser->setPath(p.debugInfoLocation);
@@ -440,7 +480,8 @@ AttachToQmlPortDialog::AttachToQmlPortDialog(QWidget *parent)
setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint);
setWindowTitle(tr("Start Debugger"));
d->kitChooser = new KitChooser(this);
d->kitChooser = new DebuggerKitChooser(DebuggerKitChooser::RemoteDebugging, this);
d->kitChooser->populate();
d->portSpinBox = new QSpinBox(this);
d->portSpinBox->setMaximum(65535);

View File

@@ -31,6 +31,9 @@
#ifndef DEBUGGER_DIALOGS_H
#define DEBUGGER_DIALOGS_H
#include <projectexplorer/kitchooser.h>
#include <projectexplorer/abi.h>
#include <QDialog>
#include <QHash>
#include <QStringList>
@@ -58,6 +61,22 @@ class StartApplicationParameters;
class StartApplicationDialogPrivate;
class StartRemoteEngineDialogPrivate;
class DebuggerKitChooser : public ProjectExplorer::KitChooser {
Q_OBJECT
public:
enum Mode { RemoteDebugging, LocalDebugging };
explicit DebuggerKitChooser(Mode mode = RemoteDebugging, QWidget *parent = 0);
protected:
bool kitMatches(const ProjectExplorer::Kit *k) const;
QString kitToolTip(ProjectExplorer::Kit *k) const;
private:
const ProjectExplorer::Abi m_hostAbi;
const Mode m_mode;
};
class StartApplicationDialog : public QDialog
{
Q_OBJECT
@@ -77,8 +96,6 @@ private:
StartApplicationParameters parameters() const;
void setParameters(const StartApplicationParameters &p);
void setHistory(const QList<StartApplicationParameters> &l);
void hideStartScript();
Core::Id kitId() const;
StartApplicationDialogPrivate *d;
};

View File

@@ -29,7 +29,6 @@
**************************************************************************/
#include "debuggerkitconfigwidget.h"
#include "debuggerkitinformation.h"
#include <projectexplorer/abi.h>
@@ -48,6 +47,8 @@
#include <QHBoxLayout>
#include <QPushButton>
#include <QVBoxLayout>
#include <QLabel>
#include <QComboBox>
namespace Debugger {
namespace Internal {
@@ -55,6 +56,7 @@ namespace Internal {
static const char dgbToolsDownloadLink32C[] = "http://www.microsoft.com/whdc/devtools/debugging/installx86.Mspx";
static const char dgbToolsDownloadLink64C[] = "http://www.microsoft.com/whdc/devtools/debugging/install64bit.Mspx";
// -----------------------------------------------------------------------
// DebuggerKitConfigWidget:
// -----------------------------------------------------------------------
@@ -65,34 +67,26 @@ DebuggerKitConfigWidget::DebuggerKitConfigWidget(ProjectExplorer::Kit *k,
ProjectExplorer::KitConfigWidget(parent),
m_kit(k),
m_info(ki),
m_chooser(new Utils::PathChooser)
m_comboBox(new QComboBox(this)),
m_label(new QLabel(this)),
m_chooser(new Utils::PathChooser(this))
{
setToolTip(tr("The debugger to use for this kit."));
QVBoxLayout *layout = new QVBoxLayout(this);
layout->setMargin(0);
ProjectExplorer::ToolChain *tc = ProjectExplorer::ToolChainKitInformation::toolChain(k);
if (tc && tc->targetAbi().os() == ProjectExplorer::Abi::WindowsOS
&& tc->targetAbi().osFlavor() != ProjectExplorer::Abi::WindowsMSysFlavor) {
QLabel *msvcDebuggerConfigLabel = new QLabel;
#ifdef Q_OS_WIN
const bool is64bit = Utils::winIs64BitSystem();
#else
const bool is64bit = false;
#endif
const QString link = is64bit ? QLatin1String(dgbToolsDownloadLink64C) : QLatin1String(dgbToolsDownloadLink32C);
//: Label text for path configuration. %2 is "x-bit version".
msvcDebuggerConfigLabel->setText(tr("<html><body><p>Specify the path to the "
"<a href=\"%1\">Windows Console Debugger executable</a>"
" (%2) here.</p>"
"</body></html>").arg(link, (is64bit ? tr("64-bit version")
: tr("32-bit version"))));
msvcDebuggerConfigLabel->setTextInteractionFlags(Qt::TextBrowserInteraction);
msvcDebuggerConfigLabel->setOpenExternalLinks(true);
layout->addWidget(msvcDebuggerConfigLabel);
m_comboBox->addItem(DebuggerKitInformation::debuggerEngineName(GdbEngineType), QVariant(int(GdbEngineType)));
if (ProjectExplorer::Abi::hostAbi().os() == ProjectExplorer::Abi::WindowsOS) {
m_comboBox->addItem(DebuggerKitInformation::debuggerEngineName(CdbEngineType), QVariant(int(CdbEngineType)));
} else {
m_comboBox->addItem(DebuggerKitInformation::debuggerEngineName(LldbEngineType), QVariant(int(LldbEngineType)));
}
layout->addWidget(m_comboBox);
m_label->setTextInteractionFlags(Qt::TextBrowserInteraction);
m_label->setOpenExternalLinks(true);
layout->addWidget(m_label);
m_chooser->setContentsMargins(0, 0, 0, 0);
m_chooser->setExpectedKind(Utils::PathChooser::ExistingCommand);
@@ -102,6 +96,15 @@ DebuggerKitConfigWidget::DebuggerKitConfigWidget(ProjectExplorer::Kit *k,
discard();
connect(m_chooser, SIGNAL(changed(QString)), this, SIGNAL(dirty()));
connect(m_comboBox, SIGNAL(currentIndexChanged(int)), this, SIGNAL(dirty()));
connect(m_comboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(refreshLabel()));
}
void DebuggerKitConfigWidget::addToLayout(QGridLayout *layout, int row)
{
addLabel(layout, row);
layout->addWidget(this, row, WidgetColumn, 3 , 1);
addButtonWidget(layout, row + 2);
}
QString DebuggerKitConfigWidget::displayName() const
@@ -111,23 +114,26 @@ QString DebuggerKitConfigWidget::displayName() const
void DebuggerKitConfigWidget::makeReadOnly()
{
m_comboBox->setEnabled(false);
m_chooser->setEnabled(false);
}
void DebuggerKitConfigWidget::apply()
{
Utils::FileName fn = m_chooser->fileName();
DebuggerKitInformation::setDebuggerCommand(m_kit, fn);
DebuggerKitInformation::setDebuggerItem(m_kit, DebuggerKitInformation::DebuggerItem(engineType(), fileName()));
}
void DebuggerKitConfigWidget::discard()
{
m_chooser->setFileName(DebuggerKitInformation::debuggerCommand(m_kit));
const DebuggerKitInformation::DebuggerItem item = DebuggerKitInformation::debuggerItem(m_kit);
setEngineType(item.engineType);
setFileName(item.binary);
}
bool DebuggerKitConfigWidget::isDirty() const
{
return m_chooser->fileName() != DebuggerKitInformation::debuggerCommand(m_kit);
const DebuggerKitInformation::DebuggerItem item = DebuggerKitInformation::debuggerItem(m_kit);
return item.engineType != engineType() || item.binary != fileName();
}
QWidget *DebuggerKitConfigWidget::buttonWidget() const
@@ -137,8 +143,66 @@ QWidget *DebuggerKitConfigWidget::buttonWidget() const
void DebuggerKitConfigWidget::autoDetectDebugger()
{
QVariant v = m_info->defaultValue(m_kit);
m_chooser->setFileName(Utils::FileName::fromString(v.toString()));
const DebuggerKitInformation::DebuggerItem item = DebuggerKitInformation::autoDetectItem(m_kit);
setEngineType(item.engineType);
setFileName(item.binary);
}
DebuggerEngineType DebuggerKitConfigWidget::engineType() const
{
const int index = m_comboBox->currentIndex();
return static_cast<DebuggerEngineType>(m_comboBox->itemData(index).toInt());
}
void DebuggerKitConfigWidget::setEngineType(DebuggerEngineType et)
{
const int size = m_comboBox->count();
for (int i = 0; i < size; ++i) {
if (m_comboBox->itemData(i).toInt() == et) {
m_comboBox->setCurrentIndex(i);
refreshLabel();
break;
}
}
}
Utils::FileName DebuggerKitConfigWidget::fileName() const
{
return m_chooser->fileName();
}
void DebuggerKitConfigWidget::setFileName(const Utils::FileName &fn)
{
m_chooser->setFileName(fn);
}
void DebuggerKitConfigWidget::refreshLabel()
{
QString text;
const DebuggerEngineType type = engineType();
switch (type) {
case CdbEngineType: {
#ifdef Q_OS_WIN
const bool is64bit = Utils::winIs64BitSystem();
#else
const bool is64bit = false;
#endif
const QString link = is64bit ? QLatin1String(dgbToolsDownloadLink64C) : QLatin1String(dgbToolsDownloadLink32C);
const QString versionString = is64bit ? tr("64-bit version") : tr("32-bit version");
//: Label text for path configuration. %2 is "x-bit version".
text = tr("<html><body><p>Specify the path to the "
"<a href=\"%1\">Windows Console Debugger executable</a>"
" (%2) here.</p>""</body></html>").arg(link, versionString);
}
break;
default:
break;
}
m_label->setText(text);
m_label->setVisible(!text.isEmpty());
m_chooser->setCommandVersionArguments(type == CdbEngineType ?
QStringList(QLatin1String("-version")) :
QStringList(QLatin1String("--version")));
}
} // namespace Internal

View File

@@ -33,11 +33,16 @@
#include <projectexplorer/kitconfigwidget.h>
#include <QLabel>
#include <debuggerkitinformation.h>
#include "debuggerconstants.h"
QT_FORWARD_DECLARE_CLASS(QLabel)
QT_FORWARD_DECLARE_CLASS(QComboBox)
namespace ProjectExplorer { class Kit; }
namespace Utils { class PathChooser; }
namespace Utils {
class PathChooser;
class FileName;
}
namespace Debugger {
class DebuggerKitInformation;
@@ -64,13 +69,23 @@ public:
void discard();
bool isDirty() const;
QWidget *buttonWidget() const;
void addToLayout(QGridLayout *layout, int row);
DebuggerEngineType engineType() const;
void setEngineType(DebuggerEngineType et);
Utils::FileName fileName() const;
void setFileName(const Utils::FileName &fn);
private slots:
void autoDetectDebugger();
void refreshLabel();
private:
ProjectExplorer::Kit *m_kit;
const DebuggerKitInformation *m_info;
QComboBox *m_comboBox;
QLabel *m_label;
Utils::PathChooser *m_chooser;
};

View File

@@ -114,12 +114,32 @@ static QPair<QString, QString> autoDetectCdbDebugger()
namespace Debugger {
static DebuggerEngineType engineTypeFromBinary(const QString &binary)
{
if (binary.contains(QLatin1String("cdb"), Qt::CaseInsensitive))
return CdbEngineType;
if (binary.contains(QLatin1String("lldb"), Qt::CaseInsensitive))
return LldbEngineType;
return GdbEngineType;
}
// --------------------------------------------------------------------------
// DebuggerKitInformation:
// --------------------------------------------------------------------------
static const char DEBUGGER_INFORMATION[] = "Debugger.Information";
DebuggerKitInformation::DebuggerItem::DebuggerItem()
: engineType(NoEngineType)
{
}
DebuggerKitInformation::DebuggerItem::DebuggerItem(DebuggerEngineType et, const Utils::FileName &fn)
: engineType(et)
, binary(fn)
{
}
DebuggerKitInformation::DebuggerKitInformation()
{
setObjectName(QLatin1String("DebuggerKitInformation"));
@@ -136,9 +156,10 @@ unsigned int DebuggerKitInformation::priority() const
return 28000;
}
QVariant DebuggerKitInformation::defaultValue(Kit *k) const
DebuggerKitInformation::DebuggerItem DebuggerKitInformation::autoDetectItem(const Kit *k)
{
ToolChain *tc = ToolChainKitInformation::toolChain(k);
DebuggerItem result;
const ToolChain *tc = ToolChainKitInformation::toolChain(k);
Abi abi = Abi::hostAbi();
if (tc)
abi = tc->targetAbi();
@@ -146,59 +167,100 @@ QVariant DebuggerKitInformation::defaultValue(Kit *k) const
// CDB for windows:
if (abi.os() == Abi::WindowsOS && abi.osFlavor() != Abi::WindowsMSysFlavor) {
QPair<QString, QString> cdbs = autoDetectCdbDebugger();
return (abi.wordWidth() == 32) ? cdbs.first : cdbs.second;
}
// fall back to system GDB:
QString debugger = QLatin1String("gdb");
if (tc) {
// Check suggestions from the SDK:
const QString path = tc->suggestedDebugger().toString();
if (!path.isEmpty()) {
QFileInfo fi(path);
if (fi.isAbsolute())
return path;
debugger = path;
}
}
Environment env = Environment::systemEnvironment();
return env.searchInPath(debugger);
}
QList<Task> DebuggerKitInformation::validate(Kit *k) const
{
const Core::Id id(Constants::TASK_CATEGORY_BUILDSYSTEM);
QList<Task> result;
FileName dbg = debuggerCommand(k);
if (dbg.isEmpty()) {
result << Task(Task::Warning, tr("No debugger set up."), FileName(), -1, id);
result.binary = Utils::FileName::fromString(abi.wordWidth() == 32 ? cdbs.first : cdbs.second);
result.engineType = CdbEngineType;
return result;
}
QFileInfo fi = dbg.toFileInfo();
// Check suggestions from the SDK.
const Environment env = Environment::systemEnvironment();
if (tc) {
QString path = tc->suggestedDebugger().toString();
if (!path.isEmpty()) {
const QFileInfo fi(path);
if (!fi.isAbsolute())
path = env.searchInPath(path);
result.binary = Utils::FileName::fromString(path);
result.engineType = engineTypeFromBinary(path);
return result;
}
}
// Default to GDB, system GDB
result.engineType = GdbEngineType;
QString gdb;
const QString systemGdb = QLatin1String("gdb");
// MinGW: Search for the python-enabled gdb first.
if (abi.os() == Abi::WindowsOS && abi.osFlavor() == Abi::WindowsMSysFlavor)
gdb = env.searchInPath(QLatin1String("gdb-i686-pc-mingw32"));
if (gdb.isEmpty())
gdb = env.searchInPath(systemGdb);
result.binary = Utils::FileName::fromString(env.searchInPath(gdb.isEmpty() ? systemGdb : gdb));
return result;
}
// Check the configuration errors and return a flag mask. Provide a quick check and
// a verbose one with a list of errors.
enum DebuggerConfigurationErrors {
NoDebugger = 0x1,
DebuggerNotFound = 0x2,
DebuggerNotExecutable = 0x4,
DebuggerNeedsAbsolutePath = 0x8
};
static unsigned debuggerConfigurationErrors(const ProjectExplorer::Kit *p)
{
unsigned result = 0;
const DebuggerKitInformation::DebuggerItem item = DebuggerKitInformation::debuggerItem(p);
if (item.engineType == NoEngineType || item.binary.isEmpty())
return NoDebugger;
const QFileInfo fi = item.binary.toFileInfo();
if (!fi.exists() || fi.isDir()) {
result |= DebuggerNotFound;
} else if (!fi.isExecutable()) {
result |= DebuggerNotExecutable;
}
if (!fi.exists() || fi.isDir())
result << Task(Task::Error, tr("Debugger not found."), FileName(), -1, id);
else if (!fi.isExecutable())
result << Task(Task::Error, tr("Debugger not exectutable."), FileName(), -1, id);
if (ToolChain *tc = ToolChainKitInformation::toolChain(k)) {
// We need an absolute path to be able to locate Python on Windows.
const Abi abi = tc->targetAbi();
if (abi.os() == Abi::WindowsOS && !fi.isAbsolute()) {
result << Task(Task::Error, tr("The debugger location must be given as an "
"absolute path (%1).").arg(dbg.toString()), FileName(), -1, id);
}
// FIXME: Make sure debugger matches toolchain.
// if (isCdb()) {
// if (abi.binaryFormat() != Abi::PEFormat || abi.os() != Abi::WindowsOS) {
// result << Task(Tas->errorDetails.push_back(CdbEngine::tr("The CDB debug engine does not support the %1 ABI.").
// arg(abi.toString()));
// return false;
// }
// }
if (item.engineType == GdbEngineType)
if (const ToolChain *tc = ToolChainKitInformation::toolChain(p))
if (tc->targetAbi().os() == Abi::WindowsOS && !fi.isAbsolute())
result |= DebuggerNeedsAbsolutePath;
return result;
}
bool DebuggerKitInformation::isValidDebugger(const ProjectExplorer::Kit *p)
{
return debuggerConfigurationErrors(p) == 0;
}
QList<ProjectExplorer::Task> DebuggerKitInformation::validateDebugger(const ProjectExplorer::Kit *p)
{
const unsigned errors = debuggerConfigurationErrors(p);
const Core::Id id(ProjectExplorer::Constants::TASK_CATEGORY_BUILDSYSTEM);
QList<Task> result;
if (errors & NoDebugger)
result << Task(Task::Warning, tr("No debugger set up."), FileName(), -1, id);
if (errors & DebuggerNotFound) {
const QString path = DebuggerKitInformation::debuggerCommand(p).toUserOutput();
result << Task(Task::Error, tr("Debugger '%1' not found.").arg(path),
FileName(), -1, id);
}
if (errors & DebuggerNotExecutable) {
const QString path = DebuggerKitInformation::debuggerCommand(p).toUserOutput();
result << Task(Task::Error, tr("Debugger '%1' not executable.").arg(path), FileName(), -1, id);
}
if (errors & DebuggerNeedsAbsolutePath) {
const QString path = DebuggerKitInformation::debuggerCommand(p).toUserOutput();
const QString message =
tr("The debugger location must be given as an "
"absolute path (%1).").arg(path);
result << Task(Task::Error, message, FileName(), -1, id);
}
return result;
}
@@ -207,20 +269,81 @@ KitConfigWidget *DebuggerKitInformation::createConfigWidget(Kit *k) const
return new Internal::DebuggerKitConfigWidget(k, this);
}
QString DebuggerKitInformation::userOutput(const ProjectExplorer::Kit *k)
{
const DebuggerItem item = DebuggerKitInformation::debuggerItem(k);
return tr("%1 using '%2'").arg(debuggerEngineName(item.engineType),
item.binary.toUserOutput());
}
KitInformation::ItemList DebuggerKitInformation::toUserOutput(Kit *k) const
{
return ItemList() << qMakePair(tr("Debugger"), debuggerCommand(k).toUserOutput());
return ItemList() << qMakePair(tr("Debugger"), DebuggerKitInformation::userOutput(k));
}
FileName DebuggerKitInformation::debuggerCommand(const Kit *k)
static const char engineTypeKeyC[] = "EngineType";
static const char binaryKeyC[] = "Binary";
DebuggerKitInformation::DebuggerItem DebuggerKitInformation::variantToItem(const QVariant &v)
{
return FileName::fromString(k ? k->value(Core::Id(DEBUGGER_INFORMATION)).toString() : QString());
DebuggerItem result;
if (v.type() == QVariant::String) { // Convert legacy config items, remove later.
const QString binary = v.toString();
result.binary = Utils::FileName::fromString(binary);
result.engineType = engineTypeFromBinary(binary);
return result;
}
QTC_ASSERT(v.type() == QVariant::Map, return result);
const QVariantMap vmap = v.toMap();
result.binary = Utils::FileName::fromString(vmap.value(QLatin1String(binaryKeyC)).toString());
result.engineType = static_cast<DebuggerEngineType>(vmap.value(QLatin1String(engineTypeKeyC)).toInt());
return result;
}
void DebuggerKitInformation::setDebuggerCommand(Kit *k, const FileName &command)
QVariant DebuggerKitInformation::itemToVariant(const DebuggerItem &i)
{
QTC_ASSERT(k, return);
k->setValue(Core::Id(DEBUGGER_INFORMATION), command.toString());
QVariantMap vmap;
vmap.insert(QLatin1String(binaryKeyC), QVariant(i.binary.toUserOutput()));
vmap.insert(QLatin1String(engineTypeKeyC), QVariant(int(i.engineType)));
return QVariant(vmap);
}
DebuggerKitInformation::DebuggerItem DebuggerKitInformation::debuggerItem(const ProjectExplorer::Kit *p)
{
return p ?
DebuggerKitInformation::variantToItem(p->value(Core::Id(DEBUGGER_INFORMATION))) :
DebuggerItem();
}
void DebuggerKitInformation::setDebuggerItem(ProjectExplorer::Kit *p, const DebuggerItem &item)
{
QTC_ASSERT(p, return);
p->setValue(Core::Id(DEBUGGER_INFORMATION), itemToVariant(item));
}
void DebuggerKitInformation::setDebuggerCommand(ProjectExplorer::Kit *k, const FileName &command)
{
setDebuggerItem(k, DebuggerItem(engineType(k), command));
}
void DebuggerKitInformation::setEngineType(ProjectExplorer::Kit *p, DebuggerEngineType type)
{
setDebuggerItem(p, DebuggerItem(type, debuggerCommand(p)));
}
QString DebuggerKitInformation::debuggerEngineName(DebuggerEngineType t)
{
switch (t) {
case Debugger::GdbEngineType:
return tr("GDB Engine");
case Debugger::CdbEngineType:
return tr("CDB Engine");
case Debugger::LldbEngineType:
return tr("LLDB Engine");
default:
break;
}
return QString();
}
} // namespace Debugger

View File

@@ -32,6 +32,7 @@
#define DEBUGGER_DEBUGGERKITINFORMATION_H
#include "debugger_global.h"
#include "debuggerconstants.h"
#include <projectexplorer/kitinformation.h>
@@ -42,22 +43,54 @@ class DEBUGGER_EXPORT DebuggerKitInformation : public ProjectExplorer::KitInform
Q_OBJECT
public:
class DEBUGGER_EXPORT DebuggerItem {
public:
DebuggerItem();
DebuggerItem(DebuggerEngineType engineType, const Utils::FileName &fn);
DebuggerEngineType engineType;
Utils::FileName binary;
};
DebuggerKitInformation();
Core::Id dataId() const;
unsigned int priority() const; // the higher the closer to the top.
QVariant defaultValue(ProjectExplorer::Kit *k) const;
static DebuggerItem autoDetectItem(const ProjectExplorer::Kit *k);
QVariant defaultValue(ProjectExplorer::Kit *k) const
{ return DebuggerKitInformation::itemToVariant(DebuggerKitInformation::autoDetectItem(k)); }
QList<ProjectExplorer::Task> validate(ProjectExplorer::Kit *k) const;
QList<ProjectExplorer::Task> validate(ProjectExplorer::Kit *k) const
{ return DebuggerKitInformation::validateDebugger(k); }
static QList<ProjectExplorer::Task> validateDebugger(const ProjectExplorer::Kit *p);
static bool isValidDebugger(const ProjectExplorer::Kit *p);
ProjectExplorer::KitConfigWidget *createConfigWidget(ProjectExplorer::Kit *k) const;
ItemList toUserOutput(ProjectExplorer::Kit *k) const;
static QString userOutput(const ProjectExplorer::Kit *k);
static Utils::FileName debuggerCommand(const ProjectExplorer::Kit *k);
static void setDebuggerCommand(ProjectExplorer::Kit *k, const Utils::FileName &command);
static DebuggerItem debuggerItem(const ProjectExplorer::Kit *p);
static void setDebuggerItem(ProjectExplorer::Kit *p, const DebuggerItem &item);
static Utils::FileName debuggerCommand(const ProjectExplorer::Kit *p)
{ return debuggerItem(p).binary; }
static void setDebuggerCommand(ProjectExplorer::Kit *p, const Utils::FileName &command);
static DebuggerEngineType engineType(const ProjectExplorer::Kit *p)
{ return debuggerItem(p).engineType; }
static void setEngineType(ProjectExplorer::Kit *p, DebuggerEngineType type);
static QString debuggerEngineName(DebuggerEngineType t);
private:
static DebuggerItem variantToItem(const QVariant &v);
static QVariant itemToVariant(const DebuggerItem &i);
};
} // namespace Debugger

View File

@@ -568,8 +568,10 @@ public:
explicit AbiKitMatcher(const QList<Abi> &abis) : m_abis(abis) {}
bool matches(const Kit *p) const
{
if (const ToolChain *tc = ToolChainKitInformation::toolChain(p))
return m_abis.contains(tc->targetAbi());
if (const ToolChain *tc = ToolChainKitInformation::toolChain(p)) {
return m_abis.contains(tc->targetAbi())
&& DebuggerKitInformation::isValidDebugger(p);
}
return false;
}
@@ -585,7 +587,7 @@ public:
{
if (const ToolChain *tc = ToolChainKitInformation::toolChain(p))
foreach (const Abi &a, m_abis)
if (a.isCompatibleWith(tc->targetAbi()))
if (a.isCompatibleWith(tc->targetAbi()) && DebuggerKitInformation::isValidDebugger(p))
return true;
return false;
}
@@ -601,18 +603,14 @@ public:
bool matches(const Kit *k) const
{
if (DebuggerKitInformation::engineType(k) != CdbEngineType
|| !DebuggerKitInformation::isValidDebugger(k)) {
return false;
}
if (m_wordWidth) {
const ToolChain *tc = ToolChainKitInformation::toolChain(k);
QTC_ASSERT(tc, return false);
const Abi abi = tc->targetAbi();
if (abi.architecture() != Abi::X86Architecture
|| abi.os() != Abi::WindowsOS
|| abi.binaryFormat() != Abi::PEFormat)
return false;
if (abi.osFlavor() == Abi::WindowsMSysFlavor
|| abi.osFlavor() == Abi::WindowsCEFlavor)
return false;
if (m_wordWidth && abi.wordWidth() != m_wordWidth)
return false;
return tc && m_wordWidth == tc->targetAbi().wordWidth();
}
return true;
}
@@ -635,7 +633,7 @@ private:
const char m_wordWidth;
};
void fillParameters(DebuggerStartParameters *sp, const Kit *kit /* = 0 */)
bool fillParameters(DebuggerStartParameters *sp, const Kit *kit /* = 0 */, QString *errorMessage /* = 0 */)
{
if (!kit) {
// This code can only be reached when starting via the command line
@@ -665,6 +663,27 @@ void fillParameters(DebuggerStartParameters *sp, const Kit *kit /* = 0 */)
kit = KitManager::instance()->defaultKit();
}
// Verify that debugger and profile are valid
if (!kit) {
sp->startMode = NoStartMode;
if (errorMessage)
*errorMessage = DebuggerKitInformation::tr("No kit found.");
return false;
}
const QList<ProjectExplorer::Task> tasks = DebuggerKitInformation::validateDebugger(kit);
if (!tasks.isEmpty()) {
sp->startMode = NoStartMode;
if (errorMessage) {
foreach (const ProjectExplorer::Task &t, tasks) {
if (errorMessage->isEmpty())
errorMessage->append(QLatin1Char('\n'));
errorMessage->append(t.description);
}
}
return false;
}
sp->cppEngineType = DebuggerKitInformation::engineType(kit);
sp->sysRoot = SysRootKitInformation::sysRoot(kit).toString();
sp->debuggerCommand = DebuggerKitInformation::debuggerCommand(kit).toString();
@@ -677,6 +696,7 @@ void fillParameters(DebuggerStartParameters *sp, const Kit *kit /* = 0 */)
sp->connParams = device->sshParameters();
sp->remoteChannel = sp->connParams.host + QLatin1Char(':') + QString::number(sp->connParams.port);
}
return true;
}
static TextEditor::ITextEditor *currentTextEditor()
@@ -1439,7 +1459,8 @@ bool DebuggerPluginPrivate::parseArgument(QStringList::const_iterator &it,
}
}
}
fillParameters(&sp, kit);
if (fillParameters(&sp, kit, errorMessage))
return false;
if (sp.startMode == StartExternal) {
sp.displayName = tr("Executable file \"%1\"").arg(sp.executable);
sp.startMessage = tr("Debugging file %1.").arg(sp.executable);
@@ -1459,7 +1480,8 @@ bool DebuggerPluginPrivate::parseArgument(QStringList::const_iterator &it,
return false;
}
DebuggerStartParameters sp;
fillParameters(&sp, CdbMatcher::findUniversalCdbKit());
if (!fillParameters(&sp, CdbMatcher::findUniversalCdbKit(), errorMessage))
return false;
sp.startMode = AttachCrashedExternal;
sp.crashParameter = it->section(QLatin1Char(':'), 0, 0);
sp.attachPID = it->section(QLatin1Char(':'), 1, 1).toULongLong();
@@ -1597,7 +1619,7 @@ void DebuggerPluginPrivate::attachCore()
DebuggerStartParameters sp;
QString display = dlg.isLocal() ? dlg.localCoreFile() : dlg.remoteCoreFile();
fillParameters(&sp, dlg.kit());
QTC_ASSERT(fillParameters(&sp, dlg.kit()), return);
sp.masterEngineType = GdbEngineType;
sp.executable = dlg.localExecutableFile();
sp.coreFile = dlg.localCoreFile();
@@ -1613,8 +1635,7 @@ void DebuggerPluginPrivate::startRemoteCdbSession()
const QString connectionKey = _("CdbRemoteConnection");
DebuggerStartParameters sp;
Kit *kit = CdbMatcher::findUniversalCdbKit();
QTC_ASSERT(kit, return);
fillParameters(&sp, kit);
QTC_ASSERT(kit && fillParameters(&sp, kit), return);
sp.startMode = AttachToRemoteServer;
sp.closeMode = KillAtClose;
StartRemoteCdbDialog dlg(mainWindow());
@@ -1652,7 +1673,10 @@ void DebuggerPluginPrivate::attachToRunningApplication()
void DebuggerPluginPrivate::attachToProcess(bool startServerOnly)
{
DeviceProcessesDialog *dlg = new DeviceProcessesDialog(mainWindow());
const DebuggerKitChooser::Mode mode = startServerOnly ?
DebuggerKitChooser::RemoteDebugging : DebuggerKitChooser::LocalDebugging;
DebuggerKitChooser *kitChooser = new DebuggerKitChooser(mode);
DeviceProcessesDialog *dlg = new DeviceProcessesDialog(kitChooser, mainWindow());
dlg->addAcceptButton(DeviceProcessesDialog::tr("&Attach to Process"));
dlg->showAllDevices();
if (dlg->exec() == QDialog::Rejected) {
@@ -1661,7 +1685,6 @@ void DebuggerPluginPrivate::attachToProcess(bool startServerOnly)
}
dlg->setAttribute(Qt::WA_DeleteOnClose);
KitChooser *kitChooser = dlg->kitChooser();
Kit *kit = kitChooser->currentKit();
QTC_ASSERT(kit, return);
IDevice::ConstPtr device = DeviceKitInformation::device(kit);
@@ -1684,7 +1707,7 @@ void DebuggerPluginPrivate::attachToProcess(bool startServerOnly)
if (device->type() == ProjectExplorer::Constants::DESKTOP_DEVICE_TYPE) {
DebuggerStartParameters sp;
fillParameters(&sp, kit);
QTC_ASSERT(fillParameters(&sp, kit), return);
sp.attachPID = process.pid;
sp.displayName = tr("Process %1").arg(process.pid);
sp.executable = process.exe;
@@ -1709,7 +1732,7 @@ void DebuggerPluginPrivate::attachExternalApplication(ProjectExplorer::RunContro
if (const RunConfiguration *runConfiguration = rc->runConfiguration())
if (const Target *target = runConfiguration->target())
kit = target->kit();
fillParameters(&sp, kit);
QTC_ASSERT(fillParameters(&sp, kit), return);
DebuggerRunControlFactory::createAndScheduleRun(sp);
}
@@ -1732,11 +1755,10 @@ void DebuggerPluginPrivate::attachToQmlPort()
return;
Kit *kit = dlg.kit();
QTC_ASSERT(kit, return);
QTC_ASSERT(kit && fillParameters(&sp, kit), return);
setConfigValue(_("LastQmlServerPort"), dlg.port());
setConfigValue(_("LastProfile"), kit->id().toString());
fillParameters(&sp, kit);
sp.qmlServerAddress = sp.connParams.host;
sp.qmlServerPort = dlg.port();
sp.startMode = AttachToRemoteProcess;
@@ -3388,9 +3410,9 @@ void DebuggerPlugin::remoteCommand(const QStringList &options,
}
DebuggerRunControl *DebuggerPlugin::createDebugger
(const DebuggerStartParameters &sp, RunConfiguration *rc)
(const DebuggerStartParameters &sp, RunConfiguration *rc, QString *errorMessage)
{
return DebuggerRunControlFactory::doCreate(sp, rc);
return DebuggerRunControlFactory::doCreate(sp, rc, errorMessage);
}
void DebuggerPlugin::extensionsInitialized()

View File

@@ -66,7 +66,8 @@ public:
static QAction *visibleDebugAction();
static DebuggerRunControl *createDebugger(const DebuggerStartParameters &sp,
ProjectExplorer::RunConfiguration *rc);
ProjectExplorer::RunConfiguration *rc,
QString *errorMessage);
private:
// IPlugin implementation.

View File

@@ -50,7 +50,8 @@ public:
// FIXME: Used by qmljsinspector.cpp:469
ProjectExplorer::RunControl *create(
ProjectExplorer::RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode);
ProjectExplorer::RunMode mode,
QString *errorMessage);
bool canRun(ProjectExplorer::RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode) const;
@@ -64,7 +65,7 @@ public:
ProjectExplorer::RunConfiguration *runConfiguration = 0);
static DebuggerRunControl *doCreate(const DebuggerStartParameters &sp,
ProjectExplorer::RunConfiguration *rc);
ProjectExplorer::RunConfiguration *rc, QString *errorMessage);
private:
QString displayName() const;

View File

@@ -259,11 +259,6 @@ public:
explicit DebuggerRunControlPrivate(DebuggerRunControl *parent,
RunConfiguration *runConfiguration);
DebuggerEngineType engineForExecutable(unsigned enabledEngineTypes,
const QString &executable);
DebuggerEngineType engineForMode(unsigned enabledEngineTypes,
DebuggerStartMode mode);
public:
DebuggerRunControl *q;
DebuggerEngine *m_engine;
@@ -476,7 +471,7 @@ QString DebuggerRunControlFactory::displayName() const
return DebuggerPlugin::tr("Debug");
}
static DebuggerStartParameters localStartParameters(RunConfiguration *runConfiguration)
static DebuggerStartParameters localStartParameters(RunConfiguration *runConfiguration, QString *errorMessage)
{
DebuggerStartParameters sp;
QTC_ASSERT(runConfiguration, return sp);
@@ -486,7 +481,8 @@ static DebuggerStartParameters localStartParameters(RunConfiguration *runConfigu
Target *target = runConfiguration->target();
Kit *kit = target ? target->kit() : KitManager::instance()->defaultKit();
fillParameters(&sp, kit);
if (!fillParameters(&sp, kit, errorMessage))
return sp;
sp.environment = rc->environment();
sp.workingDirectory = rc->workingDirectory();
@@ -543,109 +539,62 @@ static DebuggerStartParameters localStartParameters(RunConfiguration *runConfigu
}
RunControl *DebuggerRunControlFactory::create
(RunConfiguration *runConfiguration, RunMode mode)
(RunConfiguration *runConfiguration, RunMode mode, QString *errorMessage)
{
Q_UNUSED(errorMessage)
QTC_ASSERT(mode == DebugRunMode || mode == DebugRunModeWithBreakOnMain, return 0);
DebuggerStartParameters sp = localStartParameters(runConfiguration);
DebuggerStartParameters sp = localStartParameters(runConfiguration, errorMessage);
if (sp.startMode == NoStartMode)
return 0;
if (mode == DebugRunModeWithBreakOnMain)
sp.breakOnMain = true;
return doCreate(sp, runConfiguration);
return doCreate(sp, runConfiguration, errorMessage);
}
static DebuggerEngineType guessUnixCppEngineType(const DebuggerStartParameters &sp)
{
if (sp.debuggerCommand.contains(QLatin1String("lldb")))
return LldbEngineType;
return GdbEngineType;
}
static DebuggerEngineType guessCppEngineTypeForAbi(const DebuggerStartParameters &sp, const Abi &abi)
{
switch (abi.binaryFormat()) {
case Abi::ElfFormat:
case Abi::MachOFormat:
return guessUnixCppEngineType(sp) ;
case Abi::PEFormat:
if (abi.osFlavor() == Abi::WindowsMSysFlavor)
return guessUnixCppEngineType(sp);
return CdbEngineType;
default:
break;
}
return NoEngineType;
}
static DebuggerEngineType guessCppEngineType(const DebuggerStartParameters &sp)
{
if (sp.toolChainAbi.isValid()) {
const DebuggerEngineType et = guessCppEngineTypeForAbi(sp, sp.toolChainAbi);
if (et != NoEngineType)
return et;
}
#ifdef Q_OS_WIN
// If a file has PDB files, it has been compiled by VS.
if (sp.executable.endsWith(_(".exe"), Qt::CaseInsensitive)) {
QStringList pdbFiles;
QString errorMessage;
if (getPDBFiles(sp.executable, &pdbFiles, &errorMessage) && !pdbFiles.isEmpty())
return CdbEngineType;
}
#endif
QList<Abi> abis = Abi::abisOfBinary(FileName::fromString(sp.executable));
foreach (const Abi &abi, abis) {
DebuggerEngineType et = guessCppEngineTypeForAbi(sp, abi);
if (et != NoEngineType)
return et;
}
return guessUnixCppEngineType(sp);
}
static void fixupEngineTypes(DebuggerStartParameters &sp, RunConfiguration *rc)
static bool fixupEngineTypes(DebuggerStartParameters &sp, RunConfiguration *rc, QString *errorMessage)
{
if (sp.masterEngineType != NoEngineType)
return;
return true;
if (sp.executable.endsWith(_(".js"))) {
sp.masterEngineType = ScriptEngineType;
return;
return true;
}
if (sp.executable.endsWith(_(".py"))) {
sp.masterEngineType = PdbEngineType;
return;
return true;
}
if (rc) {
DebuggerRunConfigurationAspect *aspect = rc->debuggerAspect();
if (const Target *target = rc->target())
fillParameters(&sp, target->kit());
if (!fillParameters(&sp, target->kit(), errorMessage))
return false;
const bool useCppDebugger = aspect->useCppDebugger();
const bool useQmlDebugger = aspect->useQmlDebugger();
if (useQmlDebugger) {
if (useCppDebugger) {
sp.masterEngineType = QmlCppEngineType;
sp.firstSlaveEngineType = guessCppEngineType(sp);
sp.firstSlaveEngineType = sp.cppEngineType;
sp.secondSlaveEngineType = QmlCppEngineType;
} else {
sp.masterEngineType = QmlEngineType;
}
} else {
sp.masterEngineType = guessCppEngineType(sp);
sp.masterEngineType = sp.cppEngineType;
}
return;
return true;
}
sp.masterEngineType = guessCppEngineType(sp);
sp.masterEngineType = sp.cppEngineType;
return true;
}
DebuggerRunControl *DebuggerRunControlFactory::doCreate
(const DebuggerStartParameters &sp0, RunConfiguration *rc)
(const DebuggerStartParameters &sp0, RunConfiguration *rc, QString *errorMessage)
{
Q_UNUSED(errorMessage);
DebuggerStartParameters sp = sp0;
if (!debuggerCore()->boolSetting(AutoEnrichParameters)) {
const QString sysroot = sp.sysRoot;
@@ -662,8 +611,7 @@ DebuggerRunControl *DebuggerRunControlFactory::doCreate
}
}
fixupEngineTypes(sp, rc);
if (!sp.masterEngineType)
if (!fixupEngineTypes(sp, rc, errorMessage))
return 0;
return new DebuggerRunControl(rc, sp);
@@ -672,9 +620,12 @@ DebuggerRunControl *DebuggerRunControlFactory::doCreate
DebuggerRunControl *DebuggerRunControlFactory::createAndScheduleRun
(const DebuggerStartParameters &sp, RunConfiguration *runConfiguration)
{
DebuggerRunControl *rc = doCreate(sp, runConfiguration);
if (!rc)
QString errorMessage;
DebuggerRunControl *rc = doCreate(sp, runConfiguration, &errorMessage);
if (!rc) {
ProjectExplorer::ProjectExplorerPlugin::showRunErrorMessage(errorMessage);
return 0;
}
debuggerCore()->showMessage(sp.startMessage, 0);
ProjectExplorerPlugin::instance()->startRunControl(rc, DebugRunMode);
return rc;

View File

@@ -60,6 +60,7 @@ public:
: masterEngineType(NoEngineType),
firstSlaveEngineType(NoEngineType),
secondSlaveEngineType(NoEngineType),
cppEngineType(NoEngineType),
isSnapshot(false),
attachPID(-1),
useTerminal(false),
@@ -81,6 +82,7 @@ public:
DebuggerEngineType masterEngineType;
DebuggerEngineType firstSlaveEngineType;
DebuggerEngineType secondSlaveEngineType;
DebuggerEngineType cppEngineType;
QString sysRoot;
QString debuggerCommand;
ProjectExplorer::Abi toolChainAbi;
@@ -140,7 +142,7 @@ public:
namespace Internal {
void fillParameters(DebuggerStartParameters *sp, const ProjectExplorer::Kit *kit = 0);
bool fillParameters(DebuggerStartParameters *sp, const ProjectExplorer::Kit *kit = 0, QString *errorMessage = 0);
} // namespace Internal
} // namespace Debugger

View File

@@ -5004,12 +5004,15 @@ void GdbEngine::handleNamespaceExtraction(const GdbResponse &response)
QByteArray ba = file.readAll();
file.close();
file.remove();
int pos = ba.indexOf("7QString9fromAscii");
QByteArray ns;
int pos = ba.indexOf("7QString16fromAscii_helper");
if (pos > -1) {
int pos1 = pos - 1;
while (pos1 > 0 && ba.at(pos1) != 'N' && ba.at(pos1) > '@')
--pos1;
++pos1;
const QByteArray ns = ba.mid(pos1, pos - pos1);
ns = ba.mid(pos1, pos - pos1);
}
if (ns.isEmpty()) {
showMessage(_("FOUND NON-NAMESPACED QT"));
} else {

View File

@@ -196,7 +196,7 @@ GdbOptionsPageWidget::GdbOptionsPageWidget(QWidget *parent)
checkBoxEnableReverseDebugging = new QCheckBox(groupBoxGeneral);
checkBoxEnableReverseDebugging->setText(GdbOptionsPage::tr("Enable reverse debugging"));
checkBoxEnableReverseDebugging->setToolTip(GdbOptionsPage::tr(
"<html><head/><body><p>Enable stepping backwards.</p><.p>"
"<html><head/><body><p>Enable stepping backwards.</p><p>"
"<b>Note:</b> This feature is very slow and unstable on the GDB side. "
"It exhibits unpredictable behavior when going backwards over system "
"calls and is very likely to destroy your debugging session.</p></body></html>"));

View File

@@ -344,8 +344,9 @@ void GdbRemoteServerEngine::runEngine()
const QString remoteExecutable = startParameters().remoteExecutable;
if (!remoteExecutable.isEmpty()) {
// Cannot use -exec-run for QNX gdb as it does not support path parameter for the MI call
const QByteArray command = m_isQnxGdb ? "run" : "-exec-run";
// Cannot use -exec-run for QNX gdb 7.4 as it does not support path parameter for the MI call
const bool useRun = m_isQnxGdb && m_gdbVersion > 70300;
const QByteArray command = useRun ? "run" : "-exec-run";
postCommand(command + " " + remoteExecutable.toLocal8Bit(), GdbEngine::RunRequest, CB(handleExecRun));
} else {
notifyEngineRunAndInferiorStopOk();

View File

@@ -207,7 +207,7 @@ void GdbServerStarter::attach(int port)
}
DebuggerStartParameters sp;
fillParameters(&sp, d->kit);
QTC_ASSERT(fillParameters(&sp, d->kit), return);
sp.masterEngineType = GdbEngineType;
sp.connParams.port = port;
sp.displayName = tr("Remote: \"%1:%2\"").arg(sp.connParams.host).arg(port);

View File

@@ -140,6 +140,7 @@ LldbEngineHost::LldbEngineHost(const DebuggerStartParameters &startParameters)
:IPCEngineHost(startParameters), m_ssh(0)
{
showMessage(QLatin1String("setting up coms"));
setObjectName(QLatin1String("LLDBEngine"));
if (startParameters.startMode == StartRemoteEngine)
{

View File

@@ -33,6 +33,7 @@
#include "debuggerconstants.h"
#include "debuggercore.h"
#include "debuggerstartparameters.h"
#include "debuggerdialogs.h"
#include <coreplugin/icore.h>
#include <projectexplorer/abi.h>
@@ -245,7 +246,8 @@ AttachCoreDialog::AttachCoreDialog(QWidget *parent)
d->settings = ICore::settings();
d->kitChooser = new KitChooser(this);
d->kitChooser = new DebuggerKitChooser(DebuggerKitChooser::RemoteDebugging, this);
d->kitChooser->populate();
d->selectRemoteCoreButton = new QPushButton(tr("Browse..."), this);
d->remoteCoreFileName = new QLineEdit(this);

View File

@@ -185,7 +185,7 @@ bool CdbSymbolPathListEditor::promptToAddSymbolServer(const QString &settingsGro
"for retrieval of the symbols of the operating system libraries.</p>"
"<p><i>Note:</i> A fast internet connection is required for this to work smoothly. Also, a delay "
"might occur when connecting for the first time.</p>"
"<p>Would you like to set it up?</p></br>"
"<p>Would you like to set it up?</p>"
"</body></html>").arg(symServUrl);
const QDialogButtonBox::StandardButton answer =
Utils::CheckableMessageBox::question(Core::ICore::mainWindow(), tr("Symbol Server"), msg,

View File

@@ -1351,8 +1351,11 @@ bool WatchModel::ancestorChanged(const QSet<QByteArray> &inames, WatchItem *item
void WatchModel::insertBulkData(const QList<WatchData> &list)
{
#if 1
for (int i = 0, n = list.size(); i != n; ++i)
insertDataItem(list.at(i));
for (int i = 0, n = list.size(); i != n; ++i) {
const WatchData &data = list.at(i);
insertDataItem(data);
m_handler->showEditValue(data);
}
#else
// Destroy unneeded items.
QSet<QByteArray> inames;

View File

@@ -725,15 +725,27 @@ void decodeArray(QList<WatchData> *list, const WatchData &tmplate,
{
switch (encoding) {
case Hex2EncodedInt1:
decodeArrayHelper<uchar>(list, tmplate, rawData);
decodeArrayHelper<signed char>(list, tmplate, rawData);
break;
case Hex2EncodedInt2:
decodeArrayHelper<ushort>(list, tmplate, rawData);
decodeArrayHelper<short>(list, tmplate, rawData);
break;
case Hex2EncodedInt4:
decodeArrayHelper<uint>(list, tmplate, rawData);
decodeArrayHelper<int>(list, tmplate, rawData);
break;
case Hex2EncodedInt8:
decodeArrayHelper<qint64>(list, tmplate, rawData);
break;
case Hex2EncodedUInt1:
decodeArrayHelper<uchar>(list, tmplate, rawData);
break;
case Hex2EncodedUInt2:
decodeArrayHelper<ushort>(list, tmplate, rawData);
break;
case Hex2EncodedUInt4:
decodeArrayHelper<uint>(list, tmplate, rawData);
break;
case Hex2EncodedUInt8:
decodeArrayHelper<quint64>(list, tmplate, rawData);
break;
case Hex2EncodedFloat4:

View File

@@ -75,8 +75,12 @@ enum DebuggerEncoding
Hex2EncodedInt2 = 18,
Hex2EncodedInt4 = 19,
Hex2EncodedInt8 = 20,
Hex2EncodedFloat4 = 21,
Hex2EncodedFloat8 = 22
Hex2EncodedUInt1 = 21,
Hex2EncodedUInt2 = 22,
Hex2EncodedUInt4 = 23,
Hex2EncodedUInt8 = 24,
Hex2EncodedFloat4 = 25,
Hex2EncodedFloat8 = 26
};
bool isEditorDebuggable(Core::IEditor *editor);

View File

@@ -105,6 +105,8 @@ bool FindToolWindow::eventFilter(QObject *obj, QEvent *event)
if (obj == m_ui.searchTerm && event->type() == QEvent::KeyPress) {
QKeyEvent *ke = static_cast<QKeyEvent *>(event);
if (ke->key() == Qt::Key_Down) {
if (m_ui.searchTerm->text().isEmpty())
m_findCompleter->setCompletionPrefix(QString());
m_findCompleter->complete();
}
}

View File

@@ -106,6 +106,15 @@ bool GenericMakeStep::init()
if (!bc)
bc = static_cast<GenericBuildConfiguration *>(target()->activeBuildConfiguration());
m_tasks.clear();
ToolChain *tc = ToolChainKitInformation::toolChain(target()->kit());
if (!tc) {
m_tasks.append(Task(Task::Error, tr("Qt Creator needs a compiler set up to build. Configure a compiler in the kit options."),
Utils::FileName(), -1,
Core::Id(ProjectExplorer::Constants::TASK_CATEGORY_BUILDSYSTEM)));
return true; // otherwise the tasks will not get reported
}
ProcessParameters *pp = processParameters();
pp->setMacroExpander(bc->macroExpander());
pp->setWorkingDirectory(bc->buildDirectory());
@@ -119,7 +128,6 @@ bool GenericMakeStep::init()
setIgnoreReturnValue(m_clean);
setOutputParser(new GnuMakeParser());
ToolChain *tc = ToolChainKitInformation::toolChain(target()->kit());
if (tc)
appendOutputParser(tc->outputParser());
outputParser()->setWorkingDirectory(pp->effectiveWorkingDirectory());
@@ -180,6 +188,17 @@ QString GenericMakeStep::makeCommand() const
void GenericMakeStep::run(QFutureInterface<bool> &fi)
{
bool canContinue = true;
foreach (const Task &t, m_tasks) {
addTask(t);
canContinue = false;
}
if (!canContinue) {
emit addOutput(tr("Configuration is faulty. Check the Issues view for details."), BuildStep::MessageOutput);
fi.reportResult(false);
return;
}
AbstractProcessStep::run(fi);
}

View File

@@ -85,6 +85,7 @@ private:
QString m_makeArguments;
QString m_makeCommand;
bool m_clean;
QList<ProjectExplorer::Task> m_tasks;
};
class GenericMakeStepConfigWidget : public ProjectExplorer::BuildStepConfigWidget

View File

@@ -203,7 +203,7 @@ bool MaemoRunControlFactory::canRun(RunConfiguration *runConfiguration, RunMode
return maemoRunConfig->hasEnoughFreePorts(mode);
}
RunControl* MaemoRunControlFactory::create(RunConfiguration *runConfig, RunMode mode)
RunControl* MaemoRunControlFactory::create(RunConfiguration *runConfig, RunMode mode, QString *errorMessage)
{
Q_ASSERT(canRun(runConfig, mode));
@@ -217,7 +217,7 @@ RunControl* MaemoRunControlFactory::create(RunConfiguration *runConfig, RunMode
}
const DebuggerStartParameters params = LinuxDeviceDebugSupport::startParameters(rc);
DebuggerRunControl * const runControl = DebuggerPlugin::createDebugger(params, rc);
DebuggerRunControl * const runControl = DebuggerPlugin::createDebugger(params, rc, errorMessage);
if (!runControl)
return 0;
LinuxDeviceDebugSupport * const debugSupport

View File

@@ -82,7 +82,9 @@ public:
QString displayName() const;
bool canRun(ProjectExplorer::RunConfiguration *runConfiguration, ProjectExplorer::RunMode mode) const;
RunControl *create(ProjectExplorer::RunConfiguration *runConfiguration, ProjectExplorer::RunMode mode);
RunControl *create(ProjectExplorer::RunConfiguration *runConfiguration,
ProjectExplorer::RunMode mode,
QString *errorMessage);
};
} // namespace Internal

View File

@@ -37,6 +37,8 @@
#include <QRegExp>
#include <QDebug>
#include <QDir>
#include <QDate>
#include <QTime>
#include <QWizardPage>
#include <QFormLayout>
@@ -462,6 +464,13 @@ QMap<QString, QString> CustomWizardFieldPage::replacementMap(const QWizard *w,
// Insert paths for generator scripts.
fieldReplacementMap.insert(QLatin1String("Path"), QDir::toNativeSeparators(ctx->path));
fieldReplacementMap.insert(QLatin1String("TargetPath"), QDir::toNativeSeparators(ctx->targetPath));
// Insert additional pre-defined variables
fieldReplacementMap.insert(QLatin1String("CurrentDate"),
QDate::currentDate().toString(QLatin1String("yyyy-MM-dd")));
fieldReplacementMap.insert(QLatin1String("CurrentTime"),
QTime::currentTime().toString(QLocale::system().
timeFormat(QLocale::ShortFormat)));
return fieldReplacementMap;
}

View File

@@ -96,7 +96,7 @@ class DeviceProcessesDialogPrivate : public QObject
Q_OBJECT
public:
DeviceProcessesDialogPrivate(QWidget *parent);
DeviceProcessesDialogPrivate(KitChooser *chooser, QWidget *parent);
public slots:
void setDevice(const IDevice::ConstPtr &device);
@@ -113,6 +113,7 @@ public:
QWidget *q;
DeviceProcessList *processList;
ProcessListFilterModel proxyModel;
QLabel *kitLabel;
KitChooser *kitChooser;
QTreeView *procView;
@@ -124,16 +125,24 @@ public:
QDialogButtonBox *buttonBox;
};
DeviceProcessesDialogPrivate::DeviceProcessesDialogPrivate(QWidget *parent)
: q(parent), acceptButton(0), buttonBox(new QDialogButtonBox(parent))
DeviceProcessesDialogPrivate::DeviceProcessesDialogPrivate(KitChooser *chooser, QWidget *parent)
: q(parent)
, kitLabel(new QLabel(DeviceProcessesDialog::tr("Kit:"), parent))
, kitChooser(chooser)
, acceptButton(0)
, buttonBox(new QDialogButtonBox(parent))
{
q->setWindowTitle(DeviceProcessesDialog::tr("List of Processes"));
q->setWindowFlags(q->windowFlags() & ~Qt::WindowContextHelpButtonHint);
q->setMinimumHeight(500);
processList = 0;
processFilterLineEdit = new FilterLineEdit(q);
processFilterLineEdit->setPlaceholderText(DeviceProcessesDialog::tr("Filter"));
processFilterLineEdit->setFocus(Qt::TabFocusReason);
kitChooser = new KitChooser(q);
kitChooser->populate();
procView = new QTreeView(q);
procView->setModel(&proxyModel);
@@ -157,7 +166,7 @@ DeviceProcessesDialogPrivate::DeviceProcessesDialogPrivate(QWidget *parent)
QFormLayout *leftColumn = new QFormLayout();
leftColumn->setFieldGrowthPolicy(QFormLayout::ExpandingFieldsGrow);
leftColumn->addRow(DeviceProcessesDialog::tr("Kit:"), kitChooser);
leftColumn->addRow(kitLabel, kitChooser);
leftColumn->addRow(DeviceProcessesDialog::tr("&Filter:"), processFilterLineEdit);
// QVBoxLayout *rightColumn = new QVBoxLayout();
@@ -295,11 +304,13 @@ DeviceProcess DeviceProcessesDialogPrivate::selectedProcess() const
*/
DeviceProcessesDialog::DeviceProcessesDialog(QWidget *parent)
: QDialog(parent), d(new Internal::DeviceProcessesDialogPrivate(this))
: QDialog(parent), d(new Internal::DeviceProcessesDialogPrivate(new KitChooser(this), this))
{
}
DeviceProcessesDialog::DeviceProcessesDialog(KitChooser *chooser, QWidget *parent)
: QDialog(parent), d(new Internal::DeviceProcessesDialogPrivate(chooser, this))
{
setWindowTitle(tr("List of Processes"));
setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint);
setMinimumHeight(500);
}
DeviceProcessesDialog::~DeviceProcessesDialog()
@@ -321,15 +332,21 @@ void DeviceProcessesDialog::addCloseButton()
d->buttonBox->addButton(QDialogButtonBox::Close);
}
void DeviceProcessesDialog::setKitVisible(bool v)
{
d->kitLabel->setVisible(v);
d->kitChooser->setVisible(v);
}
void DeviceProcessesDialog::setDevice(const IDevice::ConstPtr &device)
{
d->kitChooser->hide();
setKitVisible(false);
d->setDevice(device);
}
void DeviceProcessesDialog::showAllDevices()
{
d->kitChooser->show();
setKitVisible(true);
d->updateDevice();
}

View File

@@ -59,8 +59,11 @@ public:
DeviceProcess currentProcess() const;
KitChooser *kitChooser() const;
void logMessage(const QString &line);
DeviceProcessesDialog(KitChooser *chooser, QWidget *parent);
private:
void setKitVisible(bool);
Internal::DeviceProcessesDialogPrivate * const d;
};

View File

@@ -150,6 +150,8 @@ void Kit::setDisplayName(const QString &name)
QStringList nameList;
foreach (Kit *p, pm->kits()) {
if (p == this)
continue;
nameList << p->displayName();
foreach (KitInformation *ki, kitInfo) {
const QString postfix = ki->displayNamePostfix(p);

View File

@@ -38,42 +38,43 @@
namespace ProjectExplorer {
KitChooser::KitChooser(QWidget *parent, unsigned flags) :
KitChooser::KitChooser(QWidget *parent) :
QComboBox(parent)
{
populate(flags);
onCurrentIndexChanged(currentIndex());
connect(this, SIGNAL(currentIndexChanged(int)), SLOT(onCurrentIndexChanged(int)));
}
void KitChooser::onCurrentIndexChanged(int index)
{
if (Kit *kit = kitAt(index))
setToolTip(kit->toHtml());
setToolTip(kitToolTip(kit));
else
setToolTip(QString());
}
void KitChooser::populate(unsigned flags)
bool KitChooser::kitMatches(const Kit *k) const
{
return k->isValid();
}
QString KitChooser::kitText(const Kit *k) const
{
return k->displayName();
}
QString KitChooser::kitToolTip(Kit *k) const
{
return k->toHtml();
}
void KitChooser::populate()
{
clear();
const Abi hostAbi = Abi::hostAbi();
foreach (Kit *kit, KitManager::instance()->kits()) {
if (!kit->isValid() && !(flags & IncludeInvalidKits))
continue;
ToolChain *tc = ToolChainKitInformation::toolChain(kit);
if (!tc)
continue;
const Abi abi = tc->targetAbi();
if ((flags & HostAbiOnly) && hostAbi.os() != abi.os())
continue;
const QString debuggerCommand = kit->value(Core::Id("Debugger.Information")).toString();
if ((flags & HasDebugger) && debuggerCommand.isEmpty())
continue;
const QString completeBase = QFileInfo(debuggerCommand).completeBaseName();
const QString name = tr("%1 (%2)").arg(kit->displayName(), completeBase);
addItem(name, qVariantFromValue(kit->id()));
setItemData(count() - 1, kit->toHtml(), Qt::ToolTipRole);
if (kitMatches(kit)) {
addItem(kitText(kit), qVariantFromValue(kit->id()));
setItemData(count() - 1, kitToolTip(kit), Qt::ToolTipRole);
}
}
setEnabled(count() > 1);
}

View File

@@ -47,24 +47,25 @@ class PROJECTEXPLORER_EXPORT KitChooser : public QComboBox
Q_OBJECT
public:
enum Flags {
HostAbiOnly = 0x1,
IncludeInvalidKits = 0x2,
HasDebugger = 0x4,
RemoteDebugging = IncludeInvalidKits | HasDebugger,
LocalDebugging = RemoteDebugging | HostAbiOnly
};
explicit KitChooser(QWidget *parent, unsigned flags = 0);
explicit KitChooser(QWidget *parent = 0);
void setCurrentKitId(Core::Id id);
Core::Id currentKitId() const;
Kit *currentKit() const;
public slots:
void populate();
private slots:
void onCurrentIndexChanged(int index);
protected:
virtual bool kitMatches(const Kit *k) const;
virtual QString kitText(const Kit *k) const;
virtual QString kitToolTip(Kit *k) const;
private:
Q_SLOT void onCurrentIndexChanged(int index);
void populate(unsigned flags);
Kit *kitAt(int index) const;
};

View File

@@ -35,6 +35,8 @@
#include <QWidget>
QT_FORWARD_DECLARE_CLASS(QGridLayout)
namespace ProjectExplorer {
// --------------------------------------------------------------------------
@@ -46,6 +48,12 @@ class PROJECTEXPLORER_EXPORT KitConfigWidget : public QWidget
Q_OBJECT
public:
enum LayoutColumns {
LabelColumn,
WidgetColumn,
ButtonColumn
};
KitConfigWidget(QWidget *parent = 0) : QWidget(parent)
{ }
@@ -57,8 +65,15 @@ public:
virtual bool isDirty() const = 0;
virtual QWidget *buttonWidget() const { return 0; }
virtual void addToLayout(QGridLayout *layout, int row);
signals:
void dirty();
protected:
void addLabel(QGridLayout *layout, int row);
void addButtonWidget(QGridLayout *layout, int row);
};
} // namespace ProjectExplorer

View File

@@ -44,6 +44,32 @@
#include <QStyle>
namespace ProjectExplorer {
void KitConfigWidget::addToLayout(QGridLayout *layout, int row)
{
addLabel(layout, row);
layout->addWidget(this, row, WidgetColumn);
addButtonWidget(layout, row);
}
void KitConfigWidget::addLabel(QGridLayout *layout, int row)
{
static const Qt::Alignment alignment
= static_cast<Qt::Alignment>(style()->styleHint(QStyle::SH_FormLayoutLabelAlignment));
QLabel *label = new QLabel(displayName());
label->setToolTip(toolTip());
layout->addWidget(label, row, LabelColumn, alignment);
}
void KitConfigWidget::addButtonWidget(QGridLayout *layout, int row)
{
if (QWidget *button = buttonWidget()) {
if (button->toolTip().isEmpty())
button->setToolTip(toolTip());
layout->addWidget(button, row, ButtonColumn);
}
}
namespace Internal {
KitManagerConfigWidget::KitManagerConfigWidget(Kit *k, QWidget *parent) :
@@ -122,19 +148,7 @@ void KitManagerConfigWidget::addConfigWidget(ProjectExplorer::KitConfigWidget *w
Q_ASSERT(!m_widgets.contains(widget));
connect(widget, SIGNAL(dirty()), this, SIGNAL(dirty()));
int row = m_layout->rowCount();
QLabel *label = new QLabel(widget->displayName());
label->setToolTip(widget->toolTip());
m_layout->addWidget(label, row, 0,
Qt::Alignment(style()->styleHint(QStyle::SH_FormLayoutLabelAlignment)));
m_layout->addWidget(widget, row, 1);
QWidget *buttonWidget = widget->buttonWidget();
if (buttonWidget) {
if (buttonWidget->toolTip().isEmpty())
buttonWidget->setToolTip(widget->toolTip());
m_layout->addWidget(widget->buttonWidget(), row, 2);
}
widget->addToLayout(m_layout, m_layout->rowCount());
m_widgets.append(widget);
}

View File

@@ -123,11 +123,14 @@ QWidget *KitOptionsPage::createPage(QWidget *parent)
updateState();
if (m_toShow)
m_selectionModel->select(m_model->indexOf(m_toShow),
if (m_toShow) {
QModelIndex index = m_model->indexOf(m_toShow);
m_selectionModel->select(index,
QItemSelectionModel::Clear
| QItemSelectionModel::SelectCurrent
| QItemSelectionModel::Rows);
m_kitsView->scrollTo(index);
}
m_toShow = 0;
return m_configWidget;
@@ -182,6 +185,7 @@ void KitOptionsPage::addNewKit()
m_model->markForAddition(k);
QModelIndex newIdx = m_model->indexOf(k);
m_kitsView->scrollTo(newIdx);
m_selectionModel->select(newIdx,
QItemSelectionModel::Clear
| QItemSelectionModel::SelectCurrent
@@ -199,6 +203,7 @@ void KitOptionsPage::cloneKit()
m_model->markForAddition(k);
QModelIndex newIdx = m_model->indexOf(k);
m_kitsView->scrollTo(newIdx);
m_selectionModel->select(newIdx,
QItemSelectionModel::Clear
| QItemSelectionModel::SelectCurrent

View File

@@ -61,13 +61,16 @@ QString LocalApplicationRunControlFactory::displayName() const
return tr("Run");
}
RunControl *LocalApplicationRunControlFactory::create(RunConfiguration *runConfiguration, RunMode mode)
RunControl *LocalApplicationRunControlFactory::create(RunConfiguration *runConfiguration, RunMode mode, QString *errorMessage)
{
QTC_ASSERT(canRun(runConfiguration, mode), return 0);
LocalApplicationRunConfiguration *localRunConfiguration = qobject_cast<LocalApplicationRunConfiguration *>(runConfiguration);
// Force the dialog about executables at this point and fail if there is none
if (localRunConfiguration->executable().isEmpty())
if (localRunConfiguration->executable().isEmpty()) {
if (errorMessage)
*errorMessage = tr("No executable");
return 0;
}
return new LocalApplicationRunControl(localRunConfiguration, mode);
}

View File

@@ -48,7 +48,7 @@ public:
virtual ~LocalApplicationRunControlFactory();
virtual bool canRun(RunConfiguration *runConfiguration, RunMode mode) const;
virtual QString displayName() const;
virtual RunControl* create(RunConfiguration *runConfiguration, RunMode mode);
virtual RunControl* create(RunConfiguration *runConfiguration, RunMode mode, QString *errorMessage);
};
class LocalApplicationRunControl : public RunControl

View File

@@ -439,6 +439,11 @@ void Project::configureAsExampleProject(const QStringList &platforms)
Q_UNUSED(platforms);
}
bool Project::supportsNoTargetPanel() const
{
return false;
}
void Project::onBuildDirectoryChanged()
{
Target *target = qobject_cast<Target *>(sender());

View File

@@ -124,6 +124,8 @@ public:
virtual bool needsConfiguration() const;
virtual void configureAsExampleProject(const QStringList &platforms);
virtual bool supportsNoTargetPanel() const;
signals:
void displayNameChanged();
void fileListChanged();

View File

@@ -1626,13 +1626,29 @@ void ProjectExplorerPlugin::executeRunConfiguration(RunConfiguration *runConfigu
if (IRunControlFactory *runControlFactory = findRunControlFactory(runConfiguration, runMode)) {
emit aboutToExecuteProject(runConfiguration->target()->project(), runMode);
RunControl *control = runControlFactory->create(runConfiguration, runMode);
if (!control)
QString errorMessage;
RunControl *control = runControlFactory->create(runConfiguration, runMode, &errorMessage);
if (!control) {
showRunErrorMessage(errorMessage);
return;
}
startRunControl(control, runMode);
}
}
void ProjectExplorerPlugin::showRunErrorMessage(const QString &errorMessage)
{
if (errorMessage.isNull()) {
// a error occured, but message was not set
QMessageBox::critical(Core::ICore::mainWindow(), tr("Unknown error"), errorMessage);
} else if (errorMessage.isEmpty()) {
// a error, but the message was set to empty
// hack for qml observer warning, show nothing at all
} else {
QMessageBox::critical(Core::ICore::mainWindow(), tr("Could Not Run"), errorMessage);
}
}
void ProjectExplorerPlugin::startRunControl(RunControl *runControl, RunMode runMode)
{
d->m_outputPane->createNewOutputWindow(runControl);

View File

@@ -109,6 +109,7 @@ public:
Internal::ProjectExplorerSettings projectExplorerSettings() const;
void startRunControl(RunControl *runControl, RunMode runMode);
static void showRunErrorMessage(const QString &errorMessage);
// internal public for FlatModel
void renameFile(Node *node, const QString &to);

Some files were not shown because too many files have changed in this diff Show More