SocketTlsHandshake fails against server with self-signed certificate

Hi there,


I am currently trying to connect my expert advisor to a remote machine via the network functions SocketCreate, SocketConnect and secure it with SocketTlsHandshake. For that I created a self-signed certificate. Currently, the handshake fails with the expected error 5274 and I want to find out why that is.

The certificate I created has the following attributes (read out with openssl):

Certificate:
    Data:
        Version: 3 (0x2)
        Serial Number:
            f7:51:c0:bf:ad:5a:56:03
        Signature Algorithm: ecdsa-with-SHA256
        Issuer: C=CH, O=self-signed certificate, CN=self-signed certificate
        Validity
            Not Before: Jun  4 04:00:38 2026 GMT
            Not After : Jun  1 04:00:38 2036 GMT
        Subject: C=CH, O=self-signed certificate, CN=self-signed certificate
        Subject Public Key Info:
            Public Key Algorithm: id-ecPublicKey
                Public-Key: (384 bit)
                pub:
                    04:b2:aa:48:bf:5c:06:33:48:9b:6f:98:f4:16:cc:
                    43:99:90:fb:ad:5f:ea:e8:6e:c0:87:35:94:a0:91:
                    55:ed:ef:8b:34:44:7a:aa:2d:8d:3d:22:bf:1d:f9:
                    0e:61:e9:b2:3b:60:dd:2e:5b:aa:64:89:7b:ef:06:
                    1f:ca:54:c9:1a:f1:03:13:ae:ab:ab:c2:2a:95:b9:
                    c8:61:9b:dc:ad:88:28:21:09:74:4e:e8:a1:62:dd:
                    41:84:c4:f9:4c:1d:71
                ASN1 OID: secp384r1
                NIST CURVE: P-384
        X509v3 extensions:
            X509v3 Key Usage: 
                Digital Signature, Data Encipherment, Key Agreement
            X509v3 Extended Key Usage: 
                TLS Web Client Authentication, TLS Web Server Authentication
            X509v3 Basic Constraints: 
                CA:TRUE
            X509v3 Subject Alternative Name: 
                IP Address:127.0.0.1, IP Address:*another local ip address*
    Signature Algorithm: ecdsa-with-SHA256
    Signature Value:
        30:66:02:31:00:e5:0a:2c:a3:9f:5f:f4:dd:1f:34:0c:ce:92:
        78:d9:a8:43:66:32:2e:9b:ac:2b:22:44:c8:3b:87:3f:78:46:
        b3:ac:a6:29:77:9f:8c:b3:f0:f4:93:e5:01:ce:53:2b:6c:02:
        31:00:b2:4e:38:72:f9:f9:ea:c5:47:1e:f3:b9:88:db:6f:d3:
        e9:85:ab:db:47:b0:be:3e:29:88:d0:67:21:00:2b:42:0d:2a:
        cf:25:06:d7:62:ad:ab:cb:64:b4:ca:d3:09:06
-----BEGIN CERTIFICATE-----
*certificate information* 
-----END CERTIFICATE-----

I just basically copied how the google CA certificate looks like and added TLS authentication to the extended key usage. I then imported the certificate into the "Trusted Root Certification Authorities" certificate storage inside the Windows machine on which I run the MetaTrader5 instance.

My server runs on python, so I can see that the handshake fails because of an SSL error called "SSLV3_ALERT_ILLEGAL_PARAMETER", which is an error that was forwarded to python right over cpython directly from openssl, so the error does not happen inside the python code, but when openssl code is invoked. Another small remark is that if I try to connect to the python server using a python client, the handshake is successful, even when I'm connecting from a remote computer, so it has to be something in the implementation of the SocketTlsHandshake function.

Anyways, the certificate seems to have illegal parameters and I wanted to ask you guys if you know about the prerequisites of certificates in order for the expert advisor to be able to connect to the server. Is it maybe because it does not want to use CA certificates directly for authentication but rather a non-CA "server TLS certificate" and I got to have some kind of a certificate chain for it to work? Or are just some parameters inside the certificate given above missing? help.


Cheers,

tandoori

Hello again,

it seems like this topic is a bit of a dead spot in the community...

And unfortunately the error message I get from MT5 is not terribly helpful either. It is just error 5274, which is a generic handshake error, so I really do not get any insight as to what the certificate lacks in order to be accepted by MT5. Are there maybe any devs here, that can enlighten me? At the moment the only thing I could do is brute force through different settings for certificates and hope that at one point I get a certificate that fits the expectations, but since there are virtually thousands if not millions of combinations, I would like to circumvent that at all costs. Is there really nobody that can give a small clue as to where one might search for a solution?


Cheers,

tandoori

MT5 can only be as a socket client, you may need to create a socket server bridge with python or node before it goes to your app.

Did you try to connect to your server with TLS from a browser first? Make sure the browser is satisfied with your sertificate, only then ask questions about MQL5, and provide a code fragment.

Some time ago I generated a selfsigned serificate (by external tools, without any trials and errors) and used it for the algotrading book - it worked normally from a browser and from MQL5. Of course, now it's outdated and marked by browsers by red color, but technically should work.

MQL5 Book: Server component of web services based on the WebSocket protocol / Advanced language tools
MQL5 Book: Server component of web services based on the WebSocket protocol / Advanced language tools
  • www.mql5.com
To organize a common server component of all projects, we will create a separate folder Web inside MQL5/Experts/MQL5Book/p7/ . Ideally, it would be...

@Ebunoluwa Abimb Owodunni:

I run MT5 as a client. The server is on another machine and runs via Python. And I don't understand what you mean by a "socket server bridge". Do you mean a standard TCP connection? If yes, that is what I started out with via the SocketConnect function, which works perfectly fine.


@Stanislav Korotky:

Do you mean connect by browser as to "connect to a HTTPS site"? Because I just want to establish a TLS-encrypted connection to a general server, not an HTTPS-server via port 443. I did connect to the Python-server on the other machine succesfully. I did this from the same machine that MT5 runs on, but not via MT5 but by another Python shell (a client script). All of this worked fine, even the encryption, so I assume that the problem lies in MT5 not being able to validate my certificate. With the Python-client I can import the certificate from the general certificate store and then successfully connect to the server and encrypt the connection.

What kind of code fragment do you want? From the expert advisor? It would just be the two functions SocketConnect and SocketTlsHandshake run after each other, but I can provide that if you want.


Thanks for your replies, guys :)


Cheers,

tandoori

tandoori_mql #:

Do you mean connect by browser as to "connect to a HTTPS site"? Because I just want to establish a TLS-encrypted connection to a general server, not an HTTPS-server via port 443. I did connect to the Python-server on the other machine succesfully. I did this from the same machine that MT5 runs on, but not via MT5 but by another Python shell (a client script). All of this worked fine, even the encryption, so I assume that the problem lies in MT5 not being able to validate my certificate. With the Python-client I can import the certificate from the general certificate store and then successfully connect to the server and encrypt the connection.

What kind of code fragment do you want? From the expert advisor? It would just be the two functions SocketConnect and SocketTlsHandshake run after each other, but I can provide that if you want.


If you run a minimal web-server (powered by python or other publicly accepted engine, such as Node.js) with your TLS keys attached - can you connect to it by means of a browser? When you are paring 2 custom python scripts (client and server), this does not confirm standards. If it works, then - yes - we need to see your MQL5 code - I gave you a refernce for existing implementation which worked for me some time ago. But I'm not a python enthusiast, so can't help in this direction.

Hello again,

Stanislav Korotky #:

If you run a minimal web-server (powered by python or other publicly accepted engine, such as Node.js) with your TLS keys attached - can you connect to it by means of a browser? When you are paring 2 custom python scripts (client and server), this does not confirm standards. If it works, then - yes - we need to see your MQL5 code - I gave you a refernce for existing implementation which worked for me some time ago. But I'm not a python enthusiast, so can't help in this direction.

I did that with the additional effort of building my own CA, signing a certificate request for my server, then importing the CA certificate into the certificate store of the machine that has MT5 on it and then trying to connect and using the newly signed certificate for the server. I tried to connect with my Firefox to the minimal web server I ran with the built-in python http.server package. It did connect via https without complaining.


Now the expert advisor code that still fails with error 5274 on the MT5 side and with "ssl.SSLError: [SSL: SSLV3_ALERT_ILLEGAL_PARAMETER] sslv3 alert illegal parameter (_ssl.c:1032)" on the python side:

int OnInit() {
    uint sock = SocketCreate(SOCKET_DEFAULT);
    SocketConnect(sock, "10.10.10.10", 12345, 1000);
    SocketTlsHandshake(sock, "10.10.10.10");
    return INIT_SUCCEEDED;
} 

10.10.10.10 is the IP address that also appears in "X509v3 Subject Alternative Name" in the certificate and 12345 is the port number.

And I tried the STARTTLS message as described in the wiki page of the SocketTlsHandshake function but this only seems to be an option for SMTP connections and it fails with another error (python declines because of TLSv1) anyways.


Cheers, tandoori

tandoori_mql #:

Hello again,

I did that with the additional effort of building my own CA, signing a certificate request for my server, then importing the CA certificate into the certificate store of the machine that has MT5 on it and then trying to connect and using the newly signed certificate for the server. I tried to connect with my Firefox to the minimal web server I ran with the built-in python http.server package. It did connect via https without complaining.


Now the expert advisor code that still fails with error 5274 on the MT5 side and with "ssl.SSLError: [SSL: SSLV3_ALERT_ILLEGAL_PARAMETER] sslv3 alert illegal parameter (_ssl.c:1032)" on the python side:

10.10.10.10 is the IP address that also appears in "X509v3 Subject Alternative Name" in the certificate and 12345 is the port number.

And I tried the STARTTLS message as described in the wiki page of the SocketTlsHandshake function but this only seems to be an option for SMTP connections and it fails with another error (python declines because of TLSv1) anyways.


If it fails in python as well, then this is not an issue in MT5.

Please note, that I did not use certificates via importing them into the store, but attach them directly to the web-server, so I can't say if the store could somehow interfere while working with a custom certificate.

It would be better to handle errors on all steps, for example:

      handle = SocketCreate();
      timeout = t;
      TLS = scheme == "wss";
      if(handle != INVALID_HANDLE)
      {
         Print("Connecting to ", host, ":", port);
         if(SocketConnect(handle, host, port, timeout))
         {
            SocketTimeouts(handle, timeout, timeout);
          
            string subject, issuer, serial, thumbprint;
            datetime expiration;
            if(TLS)
            {
               if(!SocketTlsHandshake(handle, host))
               {
                  Print("TLS handshake error: ", _LastError);
                  TLS = false;
               }
               else
               {
                  Print("TLS enabled");
               }
               if(SocketTlsCertificate(handle, subject, issuer, serial, thumbprint, expiration))
               {
                  Print("TLS:");
                  Print("  Owner:      ", subject);
                  Print("  Issuer:     ", issuer);
                  Print("  Number:     ", serial);
                  Print("  Signature:  ", thumbprint);
                  Print("  Expiration: ", expiration);
               }
            }
         }
         else
         {
            Print("Can't connect: ", GetLastError());
         }
      }
      else
      {
         Print("Can't create socket: ", GetLastError());
      }

Currently it's not clear if you have a valid handle, and if it's really connected before the call to SocketTlsHandshake.

Also I'm not sure if the IP is actually operational - how did you acquire this exact IP?

Hi there,

first off: It did not fail in Python. As you suggested, I could connect to the python minimal web server with the self-signed certificate from a browser. I then tried to connect to the Python (not web- but MT5-) server that I want to connect to in the end but with another Python instance instead of via the MT5 expert advisor and this also works with TLS without any problem. The only time it fails is if I try to connect to the Python server with an MT5 expert advisor.

And I have a valid handle, since the Python server gave an SSL error, which must mean that the standard TCP connection was established successfully, but for your sake I made the same experiment with your modified code:

int OnInit() {
    uint handle = SocketCreate();
    uint timeout = 1000;
    string host = "10.10.10.10";
    uint port = 12345;
    bool TLS = true;
    if (handle != INVALID_HANDLE) {
        Print("Connecting to ", host, ":", port);
        if (SocketConnect(handle, host, port, timeout)) {
            SocketTimeouts(handle, timeout, timeout);
            string subject, issuer, serial, thumbprint;
            datetime expiration;
            if (TLS) {
                if(!SocketTlsHandshake(handle, host)) { 
                    Print("TLS handshake error: ", _LastError);
                    TLS = false;
                }
                else {
                    Print("TLS enabled");
                }
                if (SocketTlsCertificate(handle, subject, issuer, serial, thumbprint, expiration)) {
                    Print("TLS:");
                    Print("  Owner:      ", subject);
                    Print("  Issuer:     ", issuer);
                    Print("  Number:     ", serial);
                    Print("  Signature:  ", thumbprint);
                    Print("  Expiration: ", expiration);
                }
            }
        }
        else {
            Print("Can't connect: ", GetLastError());
        }
    }
    else {
        Print("Can't create socket: ", GetLastError());
    }
    return INIT_SUCCEEDED;
}

This code also gives back the same Python SSLV3_ALERT_ILLEGAL_PARAMETER error and the "experts" rider inside MT5 logs the following:

2026.10.04 16:38:49.493    test (EURUSD,M1)    Connecting to 10.10.10.10:12345
2026.10.04 16:38:49.501    test (EURUSD,M1)    TLS handshake error: 5274

And about the IP addresses: This is just an IP address out of the range of addresses reserved for private use (e.g. as in my case in my local network/LAN) and can be found under https://en.wikipedia.org/wiki/List_of_reserved_IP_addresses

Basically it's the same as the usual private LAN-network address range 192.168.0.0/16. I just configured my LAN so that it uses the range 10.0.0.0/8 (or, to be more precise, 10.10.10.0/24) instead of the standard from the sentence before which most routers use.

And here I would apply the same argument as above: If there would be any problem with the IP address, then the browser could not connect via https without any complaint, but this works.

About the certificate being imported into the store instead of directly attached to the server: First off, I could connect via browser, so this means that the certificate is accessible in the store. Second of all I would say that MT5 also uses this store (since I can't find a separate built-in store inside MT5).

To test this, I tried to connect to https://www.mql5.com:443 for fun and this worked as the log shows:

2026.10.04 17:02:26.785    test (EURUSD,M1)    Connecting to https://www.mql5.com:443
2026.10.04 17:02:27.109    test (EURUSD,M1)    TLS handshake error: 5274
2026.10.04 17:02:27.110    test (EURUSD,M1)    TLS:
2026.10.04 17:02:27.110    test (EURUSD,M1)      Owner:      /CN=*.mql5.com
2026.10.04 17:02:27.110    test (EURUSD,M1)      Issuer:     /C=US/O=DigiCert Inc/OU=www.digicert.com/CN=RapidSSL TLS ECC CA G1
2026.10.04 17:02:27.110    test (EURUSD,M1)      Number:     02:8d:32:95:51:7f:76:ec:ec:cc:a2:a1:e8:84:da:69
2026.10.04 17:02:27.110    test (EURUSD,M1)      Signature:  8afe3c3fa3ab2d02d112347ca46b49654bc375bf
2026.10.04 17:02:27.110    test (EURUSD,M1)      Expiration: 2026.10.26 23:59:59

Here the handshake fails for the reason that when you connect to port 443 the connection is automatically upgraded to TLS by SocketConnect(), which means that another handshake fails, but of course we then get the info of the certificate. So what this means is that MT5 is capable of connecting to the certificate store, since otherwise we could not connect via TLS, since the root certificate that signed the certificate of mql5.com is stored in the certificate store.

I in the meantime assume that not Python is the problem, but that the SocketTlsHandshake function uses legacy protocols? How else should a SSLV3 error happen? SSLV3 is deprecated since 2015, TLS1.0 and TLS1.1 since 2021 (https://en.wikipedia.org/wiki/Transport_Layer_Security#History_and_development), so the ssl module in Python, which uses openssl can not establish a connection with a client that "only speaks" SSLV3. And openssl also tries to use the most modern protocol, so I would say that there is no other possibility of why an SSLV3 error should happen, except when the MT5 client can not speak any more modern protocols than SSLV3. Could this be the problem? It would certainly fit the message "illegal parameter", since SSLV3 is illegal security-wise. I am almost ready to assume that since most website providers don't care too much about security and prefer many people being able to use their service, they just allow deprecated protocols like SSLV3 to be used by their clients and this is why you can connect MT5 to most websites but not to my Python server?

Cheers, tandoori

tandoori_mql #:

Hi there,

first off: It did not fail in Python. As you suggested, I could connect to the python minimal web server with the self-signed certificate from a browser. I then tried to connect to the Python (not web- but MT5-) server that I want to connect to in the end but with another Python instance instead of via the MT5 expert advisor and this also works with TLS without any problem. The only time it fails is if I try to connect to the Python server with an MT5 expert advisor.

And I have a valid handle, since the Python server gave an SSL error, which must mean that the standard TCP connection was established successfully, but for your sake I made the same experiment with your modified code:

This code also gives back the same Python SSLV3_ALERT_ILLEGAL_PARAMETER error and the "experts" rider inside MT5 logs the following:

2026.10.04 16:38:49.493    test (EURUSD,M1)    Connecting to 10.10.10.10:12345
2026.10.04 16:38:49.501    test (EURUSD,M1)    TLS handshake error: 5274

And about the IP addresses: This is just an IP address out of the range of addresses reserved for private use (e.g. as in my case in my local network/LAN) and can be found under https://en.wikipedia.org/wiki/List_of_reserved_IP_addresses

Basically it's the same as the usual private LAN-network address range 192.168.0.0/16. I just configured my LAN so that it uses the range 10.0.0.0/8 (or, to be more precise, 10.10.10.0/24) instead of the standard from the sentence before which most routers use.

And here I would apply the same argument as above: If there would be any problem with the IP address, then the browser could not connect via https without any complaint, but this works.

About the certificate being imported into the store instead of directly attached to the server: First off, I could connect via browser, so this means that the certificate is accessible in the store. Second of all I would say that MT5 also uses this store (since I can't find a separate built-in store inside MT5).

To test this, I tried to connect to https://www.mql5.com:443 for fun and this worked as the log shows:

2026.10.04 17:02:26.785    test (EURUSD,M1)    Connecting to https://www.mql5.com:443
2026.10.04 17:02:27.109    test (EURUSD,M1)    TLS handshake error: 5274
2026.10.04 17:02:27.110    test (EURUSD,M1)    TLS:
2026.10.04 17:02:27.110    test (EURUSD,M1)      Owner:      /CN=*.mql5.com
2026.10.04 17:02:27.110    test (EURUSD,M1)      Issuer:     /C=US/O=DigiCert Inc/OU=www.digicert.com/CN=RapidSSL TLS ECC CA G1
2026.10.04 17:02:27.110    test (EURUSD,M1)      Number:     02:8d:32:95:51:7f:76:ec:ec:cc:a2:a1:e8:84:da:69
2026.10.04 17:02:27.110    test (EURUSD,M1)      Signature:  8afe3c3fa3ab2d02d112347ca46b49654bc375bf
2026.10.04 17:02:27.110    test (EURUSD,M1)      Expiration: 2026.10.26 23:59:59

Here the handshake fails for the reason that when you connect to port 443 the connection is automatically upgraded to TLS by SocketConnect(), which means that another handshake fails, but of course we then get the info of the certificate. So what this means is that MT5 is capable of connecting to the certificate store, since otherwise we could not connect via TLS, since the root certificate that signed the certificate of mql5.com is stored in the certificate store.

That proves nothing actually, except the mql5.com certificate is trusted. It could be checked in different way without using the Windows certificate store at all.

I in the meantime assume that not Python is the problem, but that the SocketTlsHandshake function uses legacy protocols? How else should a SSLV3 error happen? SSLV3 is deprecated since 2015, TLS1.0 and TLS1.1 since 2021 (https://en.wikipedia.org/wiki/Transport_Layer_Security#History_and_development), so the ssl module in Python, which uses openssl can not establish a connection with a client that "only speaks" SSLV3. And openssl also tries to use the most modern protocol, so I would say that there is no other possibility of why an SSLV3 error should happen, except when the MT5 client can not speak any more modern protocols than SSLV3. Could this be the problem? It would certainly fit the message "illegal parameter", since SSLV3 is illegal security-wise. I am almost ready to assume that since most website providers don't care too much about security and prefer many people being able to use their service, they just allow deprecated protocols like SSLV3 to be used by their clients and this is why you can connect MT5 to most websites but not to my Python server?

Cheers, tandoori

SSLV3 in the error message is not about the protocol used, it's legacy nomenclature. If TLS is used it will still talk about SLLV3 in the error message.

You should check which protocol is used, or forced one to be sure, then verify that the algorithm you used for your certificate and the signature are fully compatible. (that's where an invalid parameter could appear for a given combination of protocol/encryption/signature).

Alain Verleyen #:

That proves nothing actually, except the mql5.com certificate is trusted. It could be checked in different way without using the Windows certificate store at all.

SSLV3 in the error message is not about the protocol used, it's legacy nomenclature. If TLS is used it will still talk about SLLV3 in the error message.

You should check which protocol is used, or forced one to be sure, then verify that the algorithm you used for your certificate and the signature are fully compatible. (that's where an invalid parameter could appear for a given combination of protocol/encryption/signature).

Hey,

yeah you're right with the first thing. That only proves that the certificate is acknowledged, not why. But does anyone know something about an internal certificate store of MT5? I mean how else should certificates be acknowledged than via MT5-internal mechanisms or via the certificate store of the OS?

And thanks a great deal for the tip with the legacy nomenclature. That brings us further forward, although this means that we are kind of at the beginning of the analysis again, but at least we are not digging in the wrong direction any more.

Do you have any idea of how to probe a client for his supported protocols? With Python I can not force single protocols any more (deprecated since 3.6) and therefore probing is uncomfortable here, since Python-wise the only thing I could imagine is to copy the ssl package and add logging to its handshake handling at the right places, since it does not seem to have internal logging by itself (https://stackoverflow.com/questions/26554106/python-3-how-to-log-ssl-handshake-errors-from-server-side).

Thanks and cheers,

tandoori