2015-10-22 4 views
1

У меня очень странное поведение с моим очень простым примером, который сбой, когда я использую наследование (class NapanaApplication : public QGuiApplication), но не работает с ошибкой и работает правильно при непосредственном использовании QGuiApplication.C++ - ошибка сегментации при наследовании

Код в точности такой, как показано ниже, NapanaApplication ничего не делает, просто наследует от QGuiApplication.

Что случилось?

РЕШЕННЫЙ: Я нашел причину. Это потому, что QGuiApplication принимает argc в качестве справочного материала, но конструктор NapanaApplication этого не делает. Он не вызывает никаких ошибок, но это приводит к тому, что QGuiApplication работает с некоторой временной переменной argc вместо одной из main.

main.cpp

#include "napanaapplication.h" 
#include "napanawindow.h" 

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

    /*NapanaApplication app(argc, argv);*/ // segmentation fault 

    QGuiApplication app(argc, argv); // no error   

    NapanaWindow win; 

    win.resize(800, 600); 
    win.show(); 

    return app.exec(); 
} 

napanaapplication.h

#ifndef NAPANAAPPLICATION_H 
#define NAPANAAPPLICATION_H 

#include <QGuiApplication> 

class NapanaApplication : public QGuiApplication 
{ 

    Q_OBJECT 

public: 
    explicit NapanaApplication(int argc, char* argv[]); 
signals: 

public slots: 
}; 

#endif // NAPANAAPPLICATION_H 

napanapplication.c

#include "napanaapplication.h" 

NapanaApplication::NapanaApplication(int argc, char* argv[]) : QGuiApplication(argc, argv) {} 

Выход из отладчика: он вылетает, когда strlen вызывается в QString::fromLocal8Bit. Указатель char*, на который вызывается strlen, имеет значение 0x21, я не понимаю, почему это должно быть, вероятно, что-то от argv.

0 strlen /usr/lib/debug/lib/x86_64-linux-gnu/libc-2.19.so 106 0x7ffff65c0aea 
1 QString::fromLocal8Bit qstring.h 534 0x7ffff7142c11 
2 QCoreApplication::arguments qcoreapplication.cpp 2254 0x7ffff738503d 
3 sm_performSaveYourself qxcbsessionmanager.cpp 188 0x7ffff05f5e3a 
4 sm_saveYourselfCallback qxcbsessionmanager.cpp 171 0x7ffff05f5cc9 
5 _SmcProcessMessage   0x7ffff014ad37 
6 IceProcessMessages   0x7fffeff3b8c7 
7 QSmSocketReceiver::socketActivated qxcbsessionmanager.cpp 322 0x7ffff05f67e0 
8 QSmSocketReceiver::qt_static_metacall qxcbsessionmanager.moc 68 0x7ffff05f6f88 
9 QMetaObject::activate qobject.cpp 3718 0x7ffff73c097e 
10 QMetaObject::activate qobject.cpp 3583 0x7ffff73c016c 
11 QSocketNotifier::activated moc_qsocketnotifier.cpp 134 0x7ffff7458376 
12 QSocketNotifier::event qsocketnotifier.cpp 296 0x7ffff73cb4db 
13 QCoreApplicationPrivate::notify_helper qcoreapplication.cpp 1093 0x7ffff7382872 
14 QCoreApplication::notify qcoreapplication.cpp 1038 0x7ffff7382554 
15 QGuiApplication::notify qguiapplication.cpp 1537 0x7ffff77f3076 
16 QCoreApplication::notifyInternal qcoreapplication.cpp 965 0x7ffff738245e 
17 QCoreApplication::sendEvent qcoreapplication.h 224 0x7ffff7386087 
18 socketNotifierSourceDispatch qeventdispatcher_glib.cpp 101 0x7ffff73f6afe 
19 g_main_context_dispatch   0x7ffff4f8dbd4 
20 ??   0x7ffff4f8de18 
21 g_main_context_iteration   0x7ffff4f8debc 
22 QEventDispatcherGlib::processEvents qeventdispatcher_glib.cpp 418 0x7ffff73f7799 
23 QPAEventDispatcherGlib::processEvents qeventdispatcher_glib.cpp 115 0x7ffff0648906 
24 QEventLoop::processEvents qeventloop.cpp 128 0x7ffff737f0b2 
25 QEventLoop::exec qeventloop.cpp 204 0x7ffff737f373 
26 QCoreApplication::exec qcoreapplication.cpp 1229 0x7ffff7382b36 
27 QGuiApplication::exec qguiapplication.cpp 1528 0x7ffff77f3026 
28 main main.cpp 13 0x40275a  
+0

Сбой с какой ошибкой? – Surt

+0

@Surt: ошибка сегментации (сигнал SIGSEGV) – Krab

ответ

7

Note the signature of QGuiApplication:

QGuiApplication(int & argc, char ** argv) 

Ваша функция имеет int argc вместо. Я думаю, что вы вызываете segfault, когда целочисленное значение затем рассматривается как ссылка конструктором родительского класса.

+1

Oooo. Это сделало бы это. Плохое число приводит к неправильному количеству аргументов, приводит к 'strlen' в unterminated char array. – user4581301

+0

@ user4581301 Что странно, что это происходит только тогда, когда вы запускаете цикл событий через 'app.exec()', хотя? Я думаю, Qt не проверяет некоторые аргументы до этого. –

+2

Я посмотрел в исходный код, и потому, что Qt хранит argc как ссылку тоже, они инициализируют его в конструкторе QtConstructor (int & argcc): argc (argcc). Если они хранят его как обычный int, ничего не произойдет. – Krab

Смежные вопросы