/* # Copyright (c) 2009 - OpenSLX Project, Computer Center University of Freiburg # # This program is free software distributed under the GPL version 2. # See http://openslx.org/COPYING # # If you have any feedback please consult http://openslx.org/feedback and # send your suggestions, praise, or complaints to feedback@openslx.org # # General information about OpenSLX can be found at http://openslx.org/ # ----------------------------------------------------------------------------- # src/net/SslServer.cpp # - provide QTcpServer-like behaviour for SSL # ----------------------------------------------------------------------------- */ #include "sslserver.h" #include #include #include "certmanager.h" SslServer::SslServer() { _tmr = startTimer(5123); //QSslSocket::setDefaultCiphers(QSslSocket::supportedCiphers()); } SslServer::~SslServer() { killTimer((_tmr)); } /** * Handle incomming connection. * @param socketDescriptor */ void SslServer::incomingConnection(int socketDescriptor) { QSslSocket *serverSocket = new QSslSocket(NULL); connect(serverSocket, SIGNAL(sslErrors(const QList &)), this, SLOT(sslErrors(const QList &))); QSslKey key; QSslCertificate cert; CertManager::getPrivateKeyAndCert("manager", key, cert); serverSocket->setPrivateKey(key); serverSocket->setLocalCertificate(cert); serverSocket->setPeerVerifyMode(QSslSocket::VerifyNone); serverSocket->setProtocol(QSsl::TlsV1SslV3); //printf("Keylen %d\n", serverSocket->privateKey().length()); if (serverSocket->setSocketDescriptor(socketDescriptor)) { // Once the connection is successfully encrypted, raise our newConnection event connect(serverSocket, SIGNAL(encrypted()), this, SIGNAL(newConnection())); serverSocket->startServerEncryption(); _pending.push_back(serverSocket); } else { serverSocket->deleteLater(); } } void SslServer::sslErrors(const QList & errors) { //qDebug("FIXME: SSL ERRORS on SERVER: %s", qPrintable(errors.begin()->errorString())); } void SslServer::timerEvent(QTimerEvent* event) { // Remove all sockets marked for deletion while (!_delete.isEmpty()) { QSslSocket *sock = _delete.takeFirst(); sock->blockSignals(true); sock->deleteLater(); } _delete = _pending; _pending.clear(); } bool SslServer::hasPendingConnections() const { for (QList::const_iterator it(_pending.begin()); it != _pending.end(); it++) { qDebug("State: %d - Encrypted: %d", (int)(*it)->state(), (*it)->isEncrypted()); if ((*it)->state() == QAbstractSocket::ConnectedState && (*it)->isEncrypted()) return true; } return false; } QTcpSocket* SslServer::nextPendingConnection() { for (QList::iterator it(_pending.begin()); it != _pending.end(); it++) { if ((*it)->state() == QAbstractSocket::ConnectedState && (*it)->isEncrypted()) { QSslSocket *sock = *it; QObject::disconnect(sock, SIGNAL(encrypted()), this, SIGNAL(newConnection())); _pending.removeAll(sock); _delete.removeAll(sock); return sock; } } for (QList::iterator it(_delete.begin()); it != _delete.end(); it++) { if ((*it)->state() == QAbstractSocket::ConnectedState && (*it)->isEncrypted()) { QSslSocket *sock = *it; QObject::disconnect(sock, SIGNAL(encrypted()), this, SIGNAL(newConnection())); _pending.removeAll(sock); _delete.removeAll(sock); return sock; } } return NULL; }