Solved Segmentation Fault when reading from a TCPSocket
-
Hey I am trying to send data continuously through TCPSocket and when I debug I see the line below gives me SIGSEGV Segmentation Fault crash. Can you tell me how can I fix this problem?
qint64 bytes = buffer->write(socket->readAll()); //The program crashes at this line
Here is sender the code:
#include "tcpsender.h" #include "ui_tcpsender.h" #include <QtWidgets> #include <QtNetwork> #include <QtCore> #include <QDebug> #include <QBuffer> #define XRES 640 #define YRES 480 #define SIZE 640*480*3 TCPSender::TCPSender(QWidget *parent) : QWidget(parent), ui(new Ui::TCPSender) { ui->setupUi(this); statusLabel = new QLabel(tr("Ready to send frames on port 6667")); statusLabel->setWordWrap(true); startButton = new QPushButton(tr("&Start")); auto quitButton = new QPushButton(tr("&Quit")); auto buttonBox = new QDialogButtonBox; buttonBox->addButton(startButton, QDialogButtonBox::ActionRole); buttonBox->addButton(quitButton, QDialogButtonBox::RejectRole); socket = new QTcpSocket(this); connect(startButton, &QPushButton::clicked, this, &TCPSender::startConnection); connect(quitButton, &QPushButton::clicked, this, &TCPSender::close); connect(socket, SIGNAL(connected()), SLOT(startSending())); connect(&timer, &QTimer::timeout, this, &TCPSender::sendFrame); auto mainLayout = new QVBoxLayout; mainLayout->addWidget(statusLabel); mainLayout->addWidget(buttonBox); setLayout(mainLayout); setWindowTitle(tr("Broadcast Sender")); camera = new Camera("/dev/video0", XRES, YRES); time = QTime::currentTime(); } TCPSender::~TCPSender() { delete ui; } void TCPSender::startConnection() { socket->connectToHost(ui->lineEdit->text(), 6667, QIODevice::WriteOnly); } void TCPSender::startSending() { startButton->setEnabled(false); //timer.start(1000/(24*1800)); timer.start(1000/24); qDebug()<<"Timer start"; } void TCPSender::sendFrame() { if(socket->state()==QAbstractSocket::ConnectedState){ auto frame = camera->frame(); image = new QImage(frame.data,XRES,YRES,QImage::Format_RGB888); QImage im = image->convertToFormat(QImage::Format_Grayscale8); QByteArray ba; QBuffer buffer(&ba); qDebug()<<"writing socket"; socket->write(ba); int speed = time.msecsTo(QTime::currentTime()); time = QTime::currentTime(); speed = 1000*300/speed; ui->label->setText(QString("%1 kb/s").arg(speed)); delete image; } }
And here is the reciever code:
#include "reciever.h" #include <QBuffer> #include <QTcpSocket> #include <QImage> #include <QDebug> #include <iostream> #include <fstream> #include <string> #include <sstream> #include <unistd.h> #define XRES 640 #define YRES 480 #define SIZE 640*480*3 Reciever::Reciever(QObject* parent): QTcpServer(parent) { connect(this, SIGNAL(newConnection()), this, SLOT(addConnection())); qDebug()<<"Const"; } void Reciever::addConnection() { qDebug()<<"Selam"; QTcpSocket* connection = nextPendingConnection(); connect(connection, SIGNAL(readyRead()), this, SLOT(receiveImage())); } void Reciever::receiveImage() { qDebug()<<"RECIEVE"; QTcpSocket* socket = static_cast<QTcpSocket*>(sender()); QBuffer* buffer = buffers.value(socket); qint64 bytes = buffer->write(socket->readAll()); emit sendBuffer(buffer,bytes); }
Please note that I only posted the relevant parts of the code.
-
@onurcevik said in Segmentation Fault when reading from a TCPSocket:
QTcpSocket* socket = static_cast<QTcpSocket*>(sender());
QBuffer* buffer = buffers.value(socket);qint64 bytes = buffer->write(socket->readAll());
In such cases you ALWAYS have to check the pointers!
Either socket is an invalid pointer or buffer. -
@jsulm Code was working just fine in the previous version where I was creating new connection and ending the previous one whenever I wanted to send new data. Which wasn't really optimized way to do it. But it started to give me this error when I switched to this version(single-connection) Where I create the connection and don't end it until program exits. So I am not sure if its really the pointers.
-
@onurcevik Please simply print out socket to see whether it is nullptr or not, else we can guess here a lot about something you can easily check.
QTcpSocket* socket = static_cast<QTcpSocket*>(sender()); qDebug() << socket; QBuffer* buffer = buffers.value(socket); qDebug() << buffer;
-
@jsulm said in Segmentation Fault when reading from a TCPSocket:
QTcpSocket* socket = static_cast<QTcpSocket*>(sender());
qDebug() << socket;
QBuffer* buffer = buffers.value(socket);
qDebug() << buffer;Oh I see it now
QBuffer* buffer = buffers.value(socket);
causes the problem because I commented out the lines
connections.append(connection); QBuffer* buffer = new QBuffer(this); buffer->open(QIODevice::ReadWrite); buffers.insert(connection, buffer);
I removed this lines since I will only have single connection. Thanks for the help @jsulm . Since its just a comment line that causes problem should I delete this thread ?
-
Since its just a comment line that causes problem should I delete this thread ?
No! It may help others, or yourself later. You only learn from mistakes ;)
Just mark the topic as SOLVED.
Thanks
-
Hi,
One small note, use qobject_cast when casting QObject based classes. This will return a null pointer if either the source is already a null pointer or not from the correct class.