void streamLoop(qintptr socketDesc, QQueue<QByteArray> &queue, bool& streaming) { QTcpSocket* socket = new QTcpSocket(); // TCP_NODELAY + disable Nagle's algorithm socket->setSocketOption(QAbstractSocket::LowDelayOption, QVariant::fromValue(1)); // Internetwork control socket->setSocketOption(QAbstractSocket::TypeOfServiceOption, QVariant::fromValue(192)); socket->setSocketDescriptor(socketDesc); socket->readAll(); QByteArray ContentType = ("HTTP/1.1 200 OK\r\n" \ "Server: test\r\n" \ "Cache-Control: no-cache\r\n" \ "Cache-Control: private\r\n" \ "Connection: close\r\n"\ "Pragma: no-cache\r\n"\ "Content-Type: multipart/x-mixed-replace; boundary=--boundary\r\n\r\n"); socket->write(ContentType); while((socket->state() != QAbstractSocket::ClosingState || socket->state() != QAbstractSocket::UnconnectedState) && socket->state() == QAbstractSocket::ConnectedState && streaming) { if(queue.empty()) { // no new frame available continue; } // make sure that the queue doesn't grow too big or // the OOM killer will kick in if(queue.length() > 20) { queue.clear(); continue; } QByteArray boundary = ("--boundary\r\n" \ "Content-Type: image/jpeg\r\n" \ "Content-Length: "); QByteArray img = queue.dequeue(); boundary.append(QString::number(img.length())); boundary.append("\r\n\r\n"); socket->write(boundary); socket->waitForBytesWritten(); boundary.clear(); socket->write(img); socket->waitForBytesWritten(); img.clear(); } socket->flush(); socket->abort(); socket->deleteLater(); streaming = false; queue.clear(); return; }
void SatelliteServer::connected() { QTcpSocket *socket = mpTcpServer->nextPendingConnection(); socket->setSocketOption( QAbstractSocket::SendBufferSizeSocketOption, 1024 ); socket->setSocketOption( QAbstractSocket::ReceiveBufferSizeSocketOption, 1024 ); connect(socket, SIGNAL(readyRead()), mpClientsReadMapper, SLOT(map())); mpClientsReadMapper->setMapping(socket, static_cast<QObject*>(socket)); connect(socket, SIGNAL(disconnected()), mpClientsDisconnectMapper, SLOT(map())); mpClientsDisconnectMapper->setMapping(socket, static_cast<QObject*>(socket)); mClientConnections.append( socket ); #if SATELLITESERVER_DEBUG emit debug( QString("s:client connected, %1 clients active") .arg( mClientConnections.count() ).toLatin1() ); #endif }
void CGProxy::newConnection() { QTcpSocket* newClient = m_LocalServer->nextPendingConnection(); if(m_LocalSocket) { newClient->disconnectFromHost(); return; } while( !m_LocalPackets.empty( ) ) { delete m_LocalPackets.front( ); m_LocalPackets.pop_front( ); } while( !m_RemotePackets.empty( ) ) { delete m_RemotePackets.front( ); m_RemotePackets.pop_front( ); } while( !m_PacketBuffer.empty( ) ) { delete m_PacketBuffer.front( ); m_PacketBuffer.pop_front( ); } newClient->setSocketOption(QAbstractSocket::LowDelayOption, 1); m_TotalPacketsReceivedFromLocal = 0; m_TotalPacketsReceivedFromRemote = 0; m_LastConnectionAttemptTime = 0; m_GameIsReliable = false; m_GameStarted = false; m_LeaveGameSent = false; m_ActionReceived = false; m_Synchronized = true; m_ReconnectPort = 0; m_PID = 255; m_ChatPID = 255; m_ReconnectKey = 0; m_NumEmptyActions = 0; m_NumEmptyActionsUsed = 0; m_LastAckTime = 0; m_LastActionTime = 0; m_LocalSocket = newClient; connect(m_LocalSocket, SIGNAL(disconnected()), this, SLOT(localDisconnected())); connect(m_LocalSocket, SIGNAL(disconnected()), m_LocalSocket, SLOT(deleteLater())); connect(m_LocalSocket, SIGNAL(readyRead()), this, SLOT(readLocalPackets())); }
QByteArray BtQt::sendTrackerRequest(BtTrackerRequest const &req, QUrl trackerUrl) { if(trackerUrl.scheme() != "http") { /* There may be "udp" or "https" or other schemes, * but not supported now */ qDebug() << "Request to announce" << trackerUrl; qDebug() << "Protocol not supported!"; return QByteArray(); } /* For the reason that QUrl has used RFC3986 instead of RFC 1738, * I have to emulate an HTTP GET request using tcp socket. */ QTcpSocket socket; QString host = trackerUrl.host(); quint16 port = trackerUrl.port(80); #ifndef QT_NO_DEBUG qDebug() << "Host: " << host; qDebug() << "Port: " << port; #endif // QT_NO_DEBUG /* *QString host = trackerUrl.toEncoded(QUrl::RemoveScheme | QUrl::RemovePath * | QUrl::RemoveAuthority); */ socket.connectToHost(host, port); if(!socket.waitForConnected(1000)) { qDebug() << "Can not establish tcp connection to" << host + ":" + QString::number(port); throw -1; } socket.setSocketOption(QAbstractSocket::KeepAliveOption, 1); /* HTTP 1.1 header, for more information please go to RFC2616 */ QByteArray header; header.append("HOST: " + host + ":" + QString::number(port) + "\r\n"); header.append("User-Agent: " + BtQt::application + " " + BtQt::version + "\r\n"); header.append("Accept: */*\r\n"); header.append("Connection: Keep-Alive\r\n"); header.append("\r\n"); QByteArray string; if(trackerUrl.hasQuery()) { string = "GET " + trackerUrl.toEncoded(QUrl::RemoveScheme | QUrl::RemoveAuthority) + '&' + req.toRequestData() + " HTTP/1.1\r\n"; } else { string = "GET " + trackerUrl.toEncoded(QUrl::RemoveScheme | QUrl::RemoveAuthority) + '?' + req.toRequestData() + " HTTP/1.1\r\n"; } #ifndef QT_NO_DEBUG qDebug() << "Header: " << header; qDebug() << "String: " << string; #endif // QT_NO_DEBUG socket.write(string + header); if(!socket.waitForReadyRead(1000)) { qDebug() << "There were some error occured or possibly time out! Can not get reply!"; throw -1; } QByteArray trackerReply = socket.readAll(); if(trackerReply.isEmpty()) { qDebug() << "Warnning! We got an empty reply!"; } /* Get the reply data */ int replyIdx = trackerReply.indexOf("\r\n\r\n") + 4; return trackerReply.mid(replyIdx); }