Qt try catch排错历程

前几天从网上下载了一份网友用Qt写的作品,打开时发现它是用VS2010写的,而我机器上只有VS2008,倒腾了半天最终没能用VS2008打开,而自己又不想再安装VS2010。还好在工程中有.pro文件,我只好用QtCreator打开了它。但是在编译的时候出现了这个错误提示:exception handling disabled, use -fexceptions to enable,因此也就有了以下的排错经历。
    为了找到问题的根源,我在两个环境下专门建了一个类似的小工程TryCatchTest。
    环境一:VS2008 + Qt4.8.3-vs2008 + Qt Visual Studio Add-in1.1.10
    环境二:Qt Creator 2.6.0 + Qt4.8.3-mingw + mingw32 4.6.2
    代码如下:

复制代码

  1. #include <QCoreApplication> 
    enum Excep 

    EXCEP_ONE, 
    EXCEP_TWO 
    };

    void throwFun() 

      throw EXCEP_ONE; 
    }

    int main(int argc, char *argv[]) 

      QCoreApplication a(argc, argv); 
      try 
      { 
        throwFun(); 
      } 
      catch(Excep ex) 
      { 
        if(ex == EXCEP_ONE ) 
        { 
         //ToDo.... 
        } 
      } 
    return a.exec(); 
    }

在VS环境下编译后,一点问题都没有,甚至连警告都没有。这说明问题出在编译器上,而且是编译器的配置问题。但是怎么对mingw-g++编译器进行配置呢?于是我在网上搜了下错误提示信息,找到了一篇博客http://blog.csdn.net/garybook/article/details/7764200。但是很遗憾这篇博客所解决的问题并不是Qt的,而是解决安卓的NDK问题的。但其中的内容给了我一点启发。文章中说此问题的出现是编译器的异常捕获被禁用了,需要在Android.mk文件中开启。在Android.mk文件中添加:LOCAL_CPPFLAGS += -fexceptions就可以了。于是我依葫芦画瓢的在TryCatchTest.pro文件中添加了一行CONFIG += -fexceptions,但是错误依旧。
    由于在Qt Creator中仅执行qmake时是没问题的,而且还生成了三个文件Makefile、Makefile.Debug、Makefile.Release。在Makefile.Debug和Makefile.Release文件中我找到了以下这行:
CXXFLAGS      = -O2 -Wall -Wextra -fno-exceptions -fno-rtti $(DEFINES)
那么这一行是怎么生成的,也就是说qmake.exe到底是怎么工作的呢。为了搞清楚这个疑惑,我自己编译了qmake的源码,并进行了一系列的跟踪调试(编译qmake的过程也困难重重,其又可另写篇日志了,此处不再赘述)。
    对qmake.exe进行跟踪调试后,终于发现了配置-fno-exceptions的地方。它是在Qt安装目录下的 mkspecs\features\win32\default_pre.prf文件中。这个文件中有这样一句:
CONFIG = rtti_off exceptions_off stl_off incremental_off thread_off windows $$CONFIG
随之又跟踪到了mkspecs/features/win32/exceptions_off.prf文件,在这个文件中看到了这样一句:
CONFIG  -=  exceptions。
于是我在TryCatchTest.pro文件中添加了一行 CONFIG += exceptions(也可以写成CONFIG  -= exceptions_off)。就这样问题完美解决了。
    其实如果细心的话,我们可以在上面提到的Makefile文件中看到default_pre.prf、exceptions_off.prf文件的踪迹。
    以下是Makefile文件中的部分片断:

复制代码

  1. ...... 
    Makefile: ../TryCatchTest/TryCatchTest.pro 
    ../../Qt/4.8.3/mkspecs/win32-g++/qmake.conf \ 
    ../../Qt/4.8.3/mkspecs/features/device_config.prf \ 
    ../../Qt/4.8.3/mkspecs/features/qt_functions.prf \ 
    ../../Qt/4.8.3/mkspecs/features/qt_config.prf \ 
    ../../Qt/4.8.3/mkspecs/features/exclusive_builds.prf \ 
    ../../Qt/4.8.3/mkspecs/features/default_pre.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/default_pre.prf \ 
    ../../Qt/4.8.3/mkspecs/features/debug.prf \ 
    ../../Qt/4.8.3/mkspecs/features/debug_and_release.prf \ 
    ../../Qt/4.8.3/mkspecs/features/default_post.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/default_post.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/console.prf \ 
    ../../Qt/4.8.3/mkspecs/features/declarative_debug.prf \ 
    ../../Qt/4.8.3/mkspecs/features/warn_on.prf \ 
    ../../Qt/4.8.3/mkspecs/features/qt.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/thread.prf \ 
    ../../Qt/4.8.3/mkspecs/features/moc.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/stl_off.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/exceptions_off.prf \ 
    ../../Qt/4.8.3/mkspecs/features/win32/rtti_off.prf \ 
    ../../Qt/4.8.3/mkspecs/features/resources.prf \ 
    ../../Qt/4.8.3/mkspecs/features/uic.prf \ 
    ../../Qt/4.8.3/mkspecs/features/include_source_dir.prf 
    ......

从上面的片断可以看出,编译器的配置信息都是在features文件夹中的xxx.prf中,其实如果再仔细点的话就会发现Qt Creator启动qmake时传了两个特殊的参数,-spec和win32-g++。下面是Qt Creator在编译信息显示框中启动qmake的完整命令:

复制代码

  1. "C:\Qt\4.8.3\bin\qmake.exe" E:\QtWork\TryCatchTest\TryCatchTest.pro -r -spec win32-g++ "CONFIG+=debug" "CONFIG+=declarative_debug"

这两个特殊参数的玄机我就不多说了。

后记:
    写这篇日志的目的主要在于记录这个过程,对于我这种新手文笔比不了那些博客大牛,所涉及的技术知识也许在高手眼里就根本不值得一提。但是在解决这个问题的过程中使我多少了解了些qmake的机制,这无疑是一种收获一种提升!

http://www.qtcn.org/bbs/apps.php?q=diary&a=detail&did=1197&uid=123665

时间: 2024-10-13 20:20:53

Qt try catch排错历程的相关文章

[转]KDE/QT与GNOME/GTK比较

[转]KDE/QT与GNOME/GTK比较 http://www.cnblogs.com/itech/archive/2009/08/18/1548964.html 虽然在商业方面存在竞争,GNOME与KDE两大阵营的开发者关系并没有变得更糟,相反他们都意识到支持对方的重要性—如果KDE和GNOME无法实现 应用程序的共享,那不仅是巨大的资源浪费,而且将导致Linux出现根本上的分裂.从2003年开始经过两年多的努力,KDE和GNOME都已经实现高度 的互操作性,两大平台的程序都是完全共享的,例

JBOSS配置排错

jboss提供了二种运行模式:standalone(独立运行模式).domain(域模式),日常开发中,使用standalone模式足已:但生产部署时,一个app,往往是部署在jboss集群环境中的,如果所有jboss server均采用standalone模式,会给运维带来极大的工作量,需要每台jboss server上逐一部署/更新,显然不适合. domain模式正是为了解决这一问题,该模式下,所有jbossserver可以划分成不同的group(注:这里的jbossserver并不一定要对

用QT创建WINDOWS服务程序

我写一段,你将东西套进去就可以了,这里原来写的是定时服务,用的是boost::asio库,当然最好看一看boost::asio相关介绍. #include <iostream>#include <fstream>#include <boost/asio.hpp>#include <boost/bind.hpp>#include <boost/function.hpp>#include <boost/date_time/posix_time/

Understand the Qt containers(有对应表)

Container classes are one of the cornerstones of object-oriented programming, invaluable tools that free us from having to permanently think about memory management. Qt comes with its own set of container classes, closely modeled after those in the S

Qt中事件分发源代码剖析(一共8个步骤,顺序非常清楚:全局的事件过滤器,再传递给目标对象的事件过滤器,最终传递给目标对象)

Qt中事件分发源代码剖析 Qt中事件传递顺序: 在一个应该程序中,会进入一个事件循环,接受系统产生的事件,并且进行分发,这些都是在exec中进行的.下面举例说明: 1)首先看看下面一段示例代码: [cpp] view plaincopy int main(int argc, char *argv[]) { QApplication a(argc, argv); MouseEvent w; w.show(); return a.exec(); } 2)a.exec进入事件循环,调用的是QAppli

KDE/QT与GNOME/GTK比较

转自:http://linux.chinaunix.net/bbs/thread-1125240-1-1.html 虽然在商业方面存在竞争,GNOME与KDE两大阵营的开发者关系并没有变得更糟,相反他们都意识到支持对方的重要性—如果KDE和GNOME无法实现应用程序的共享,那不仅是巨大的资源浪费,而且将导致Linux出现根本上的分裂.从2003年开始经过两年多的努力,KDE和GNOME都已经实现高度的互操作性,两大平台的程序都是完全共享的,例如你可以在GNOME中运行Konqueror浏览 器.

学习Qt,Getting started

在界面的设计中,现在用的比较多的是Qt和WPF(C#),以前的MFC已出现衰老趋势.本人最近在学习Qt,觉得很有用,遂决定将学习历程记录下来,或许有感于后之来者,不亦乐哉. 一.Hello Qt #include "try_qt.h" #include <QtGui/QApplication> #include <QLabel> int main(int argc, char *argv[]) { QApplication app(argc, argv); QL

Qt Quick应用开发介绍 13 (JavaScript)

Chapter13 Annexure: JavaScript Language Overview 附录: JavaScript语言概览 Js语言总览; 提供一个Qt支持的所有语言特性的概览; 通过本文了解Js语言的基本特性; 特别是当你开始学习一个相关的技术, 如QML时, 你可以在这获得帮助; 这篇文章是对 JavaScript Language Overview http://qt-project.org/wiki/JavaScript 的轻微改动版本; 内容经过Qt4.8和QtQuick1

Linux下编译静态MinGW环境,编译windows平台Qt程序(使用MXE)

参考链接: MXE.>大多数程序都是在windows平台下开发的程序.windows 在现实中也是绕不过的一个系统平台,做为受过几年VC,MFC”虐待”的程序员,在做为一个程序员之前是一位Linux重度使用者,受够了MFC之后一直想要找一个框架替换,使用过GTK,wxWidgets,Qt,最后还是Qt用得多一些.我认为程序跨平台应该是一个基本标准,同一份代码不需改动,或者改动极少,放在不同的平台下编译就能使用.不同平台,同样的界面,同样的操作,同样的体验.这里要讲的是我如何在Linux 下开发跨