/*------------------------------------------------------------------------------ -- This file is a part of the SocExplorer Software -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS -- -- This program is free software; you can redistribute it and/or modify -- it under the terms of the GNU General Public License as published by -- the Free Software Foundation; either version 3 of the License, or -- (at your option) any later version. -- -- This program is distributed in the hope that it will be useful, -- but WITHOUT ANY WARRANTY; without even the implied warranty of -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -- GNU General Public License for more details. -- -- You should have received a copy of the GNU General Public License -- along with this program; if not, write to the Free Software -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -------------------------------------------------------------------------------*/ /*-- Author : Alexis Jeandet -- Mail : alexis.jeandet@member.fsf.org ----------------------------------------------------------------------------*/ #include "spwtcppacketserver.h" #include "ui_spwtcppacketserver.h" #include #include #include SpwTcpPacketServer::SpwTcpPacketServer(QWidget *parent) : QWidget(parent), ui(new Ui::SpwTcpPacketServer) { ui->setupUi(this); this->p_bridge = NULL; this->p_server = new QTcpServer(); this->incomingPacketParser = new IncomingPacketParser(); connect(this->ui->startServeQpb,SIGNAL(clicked(bool)),SLOT(toggleServer())); updateHostIP(); this->ui->PortLineEdit->setText("2200"); connect(this->p_server,SIGNAL(newConnection()),this,SLOT(newConnection())); resetStatististics(); connect( this->incomingPacketParser, SIGNAL(sendPacketUsingSpaceWire(QByteArray)), this, SLOT(sendSPWPacketUsingSpaceWire(QByteArray))); } SpwTcpPacketServer::~SpwTcpPacketServer() { delete ui; } void SpwTcpPacketServer::setBridge(abstractSpwBridge *bridge) { if(this->p_bridge!=NULL) { disconnect(this,SLOT(pushPacket(char*,int))); } this->p_bridge = bridge; connect(bridge,SIGNAL(pushPacketOverTCP(char*,int)),SLOT(pushPacket(char*,int))); } void SpwTcpPacketServer::pushPacket(char *packet, int size) { QByteArray data; char sizech[3]; data.append((char)0); sizech[0]=size & 0x0FF; sizech[1]=(size>>8) & 0x0FF; sizech[2]=(size>>16) & 0x0FF; data.append(sizech,3); data.append(packet,size); for(int i=0;istate()!=QAbstractSocket::ConnectedState) { connectedClients.removeAt(i); delete soc; } else { connectedClients.at(i)->write(data); onePacketTransmitted(); } } free(packet); } void SpwTcpPacketServer::toggleServer() { if(this->p_server->isListening()) { disconnectServer(); } else { connectServer(); } } void SpwTcpPacketServer::connectServer() { this->p_server->listen(QHostAddress::Any,this->ui->PortLineEdit->text().toInt()); this->ui->startServeQpb->setText("Stop Server"); resetStatististics(); } void SpwTcpPacketServer::disconnectServer() { this->ui->startServeQpb->setText("Start Server"); this->p_server->close(); } void SpwTcpPacketServer::setServerPort(qint32 port) { this->ui->PortLineEdit->setText(QString("%1").arg(port)); } void SpwTcpPacketServer::setServerSetIP(QString ip) { this->ui->IPLineEdit->setText(ip); } void SpwTcpPacketServer::newConnection() { QTcpSocket* soc=this->p_server->nextPendingConnection(); this->connectedClients.append(soc); this->ui->listWidget->addItem(this->connectedClients.last()->peerAddress().toString()); connect(soc,SIGNAL(readyRead()),this,SLOT(parseIncomingPacket())); } void SpwTcpPacketServer::parseIncomingPacket() { for(int i=0;istate()!=QAbstractSocket::ConnectedState) { connectedClients.removeAt(i); delete soc; } else { if(soc->bytesAvailable()!=0) { do { QByteArray data = soc->readAll(); incomingPacketParser->processIncomingQByteArray( data ); }while(soc->bytesAvailable()!=0); } } } } void SpwTcpPacketServer::sendSPWPacketUsingSpaceWire(QByteArray data) { onePacketReceived(); if(data[0]==(char)0) // Protocole = 0 => Host to SpaceWire packet transmission { int size = ( (unsigned char) data[1] ) * 256 * 256 + ( (unsigned char) data[2] ) * 256 + (unsigned char) data[3]; char* SPWpacket = (char*)malloc(size); if(SPWpacket!=NULL) { memcpy(SPWpacket,data.data()+4,size); // 4 bytes will be added later to the packet emit sendSPWPacket(SPWpacket,size); } else { //TODO print some message } } } void SpwTcpPacketServer::readReady() { for(int i=0;istate()!=QAbstractSocket::ConnectedState) { connectedClients.removeAt(i); delete soc; } else { if(soc->bytesAvailable()!=0) { do { QByteArray data = soc->readAll(); onePacketReceived(); if(data[0]==(char)0) // Protocole = 0 => Host to SpaceWire packet transmission { // TODO -> change heap allocation to stack risk of memory leak // if no slot conected to sendSPWPacket signal or segfault if more // than one receiver. int size = ( (unsigned char) data[1] ) * 256 * 256 + ( (unsigned char) data[2] ) * 256 + (unsigned char) data[3]; char* SPWpacket = (char*)malloc(size); if(SPWpacket!=NULL) { memcpy(SPWpacket,data.data()+4,size); // 4 bytes will be added later to the packet emit sendSPWPacket(SPWpacket,size); } else { //TODO print some message } } }while(soc->bytesAvailable()!=0); } } } } void SpwTcpPacketServer::resetStatististics() { receivedPackets = 0; transmittedPackets = 0; this->ui->receivedPacketsNumber->display( QString::number(receivedPackets) ); this->ui->transmittedPacketsNumber->display( QString::number(transmittedPackets) ); } void SpwTcpPacketServer::updateHostIP() { QList list = QNetworkInterface::allAddresses(); for(int nIter=0; nIterui->IPLineEdit->setText(list[nIter].toString()); } } void SpwTcpPacketServer::onePacketReceived() { receivedPackets = receivedPackets + 1; this->ui->receivedPacketsNumber->display( QString::number(receivedPackets) ); } void SpwTcpPacketServer::onePacketTransmitted() { transmittedPackets = transmittedPackets + 1; this->ui->transmittedPacketsNumber->display( QString::number(transmittedPackets) ); }