如何在Qt上使用TLS协议
How to use the TLS protocol on Qt?
请给出服务器端使用TLS的示例。
现在我有以下代码:
#include <QCoreApplication>
#include "server.h"
int main(int argc, char *argv[]) {
QCoreApplication a(argc, argv);
Server h;
return a.exec();
}
///////////////////////////////////////
#ifndef SERVER_H
#define SERVER_H
#include <QTcpServer>
class Server : public QTcpServer {
public:
Server();
void incomingConnection(int);
};
#endif // SERVER_H
///////////////////////////////////////////
#include "server.h"
#include <QSslSocket>
#include <QSslCertificate>
Server::Server() {
if (!listen(QHostAddress::Any, 80)) {
//error
}
}
void Server::incomingConnection(int d) {
QSslSocket * socket = new QSslSocket();
if(socket->setSocketDescriptor(d)) {
QString c, k;
c = "site.crt";
k = "site.key";
socket->setLocalCertificate(c);
socket->setPrivateKey(k);
socket->startServerEncryption();
if(socket->waitForEncrypted()) {
if(socket->waitForReadyRead()) {
socket->write(socket->readAll());
socket->waitForBytesWritten();
socket->disconnectFromHost();
if(socket->state() == QTcpSocket::UnconnectedState) {
socket->waitForDisconnected();
}
socket->close();
socket->deleteLater();
}
else {
delete socket;
}
}
else {
delete socket;
}
}
}
如何将其更改为先使用协议TLS,然后使用SSL?
常见的任务是编写一个支持SNI的服务器。
下面是一个使用服务器的SSL或TLS服务器示例。密钥和服务器。CRT文件加密:
#include <QtNetwork>
#include <QMessageBox>
class server : public QTcpServer
{
Q_OBJECT
public:
explicit server(QObject *parent = 0);
~server();
QSslSocket server_socket;
public slots:
void tcpReady();
void encrypted();
void sslError( QList<QSslError> errors );
bool start_listen(int port_no);
protected:
void incomingConnection(qintptr descriptor );
};
server::server(QObject *parent) :
QTcpServer(parent)
{
server_socket.setProtocol(QSsl::AnyProtocol);
QByteArray key;
QByteArray cert;
QFile file_key("server.key");
if(file_key.open(QIODevice::ReadOnly))
{
key = file_key.readAll();
file_key.close();
}
else
{
qDebug() << file_key.errorString();
}
QFile file_cert("server.crt");
if(file_cert.open(QIODevice::ReadOnly))
{
cert = file_cert.readAll();
file_cert.close();
}
else
{
qDebug() << file_cert.errorString();
}
QSslKey ssl_key(key, QSsl::Rsa,QSsl::Pem,QSsl::PrivateKey,"server");
QSslCertificate ssl_cert(cert);
server_socket.addCaCertificate(ssl_cert);
server_socket.setLocalCertificate(ssl_cert);
server_socket.setPrivateKey(ssl_key);
connect( &server_socket, SIGNAL(sslErrors(QList<QSslError>)),
this, SLOT(sslError(QList<QSslError>)) );
connect(&server_socket,SIGNAL(encrypted()),this,SLOT(encrypted()));
server_socket.setSocketOption(QAbstractSocket::KeepAliveOption, true );
}
server::~server()
{
server_socket.disconnectFromHost();
server_socket.waitForDisconnected();
}
void server::tcpReady()
{
QByteArray array = server_socket.read( server_socket.bytesAvailable() );
//...
}
void server::encrypted()
{
connect( &server_socket, SIGNAL(readyRead()),
this, SLOT(tcpReady()) );
emit connection_established();
}
void server::sslError(QList<QSslError> errors)
{
QString erroStr="";
foreach (const QSslError &e, errors)
erroStr.append(e.errorString()).append("n");
QMessageBox::warning( (QWidget *)this->parent(), tr("Error"),erroStr );
server_socket.ignoreSslErrors();
}
bool server::start_listen(int port_no)
{
if( !this->listen( QHostAddress::Any, port_no ) )
{
QMessageBox::warning( (QWidget *)this->parent(), tr("Error!"), tr("Cannot listen to port %1").arg(port_no) );
}
else
return true;
}
void server::incomingConnection(qintptr descriptor)
{
if(server_socket.state()!=QAbstractSocket::UnconnectedState)
return;
if( !server_socket.setSocketDescriptor( descriptor ) )
{
QMessageBox::warning( (QWidget *)this->parent(), tr("Error!"), tr("Socket error!") );
return;
}
else
{
server_socket.startServerEncryption();
}
}
可以设置协议为QSsl::SslV3
或QSsl::TlsV1
,只接受SSL或TLS连接。
相关文章:
- 如何在cpp.中使用协议缓冲区存储大缓冲区/数组(char/int)
- 如何使用url确定网站协议
- OpenSSL TLS服务器-使用客户端证书白名单
- MSYS2 MinGW程序包中缺少grpc_cpp_plugin协议
- Websocket++ 错误:收到错误handle_transport_init TLS 握手失败
- 用CMake构建C++协议
- 使用 OpenSSL 从内存中读取原始 SSL/TLS 证书
- 从原始字节解码协议缓冲区(以 C++为单位)
- GRPC C++ TLS 客户端 grpc::SslCredentials() 方法不返回
- OpenSSL C API:如何在程序exec()之后恢复TLS连接?
- 来自带有mbedtls TLS的Mongoose Web服务器的错误消息
- 如何使用ZeroMQ为协议缓冲区编写自己的RPC实现
- 协议缓冲区字符串字段的文本编码
- 如何使用librdkafka设置明文协议(无SASL)的用户名和密码?
- 构建使用协议缓冲区(不含 APK)的 Android 可执行 gRPC 服务器
- 用于处理多个通信协议处理的设计类
- 无法使用 ReadBinaryProto Tensorflow 加载协议缓冲区
- 协议缓冲区的静态链接会导致与现有符号冲突
- 协议缓冲区ParseFromString不检查消息结尾
- 如何在Qt上使用TLS协议