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

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

Страниц: [1]   Вниз
  Печать  
Автор Тема: QTcpSocket и сигнал readyRead  (Прочитано 8981 раз)
o-henry
Гость
« : Апрель 14, 2011, 11:07 »

Хочу разобраться с использованием QTcpSocket.
Пытаюсь написать примитивный клиент под WinXP.
В качестве сервера - виндовый гипертерминал.
В частности, интересует двунаправленный обмен данными без закрытия соединения после отправки данных (в отличие от примеров Fortune).
Отправленные моим приложением данные доходят до гипертерминала, отправленные с гипертерминала данные доходят до моего приложения.
Но при этом: сигнал readyRead от используемого мной QTcpSocket я получаю не только когда мое приложение получает данные от
гипертерминала, но и когда я отправляю данные через метод write сокета.
Что бы это значило и как с этим бороться?

мои исходники:
tcptester.h
Код:
#ifndef TCPTESTER_H
#define TCPTESTER_H

#include <QtNetwork>
#include <QObject>
#include <QString>
#include <QTcpSocket>

class TcpTester : public QObject
{
    Q_OBJECT
public:
    TcpTester(QObject *parent = 0);
    ~TcpTester();
    void InitConnection(QString address, quint16 port);
    void CloseConnection();
    void WriteTo(QString str);
    QTcpSocket * client;

signals:

public slots:
    void startTransfer();
    void ReportError(QAbstractSocket::SocketError ErrCode);
    void ReadFromSocket();
    void slotOnWritten(qint64 written);
};

#endif // TCPTESTER_H

tcptester.cpp
Код:
#include "tcptester.h"

TcpTester::TcpTester(QObject *parent) :
    QObject(parent)
{   client = new QTcpSocket (this);

    connect(client, SIGNAL(connected()),
     this, SLOT(startTransfer()),Qt::DirectConnection);


    connect(client,  SIGNAL(error(QAbstractSocket::SocketError)),
     this, SLOT(ReportError(QAbstractSocket::SocketError)),Qt::DirectConnection);

    connect(client,  SIGNAL(readyRead()),
     this, SLOT(ReadFromSocket()),Qt::DirectConnection);

    connect(client,  SIGNAL(bytesWritten(qint64)),
     this, SLOT(slotOnWritten(qint64)),Qt::DirectConnection);
}

TcpTester::~TcpTester()
{
  client->close();
}

void TcpTester::InitConnection(QString address, quint16 port)
{
    QHostAddress addr(address);
    client->connectToHost(addr, port);
}

void TcpTester::startTransfer()
{
  QString qstr= "Start transfer from client";
  QByteArray bytearr = qstr.toUtf8();

  client->write(qstr.toUtf8(),  qstr.toUtf8().length() );
  client->write("\r\n\0", 3);
  client->flush();

}

void TcpTester::CloseConnection()
{
     client->close();
}


void TcpTester::WriteTo(QString str)
{
  client->write(str.toUtf8(),  str.toUtf8().length() );
  client->write("\r\n\0", 3);
  client->flush();
}

void TcpTester::ReportError(QAbstractSocket::SocketError ErrCode)
{
 qDebug() << "SOCKET  ERROR=" << ErrCode;
}

void TcpTester::ReadFromSocket()
{
    QByteArray bytes = client->readAll();
    qDebug() << "recieved:" << bytes;
}

void TcpTester::slotOnWritten(qint64 written)
{
    qDebug() <<"slotOnWritten: " << written <<" bytes";
}


mainwindow.h
Код:
#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include "tcptester.h"

namespace Ui {
    class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT
public:
    explicit MainWindow(QWidget *parent = 0);

private:
    Ui::MainWindow *ui;
    TcpTester * pTester;

private slots:
    void on_pushButton_2_clicked();
    void on_pushButton_clicked();
};

#endif // MAINWINDOW_H

mainwindow.cpp
Код:
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "tcptester.h"
#include <QDebug>

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{  ui->setupUi(this);
    pTester = new TcpTester(this);
}

void MainWindow::on_pushButton_clicked()
{
  pTester->CloseConnection();
  pTester->InitConnection("127.0.0.1",23);
}

void MainWindow::on_pushButton_2_clicked()
{
    int  state = pTester->client->state();
    bool valid = pTester->client->isValid();
    if (valid && state==QAbstractSocket::ConnectedState)
    {
        QString qstr="write test";
        pTester->WriteTo(qstr);
    };
}
Записан
mutineer
Гость
« Ответ #1 : Апрель 14, 2011, 12:38 »

А что при этом читается из сокета?
Записан
o-henry
Гость
« Ответ #2 : Апрель 14, 2011, 13:08 »

А что при этом читается из сокета?
Когда я шлю из гипертерминала данные моему приложению - приложение  по  readyRead вычитывает из сокета то, что отправил гипертерминал.
Когда я из приложения отправляю данные гипертерминалу -  почему-то опять срабатывает readyRead, обрабатывая который я вычитываю то что я отправил.
Записан
kuzulis
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2812


Просмотр профиля
« Ответ #3 : Апрель 14, 2011, 13:55 »

Цитировать
Когда я из приложения отправляю данные гипертерминалу -  почему-то опять срабатывает readyRead, обрабатывая который я вычитываю то что я отправил.
Наверное потому что в терминале настроен эхо ответ.
И ни QTcpSocket ни readyRead здесь абсолютно ни при чем!
--
Ваш К.О.
Записан

ArchLinux x86_64 / Win10 64 bit
o-henry
Гость
« Ответ #4 : Апрель 14, 2011, 15:51 »

Цитировать
Наверное потому что в терминале настроен эхо ответ.
И ни QTcpSocket ни readyRead здесь абсолютно ни при чем!
Спасибо, похоже так и есть.   Шокированный
Взял в качестве сервера FortuneServer - эффект пропал.

Тогда следующий вопрос: как в гипертерминале отключить эхо ответ?

« Последнее редактирование: Апрель 14, 2011, 16:35 от o-henry » Записан
kuzulis
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2812


Просмотр профиля
« Ответ #5 : Апрель 15, 2011, 07:39 »

Никак, там telnet. (ИМХО).
Хотя, после подключения покопайтесь в настройках текущей активной сессии гипертерминала, может где есть галочка.
 
Но в любом случае ищите другую софтину для тестирования TCP/IP.
« Последнее редактирование: Апрель 15, 2011, 07:40 от kuzulis » Записан

ArchLinux x86_64 / Win10 64 bit
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


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