尝试通过SSL套接字将服务器与客户端连接时出现问题

时间:2019-06-04 09:00:28

标签: python openssl

我正在尝试通过SSL连接服务器和客户端,我已经能够通过不安全的套接字来做到这一点,但是现在我添加了SSL,我想我正在简化握手过程。我的服务器正常加载,但是加载客户端时出现错误:

[X509:KEY_VALUES_MISMATCH]键值不匹配(_ssl.c:3845)

我已经尝试过切换一些加载到python脚本中的文件,但是发现一些更简单的解决方案无法正常工作。我觉得我已经很近了,但是我做错了事。

这些是bash脚本,先加载openSSL,然后再加载python脚本:

startServer.sh

#!/bin/bash

BOLD=$(tput bold)
CLEAR=$(tput sgr0)

echo -e "${BOLD}Generating RSA AES-256 Private Key for Root Certificate Authority${CLEAR}"
openssl genrsa -aes256 -out root.key 4096

echo -e "${BOLD}Generating Certificate for Root Certificate Authority${CLEAR}"
openssl req -x509 -new -nodes -key root.key -sha256 -days 1825 -out root.pem

echo -e "${BOLD}Generating RSA Private Key for Server Certificate${CLEAR}"
openssl genrsa -out server.key 4096

echo -e "${BOLD}Generating Certificate Signing Request for Server Certificate${CLEAR}"
openssl req -new -key server.key -out server.csr

echo -e "${BOLD}Generating Certificate for Server Certificate${CLEAR}"
openssl x509 -req -in server.csr -CA root.pem -CAkey root.key -CAcreateserial -out server.crt -days 1825 -sha256 -extfile server.ext

openssl verify -verbose -CAfile root.pem server.crt

python3 socketserv.py "$@"

startClient.sh

#!/bin/bash

BOLD=$(tput bold)
CLEAR=$(tput sgr0)

echo -e "${BOLD}Generating RSA Private Key for Client Certificate${CLEAR}"
openssl genrsa -out client.key 4096

echo -e "${BOLD}Generating Certificate Signing Request for Client Certificate${CLEAR}"
openssl req -new -key client.key -out client.csr

echo -e "${BOLD}Generating Certificate for Client Certificate${CLEAR}"
openssl x509 -req -in client.csr -CA root.pem -CAkey root.key -CAcreateserial -out client.crt -days 1825 -sha256

openssl verify -verbose -CAfile root.pem client.crt

python3 socketclient.py "$@"

这是来自服务器和客户端python脚本的一些代码,适用于SSL握手。

socketServer.py

def Main():
#attempts to connect through given port
    try:
        build_exe_options = {"include_files":[(requests.certs.where(),'cacert.pem')]}
        inputArgs = sys.argv[1:]
    except Exception as e:
        print(e)
        exit()
    try:
        host = "" 
        port = int(inputArgs[0])
        server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
        server_socket.bind((host, port))
    #if port does not work an exception is thrown and program exits
    except Exception as e:
        print(e)
        print("Error, try again")
        exit()
    print("socket binded to post", port) 
    # put the socket into listening mode 
    server_socket.listen(10)
    # a forever loop until client wants to exit
    while True: 
        # establish connection with client 
        client, fromaddr = server_socket.accept()
        secure_sock = ssl.wrap_socket(client, server_side=True, ca_certs = "client.crt", certfile="server.crt", keyfile="server.key", cert_reqs=ssl.CERT_REQUIRED,
                           ssl_version=ssl.PROTOCOL_TLSv1_2)
        print(repr(secure_sock.getpeername()))
        print(secure_sock.cipher())
        print(pprint.pformat(secure_sock.getpeercert()))
        cert = secure_sock.getpeercert()
        print(cert)

        # verify client
        if not cert or ('commonName', 'test') not in cert['subject'][3]: raise Exception("ERROR")

        print('Connected to :', fromaddr[0], ':', fromaddr[1])
        # Start a new thread and return its identifier 
        start_new_thread(threaded, (client,))
    server_socket.close()

socketClient.py

def Main():
    try:
        inputArgs = sys.argv[1:]
        host = inputArgs[0]  # The server's hostname or IP address
        port = int(inputArgs[1])   # The port used by the server
        s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
        s.setblocking(1);
        # connect to server on local computer 
        s.connect((host,port))
        context = ssl.SSLContext(ssl.PROTOCOL_TLSv1_2)
        context.verify_mode = ssl.CERT_REQUIRED
        context.load_verify_locations('server.crt')
        context.load_cert_chain(certfile="server.crt", keyfile="client.key")

        if ssl.HAS_SNI:
            secure_sock = context.wrap_socket(s, server_side=False, server_hostname=host)
        else:
            secure_sock = context.wrap_socket(s, server_side=False)
        cert = secure_sock.getpeercert()
        print (cert)
        if not cert or ('commonName', 'test') not in cert['subject'][3]: raise Exception("ERROR")
        s = secure_sock
    #if port does not work an exception is thrown and program exits
    except Exception as e:
        print(e)
        exit()

服务器回溯: https://imgur.com/mMmNVaL

客户端错误: https://imgur.com/L3CQm5F

0 个答案:

没有答案