Russian Qt Forum
Ноябрь 23, 2024, 05:51 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1]   Вниз
  Печать  
Автор Тема: [solved] установка свойства ломает приложение  (Прочитано 7521 раз)
Alex Custov
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2063


Просмотр профиля
« : Апрель 15, 2009, 00:43 »

Привет. Столкнулся с такой проблемой... Думал что я немного что-то недопонял, вынес в отдельное минимальное приложение - воспроизводится  Шокированный  Шокированный

.pro файл:

Код
Bash
TEMPLATE = app
TARGET =
DEPENDPATH += .
INCLUDEPATH += .
 
CONFIG += warn_on release
 
# Input
HEADERS += application.h
SOURCES += main.cpp application.cpp
 
#QMAKE_CXXFLAGS += -DREPRODUCE
 

Минимальный код рабочего проекта:

application.h:
Код
C++ (Qt)
#ifndef G_APPLICATION_H
#define G_APPLICATION_H
 
#ifdef REPRODUCE
 
#include <QApplication>
 
class Application : public QApplication
{
   public:
       Application(int, char **);
};
 
#endif
 
#endif
 

application.cpp:
Код
C++ (Qt)
#ifdef REPRODUCE
#include "application.h"
 
Application::Application(int argc, char **argv) : QApplication(argc, argv)
{}
#endif
 

main.cpp:
Код
C++ (Qt)
#include <QApplication>
#include <QVariant>
#include <QDebug>
 
#include "application.h"
 
#ifndef REPRODUCE
class Application : public QApplication
{
   public:
       Application(int argc, char **argv) : QApplication(argc, argv)
       {}
};
#endif
 
int main(int argc, char *argv[])
{
   Application app(argc, argv);
 
   app.setProperty("hello", "hello");
 
   return app.exec();
}
 

QMAKE_CXXFLAGS закомментирован, значит используется наследник QApplication, реализованный прямо в main.cpp. Компилируем.  Запускаем:
Цитировать
./qt4-template
("./qt4-template")

Всё вроде нормально. Теперь расскоментируем QMAKE_CXXFLAGS в про файле. В этом случае Application помещается в другой модуль, qmake && make clean && make, запускаем:

Цитировать
$ ./qt4-template
Ошибка сегментирования

ltrace:
Цитировать
$ ltrace -C ./qt4-template
__libc_start_main(0x8048e60, 1, 0xbffb6d24, 0x8048ff0, 0x8048fe0 <unfinished ...>
QApplication::QApplication(int&, char**, int)(0xbffb6c70, 0xbffb6c44, 0xbffb6d24, 263171, 0xb7466268 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb6a58, 0xbffb6940, 0, 0)                     = 0xb767ffa8
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb5dd8, 0, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb5dd8, 0xbffb5dd8, 0xbffb6c70, 0xbffb5d28 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb5dd8, 0xb7fb97c4, 0, 0)                     = 0xb7f644a8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb6978, 0, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb6978, 0xbffb6978, 0xb7db7bc3, 0xb7db7bd6 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb6978, 2, 4081, 0xbffb6ab4)                  = 0xb7f644a8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0x92298e0, 0xbffb6948, 0xb7680778, 0x91ff260 <unfinished ...>
QObject::childEvent(QChildEvent*)(0x92298e0, 0xbffb6948, 0xbffb6638, 0xb71770cd, 0xbffb6920)    = 0xb7f654a8
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QObject::connectNotify(char const*)(0x922e640, 0xb7db8320, 0x92298e0, 4, 0)                     = 0x922e640
<... QApplication::QApplication(int&, char**, int) resumed> )                                   = 263171
QVariant::QVariant(char const*)(0xbffb6c64, 0x80490a8, 0xbffb6d24, 0xb71efd30, 0xb7f79734)      = 0x9234ed0
QObject::setProperty(char const*, QVariant const&)(0xbffb6c70, 0x80490a8, 0xbffb6c64, 0xb71efd30, 0xb7f79734 <unfinished ...>
QApplication::metaObject() const(0xbffb6c70, 0xb746ca48, 0xb7f9caf0, 0xb7680778, -1)            = 0xb7f64488
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb6c0c, 0xb7483b4b, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb6c0c, 0xbffb6c0c, 0, 1)                          = 0
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 0
<... QObject::setProperty(char const*, QVariant const&) resumed> )                              = 0
QVariant::~QVariant()(0xbffb6c64, 0x80490a8, 0xbffb6c64, 0xb71efd30, 0xb7f79734)                = 0x9234ed0
QApplication::exec()(0xbffb6c64, 0x80490a8, 0xbffb6c64, 0xb71efd30, 0xb7f79734 <unfinished ...>
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0x9206400, 0xb6e20090, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0x9206400, 0x9206400, 0, 0x9bdaf51 <unfinished ...>
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb654c, 0x556b9394, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb654c, 0xbffb654c, 0xb7fa73bd, 6 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb654c, 0xb7fb8ff4, 0x10822fdb, 0xb71aa6f0)   = 0x80490c8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb654c, 0x556b9394, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb654c, 0xbffb654c, 0xb7fa73bd, 6 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb654c, 0xb7fb8ff4, 0x10822fdb, 0xb71aa6f0)   = 0x80490c8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0xbffb6c70, 0xbffb654c, 0x556b9394, 0x91ff260 <unfinished ...>
QApplication::event(QEvent*)(0xbffb6c70, 0xbffb654c, 0xbffb654c, 0xb7fa73bd, 6 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbffb6c70, 0xbffb654c, 0xb7fb8ff4, 0x10822fdb, 0xb71aa6f0)   = 0x80490c8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0x92298e0, 0x924eaf0, 0xb7435ff4, 0x91ff260 <unfinished ...>
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0x92298e0, 0xbffb65dc, 0xb71770cd, 0x91ff260 <unfinished ...>
QObject::childEvent(QChildEvent*)(0x92298e0, 0xbffb65dc, 0xb6e12b28, 0xb7f79734, 0xbffb654c)    = 0xb7f654a8
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbffb6c70, 0x922e640, 0xbffb6a10, 0x92298e0, 0x91ff260 <unfinished ...>
--- SIGSEGV (Segmentation fault) ---
+++ killed by SIGSEGV +++

Теперь комментируем строку "app.setProperty("hello", "hello");" - вуаля, всё работает.

Это нормально? Смеющийся Смеющийся

P.S. Debian Lenny, Qt 4.4.3.

Добавление: Qt 4.5 - воспроизводится

Добавление-2: Более конкретное воспроизведение: сразу после установки того свойства, argc() возвращает левое, явно неинициализированное значение.
Код
C++ (Qt)
   app.setProperty("hello", "hello");
 
   int ac = app.argc();
 
   printf("ARGC: %d\n", ac);
 

Цитировать
$ make && ./qt4-template
g++ -c -pipe -DREPRODUCE -O2 -Wall -W -D_REENTRANT -DQT_NO_DEBUG -DQT_GUI_LIB -DQT_CORE_LIB -DQT_SHARED -I/usr/share/qt4/mkspecs/linux-g++ -I. -I/usr/include/qt4/QtCore -I/usr/include/qt4/QtCore -I/usr/include/qt4/QtGui -I/usr/include/qt4/QtGui -I/usr/include/qt4 -I. -I. -I. -o main.o main.cpp
g++  -o qt4-template main.o application.o    -L/usr/lib -lQtGui -lQtCore -lpthread
ARGC: 134517160
Ошибка сегментирования

Если свойство не устанавливаем, argc() возвращает 1. Critical bug по ходу.
« Последнее редактирование: Апрель 15, 2009, 19:03 от AX » Записан
pastor
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 2901



Просмотр профиля WWW
« Ответ #1 : Апрель 15, 2009, 11:32 »

Попробкй добавить макрос Q_OBJECT в Application, изменится что-то или нет. Если нет - пишем баг репорт
Записан

Integrated Computer Solutions, Inc. (ICS)
http://www.ics.com/
Alex Custov
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2063


Просмотр профиля
« Ответ #2 : Апрель 15, 2009, 13:26 »

он там был изначально, но его наличие ни на что не влияет
Записан
pastor
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 2901



Просмотр профиля WWW
« Ответ #3 : Апрель 15, 2009, 13:51 »

Проверил на винде, краша нет.

По поводу argc, да действительно, значение меняется после вызова setProperty, причем в обоих случаях. Но думаю это не баг. В ассистанте есть примечания:

Цитировать
Note that argc and argv might be changed. Qt removes command line arguments that it recognizes.

Цитировать
The argc and argv arguments are processed by the application, and made available in a more convenient form by the arguments() function.

Я добавил вот такие вот строки, все аргументы на месте:

Код
C++ (Qt)
int main(int argc, char *argv[])
{
   Application app(argc, argv);
 
   app.setProperty("hello", "hello");
 
   QStringList list = app.arguments();
   qDebug() << list.size();
   for (int i = 0; i < list.size(); ++i)
       qDebug() << list.at(i);
 
   return app.exec();
}

Чуть позже проверю на openSuse 11.0

UPD: Более того, методы argc и argv из Qt 3 Support. В Qt4 приложениях рекомендуется использовать следующее:

Цитировать
int QCoreApplication::argc ()   [static]
Use arguments().size() instead.

Цитировать
char ** QCoreApplication::argv ()   [static]
Use arguments() instead.
« Последнее редактирование: Апрель 15, 2009, 13:54 от pastor » Записан

Integrated Computer Solutions, Inc. (ICS)
http://www.ics.com/
Alex Custov
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2063


Просмотр профиля
« Ответ #4 : Апрель 15, 2009, 17:01 »

Я добавил вот такие вот строки, все аргументы на месте:

Код
C++ (Qt)
int main(int argc, char *argv[])
{
   Application app(argc, argv);
 
   app.setProperty("hello", "hello");
 
   QStringList list = app.arguments();
   qDebug() << list.size();
   for (int i = 0; i < list.size(); ++i)
       qDebug() << list.at(i);
 
   return app.exec();
}

У меня не на месте Улыбающийся

Код
C++ (Qt)
#include <QApplication>
#include <QStringList>
#include <QVariant>
#include <QDebug>
 
#include "application.h"
 
#ifndef REPRODUCE
class Application : public QApplication
{
   public:
       Application(int argc, char **argv) : QApplication(argc, argv)
       {}
};
#endif
 
int main(int argc, char *argv[])
{
   Application app(argc, argv);
 
   app.setProperty("hello", "hello");
 
   QStringList list = app.arguments();
 
   qDebug() << list.size();
 
   for (int i = 0; i < list.size(); ++i)
           qDebug() << list.at(i);
 
   return app.exec();
}
 

Цитировать
$ ltrace -C ./qt4-template
__libc_start_main(0x8049260, 1, 0xbfbd4144, 0x80499a0, 0x8049990 <unfinished ...>
QApplication::QApplication(int&, char**, int)(0xbfbd4074, 0xbfbd4054, 0xbfbd4144, 263171, 0 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbfbd4074, 0xbfbd3e68, 0xbfbd3d50, 0, 0)                     = 0xb769cfa8
QApplication::notify(QObject*, QEvent*)(0xbfbd4074, 0xbfbd4074, 0xbfbd31e8, 0, 0x9b33260 <unfinished ...>
QApplication::event(QEvent*)(0xbfbd4074, 0xbfbd31e8, 0xbfbd31e8, 0xbfbd4074, 0xbfbd3138 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbfbd4074, 0xbfbd31e8, 0xb7fd67c4, 0, 0)                     = 0xb7f814a8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbfbd4074, 0xbfbd4074, 0xbfbd3d88, 0, 0x9b33260 <unfinished ...>
QApplication::event(QEvent*)(0xbfbd4074, 0xbfbd3d88, 0xbfbd3d88, 0xb7dd4bc3, 0xb7dd4bd6 <unfinished ...>
QObject::childEvent(QChildEvent*)(0xbfbd4074, 0xbfbd3d88, 2, 4081, 0xbfbd3ec4)                  = 0xb7f814a8
<... QApplication::event(QEvent*) resumed> )                                                    = 1
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QApplication::notify(QObject*, QEvent*)(0xbfbd4074, 0x9b5d8e0, 0xbfbd3d58, 0xb769d778, 0x9b33260 <unfinished ...>
QObject::childEvent(QChildEvent*)(0x9b5d8e0, 0xbfbd3d58, 0xbfbd3a48, 0xb71940cd, 0xbfbd3d30)    = 0xb7f824a8
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 1
QObject::connectNotify(char const*)(0x9b62640, 0xb7dd5320, 0x9b5d8e0, 4, 0)                     = 0x9b62640
<... QApplication::QApplication(int&, char**, int) resumed> )                                   = 263171
QVariant::QVariant(char const*)(0xbfbd4068, 0x8049a68, 0xbfbd4144, 0xb7334ff4, 0xb77e5330)      = 0x9b68ed0
QObject::setProperty(char const*, QVariant const&)(0xbfbd4074, 0x8049a68, 0xbfbd4068, 0xb7334ff4, 0xb77e5330 <unfinished ...>
QApplication::metaObject() const(0xbfbd4074, 0xb7489a48, 0xb7fb9af0, 0xb769d778, -1)            = 0xb7f81488
QApplication::notify(QObject*, QEvent*)(0xbfbd4074, 0xbfbd4074, 0xbfbd401c, 0xb74a0b4b, 0x9b33260 <unfinished ...>
QApplication::event(QEvent*)(0xbfbd4074, 0xbfbd401c, 0xbfbd401c, 0, 1)                          = 0
<... QApplication::notify(QObject*, QEvent*) resumed> )                                         = 0
<... QObject::setProperty(char const*, QVariant const&) resumed> )                              = 0
QVariant::~QVariant()(0xbfbd4068, 0x8049a68, 0xbfbd4068, 0xb7334ff4, 0xb77e5330)                = 0x9b68ed0
QCoreApplication::arguments()(0xbfbd4094, 0x8049a68, 0xbfbd4068, 0xb7334ff4, 0xb77e5330 <unfinished ...>
--- SIGSEGV (Segmentation fault) ---
+++ killed by SIGSEGV +++
Записан
pastor
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 2901



Просмотр профиля WWW
« Ответ #5 : Апрель 15, 2009, 18:08 »

Воспроизвел баг и на своей линукс машине. Но это оказался  не баг )

Все оказалось оч просто. Измени конструктор таким образом (передача argc по ссылке):

Код
C++ (Qt)
Application(int &argc, char **argv)
{
}

и будет тебе счастье )))
Записан

Integrated Computer Solutions, Inc. (ICS)
http://www.ics.com/
Alex Custov
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2063


Просмотр профиля
« Ответ #6 : Апрель 15, 2009, 19:02 »

тьфу, и правда Улыбающийся
Записан
pastor
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 2901



Просмотр профиля WWW
« Ответ #7 : Апрель 15, 2009, 20:33 »

Да Улыбающийся Поначалу и вправду подумал что баг. Но когда присмотрелся на конструктор, все стало на свои места Улыбающийся
Записан

Integrated Computer Solutions, Inc. (ICS)
http://www.ics.com/
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.377 секунд. Запросов: 23.