wolfssl
wolfssl copied to clipboard
Can't build ECH example on M1 Mac
Version
5.6.3
Description
Trying to make https://wolfssl.com/encrypted-client-hello-ech-now-supported-wolfssl/
this work, by compiling code from https://gist.github.com/jpbland1/ad46617fcc40934b252ce031c7aa5969
on M1 Mac.
After building the wolfssl lib by using
./configure --host=aarch64-apple-darwin
make
sudo make install
then ran
gcc ech_cloudflare.c
gave these errors:
ld: Undefined symbols:
_wolfSSL_CTX_UseSNI, referenced from:
_main in ech-f9216f.o
_wolfSSL_CTX_free, referenced from:
_main in ech-f9216f.o
_wolfSSL_CTX_load_verify_locations, referenced from:
_main in ech-f9216f.o
_wolfSSL_CTX_new, referenced from:
_main in ech-f9216f.o
_wolfSSL_Cleanup, referenced from:
_main in ech-f9216f.o
_wolfSSL_GetEchConfigs, referenced from:
_main in ech-f9216f.o
_wolfSSL_Init, referenced from:
_main in ech-f9216f.o
_wolfSSL_SetEchConfigs, referenced from:
_main in ech-f9216f.o
_wolfSSL_connect, referenced from:
_main in ech-f9216f.o
_main in ech-f9216f.o
_wolfSSL_free, referenced from:
_main in ech-f9216f.o
_main in ech-f9216f.o
_wolfSSL_get_error, referenced from:
_main in ech-f9216f.o
_main in ech-f9216f.o
_main in ech-f9216f.o
_wolfSSL_new, referenced from:
_main in ech-f9216f.o
_main in ech-f9216f.o
_wolfSSL_read, referenced from:
_main in ech-f9216f.o
_wolfSSL_set_fd, referenced from:
_main in ech-f9216f.o
_main in ech-f9216f.o
_wolfSSL_write, referenced from:
_main in ech-f9216f.o
_wolfTLSv1_3_client_method, referenced from:
_main in ech-f9216f.o
clang: error: linker command failed with exit code 1 (use -v to see invocation)
Are there any other steps to take before building this ECH example or the code from the gist need an update? Thx for the help!
Hi @FrontMage ,
Thanks for reaching out. My name is Anthony Hu and I am a member of the wolfSSL team.
I see a few things that might need to change. You'll need to enable ECH in your configure command line. Please add --enable-ech
. For your build of the ech_cloudflare.c
example, you'll need to use -I
to specify where the include directory is installed, -L
to specify where the wolfSSL library is installed -lwolfssl
to specify that the executable should be linked to the wolfSSL library.
@jpbland1 was the author of that gist, so I will assign this to him to see if he has any further suggestions.
Warm regards, Anthony
Hi, thx for the help!
I added --enable-ech
to the configure then rebuilt and reinstalled wolfssl, then using gcc ech_cloudflare.c -L/usr/local/lib -I/usr/local/include
outputs:
ld: Undefined symbols:
_wolfSSL_CTX_UseSNI, referenced from:
_main in ech-85ee66.o
_wolfSSL_CTX_free, referenced from:
_main in ech-85ee66.o
_wolfSSL_CTX_load_verify_locations, referenced from:
_main in ech-85ee66.o
_wolfSSL_CTX_new, referenced from:
_main in ech-85ee66.o
_wolfSSL_Cleanup, referenced from:
_main in ech-85ee66.o
_wolfSSL_GetEchConfigs, referenced from:
_main in ech-85ee66.o
_wolfSSL_Init, referenced from:
_main in ech-85ee66.o
_wolfSSL_SetEchConfigs, referenced from:
_main in ech-85ee66.o
_wolfSSL_connect, referenced from:
_main in ech-85ee66.o
_main in ech-85ee66.o
_wolfSSL_free, referenced from:
_main in ech-85ee66.o
_main in ech-85ee66.o
_wolfSSL_get_error, referenced from:
_main in ech-85ee66.o
_main in ech-85ee66.o
_main in ech-85ee66.o
_wolfSSL_new, referenced from:
_main in ech-85ee66.o
_main in ech-85ee66.o
_wolfSSL_read, referenced from:
_main in ech-85ee66.o
_wolfSSL_set_fd, referenced from:
_main in ech-85ee66.o
_main in ech-85ee66.o
_wolfSSL_write, referenced from:
_main in ech-85ee66.o
_wolfTLSv1_3_client_method, referenced from:
_main in ech-85ee66.o
clang: error: linker command failed with exit code 1 (use -v to see invocation)
and my installed path are
ls /usr/local/include
wolfssl
ls /usr/local/lib
docker libwolfssl.40.dylib libwolfssl.dylib libwolfssl.la pkgconfig
Hi,
Thanks for your quick work and response. You might also need to run sudo ldconfig
; its required on other POSIX systems; not sure about Mac. Also, you might have to set the DYLD_LIBRARY_PATH
environment variable.
Can you please tell me a bit about yourself and your project? For example:
- What are your goals and what are you trying to accomplish?
- Is this for personal, professional or academic interest?
- Is this work associated with any organization or institution?
Any information would be helpful so that we can prioritize this issue. Warm regards, Anthony
OK, mac does not have ldconfig and DYLD_LIBRARY_PATH=/usr/local/lib
does not work, I'll try to redo this on a Linux machine.
My goal is to see if ECH works on wolfssl and to integrate it into our product, our company is routers and we would like our router manager login and other APIs are protected by ECH. To do this I need to make a version of curl that supports ECH, which then requires either a openssl or wolfssl that supports ECH.
Hi @FrontMage ,
Yes, please do try on Linux.
As this is a commercial project, might I suggest you reach out to us a [email protected] where we can provide free pre-sales support. If you choose to do so, please include a reference to this github issue. I will now close this ticket and await any further responses at [email protected].
Warm regards, Anthony
Hi @FrontMage ,
I still don't see where you are indicating use of libwolfssl in your gcc call: gcc ech_cloudflare.c
. Can you try adding -lwolfssl
?
The typical way to build an application with wolfSSL:
./autogen.sh
./configure [--enable-args]
make
sudo make installl
(sudo ldconfig) if Linux
gcc -lwolfssl myapp.c
Make sure your my app.c includes wolfssl/options.h
at the top then wolfssl/wolfcrypt/settings.h
. See FAQ 1: https://www.wolfssl.com/docs/frequently-asked-questions-faq/#How_do_I_manage_the_build_configuration_for_wolfSSL?
Thanks, David Garske, wolfSSL
@dgarske Oh wow, this makes it working!
gcc ech.c -L/usr/local/lib -I/usr/local/include/wolfssl -lwolfssl
Thx!! But the ssl hello seems failed with
-1 -188
wolfSSL error: Error wolfSSL_connect
Hi @FrontMage ,
The error ASN_NO_SIGNER_E = -188, /* ASN no signer to confirm failure */
indicates you do not have a CA loaded to validate the peer. If you would like to skip certificate root of trust checking then add something like: wolfSSL_CTX_set_verify(ctx, WOLFSSL_VERIFY_NONE, NULL);
We at wolfSSL default to requiring the peer's certificate to be validated (unlike openssl), and require it be disabled purposefully in code.
Thanks, David Garske, wolfSSL
10 /* Connect wolfssl to the socket, server, then send message */
9 wolfSSL_set_fd(ssl, sockfd);
8 wolfSSL_CTX_set_verify(ctx, WOLFSSL_VERIFY_NONE, NULL);
7
6 /* this connect will send a grease ech and get the retry configs back */
5 ret = wolfSSL_connect(ssl);
4
3 if (ret != SSL_SUCCESS) {
2 printf( "%d %d\n", ret, wolfSSL_get_error( ssl, ret ) );
1 err_sys("Error wolfSSL_connect");
92 }
Hi, I've added wolfSSL_CTX_set_verify(ctx, WOLFSSL_VERIFY_NONE, NULL);
but it does not seem to help, the error came from this line ret = wolfSSL_connect(ssl);
, so maybe I think it's due to de server does no respond the ECH msg correctly?
Hi @FrontMage ,
You did not properly set the verify callback option. Either use wolfSSL_set_verify(ssl...
or set it before the call to wolfSSL_new(ctx)
. You set it at the WOLFSSL_CTX after the creation of the object, so it is still using the defaults.
Thanks, David Garske, wolfSSL
Indeed my problem, after adding it before the ctx was created, I got
-1 -308
wolfSSL error: Error wolfSSL_connect
41 SOCKET_ERROR_E = -308, /* error state on socket */
So there is a server connection error to 162.159.137.85
, and I can't ping to it.
This is the server from the gist code, so currently the testing server is down?
Hi @FrontMage ,
That's a socket error SOCKET_ERROR_E = -308, /* error state on socket */
. It means the peer closed the connection. You can enable debugging to see what happened. Add --enable-debug
and make sure you call wolfSSL_Debugging_ON();
. This will print a bunch of logs to stderr. I suspect its is related to the ECH.
Thanks, David Garske, wolfSSL
Where to put --enable-debug
?
I did gcc ech.c -L/usr/local/lib -I/usr/local/include/wolfssl -lwolfssl && ./a.out --enable-debug
and added wolfSSL_Debugging_ON()
then the error becames
-1 -313
wolfSSL error: Error wolfSSL_connect
Hi @FrontMage ,
You add it when building the wolfSSL library. So in your example above use ./configure --host=aarch64-apple-darwin --enable-debug
. The wolfSSL_Debugging_ON()
API comes from logging.c, so you might need to add the include #include <wolfssl/wolfcrypt/logging.h>
.
Thanks, David Garske, wolfSSL
wolfSSL Entering wolfSSL_free
Free'ing client ssl
wolfSSL Entering ClientSessionToSession
wolfSSL Entering wolfSSL_FreeSession
wolfSSL_FreeSession full free
CTX ref count not 0 yet, no free
wolfSSL Leaving wolfSSL_free, return 0
wolfSSL Entering wolfSSL_new
wolfSSL Entering ReinitSSL
wolfSSL Entering SetSSL_CTX
wolfSSL Entering wolfSSL_NewSession
wolfSSL Leaving wolfSSL_new, return 0
wolfSSL Entering wolfSSL_set_fd
wolfSSL Entering wolfSSL_set_read_fd
wolfSSL Leaving wolfSSL_set_read_fd, return 1
wolfSSL Entering wolfSSL_set_write_fd
wolfSSL Leaving wolfSSL_set_write_fd, return 1
wolfSSL Entering wolfSSL_connect
wolfSSL Entering ReinitSSL
wolfSSL Entering SendTls13ClientHello
Adding signature algorithms extension
Adding supported versions extension
wolfSSL Entering EccMakeKey
wolfSSL Leaving EccMakeKey, return 0
growing output buffer
Key Share extension to write
Supported Versions extension to write
Signature Algorithms extension to write
Supported Groups extension to write
Encrypt-Then-Mac extension to write
SNI extension to write
TLSX_ECH_Write
Key Share extension to write
Supported Versions extension to write
Signature Algorithms extension to write
Supported Groups extension to write
Encrypt-Then-Mac extension to write
SNI extension to write
TLSX_ECH_Write
Shrinking output buffer
wolfSSL Leaving SendTls13ClientHello, return 0
connect state: CLIENT_HELLO_SENT
growing input buffer
received record layer msg
got HANDSHAKE
wolfSSL Entering wolfSSL_get_options
wolfSSL Entering DoTls13HandShakeMsg
wolfSSL Entering DoTls13HandShakeMsgType
processing server hello
wolfSSL Entering DoTls13ServerHello
HelloRetryRequest format
Supported Versions extension received
Skipping Supported Versions - already processed
Key Share extension received
TLSX_ECH_Parse
wolfSSL Entering VerifyClientSuite
wolfSSL Leaving DoTls13ServerHello, return 0
wolfSSL Leaving DoTls13HandShakeMsgType(), return 0
wolfSSL Leaving DoTls13HandShakeMsg, return 0
Shrinking input buffer
wolfSSL Entering wolfSSL_connect_TLSv13
wolfSSL Entering ReinitSSL
connect state: HELLO_AGAIN
wolfSSL Entering SendTls13ClientHello
Adding signature algorithms extension
Adding supported versions extension
growing output buffer
Supported Versions extension to write
Key Share extension to write
Signature Algorithms extension to write
Supported Groups extension to write
Encrypt-Then-Mac extension to write
SNI extension to write
TLSX_ECH_Write
Supported Versions extension to write
Key Share extension to write
Signature Algorithms extension to write
Supported Groups extension to write
Encrypt-Then-Mac extension to write
SNI extension to write
TLSX_ECH_Write
Shrinking output buffer
wolfSSL Leaving SendTls13ClientHello, return 0
connect state: HELLO_AGAIN_REPLY
received record layer msg
got CHANGE CIPHER SPEC
received record layer msg
got ALERT!
Alert type: illegal_parameter
wolfSSL error occurred, error = 47
wolfSSL error occurred, error = -313
wolfSSL Entering wolfSSL_get_error
wolfSSL Leaving wolfSSL_get_error, return -313
-1 -313
wolfSSL error: Error wolfSSL_connect
Hi @FrontMage ,
Can you share your full example so we can try to reproduce?
@jpbland1 can you review this?
#include <wolfssl/options.h>
#include <wolfssl/ssl.h>
#include <wolfssl/test.h>
#include <errno.h>
#define SERV_PORT 443
int main()
{
int ret;
byte rd_buf[512];
int sockfd;
WOLFSSL_CTX* ctx;
WOLFSSL* ssl;
WOLFSSL_METHOD* method;
struct sockaddr_in servAddr;
const char message[] =
"GET /cdn-cgi/trace/ HTTP/1.1\r\n"
"Host: crypto.cloudflare.com\r\n"
"User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:105.0) Gecko/20100101 Firefox/105.0\r\n"
"Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8\r\n"
"Accept-Language: en-US,en;q=0.5\r\n"
"Referer: https://www.google.com/\r\n"
"DNT: 1\r\n"
"Connection: keep-alive\r\n"
"Upgrade-Insecure-Requests: 1\r\n"
"Sec-Fetch-Dest: document\r\n"
"Sec-Fetch-Mode: navigate\r\n"
"Sec-Fetch-Site: cross-site\r\n"
"Pragma: no-cache\r\n"
"Cache-Control: no-cache\r\n"
"\r\n";
const char ip_string[] = "162.159.137.85";
uint8_t ech_configs[72];
uint32_t ech_configs_len = 72;
/* this first tls connection is only used to get the retry configs */
/* these configs can also be retrieved from DNS */
/* create and set up socket */
sockfd = socket(AF_INET, SOCK_STREAM, 0);
memset(&servAddr, 0, sizeof(servAddr));
servAddr.sin_family = AF_INET;
servAddr.sin_port = htons(SERV_PORT);
// set the ip string to the cloudflare server
servAddr.sin_addr.s_addr = inet_addr( ip_string );
/* connect to socket */
connect(sockfd, (struct sockaddr *) &servAddr, sizeof(servAddr));
/* initialize wolfssl library */
wolfSSL_Init();
printf("1\n");
method = wolfTLSv1_3_client_method(); /* use TLS v1.3 */
/* make new ssl context */
if ( (ctx = wolfSSL_CTX_new(method)) == NULL) {
err_sys("wolfSSL_CTX_new error");
}
printf("2\n");
/* set the server name we want to connect to */
ret = wolfSSL_CTX_UseSNI( ctx, WOLFSSL_SNI_HOST_NAME, "crypto.cloudflare.com", strlen("crypto.cloudflare.com") );
if ( ret != WOLFSSL_SUCCESS ) {
printf( "%d", ret );
err_sys("wolfSSL_CTX_UseSNI error");
}
printf("3\n");
wolfSSL_CTX_set_verify(ctx, WOLFSSL_VERIFY_NONE, NULL);
wolfSSL_Debugging_ON();
/* make new wolfSSL struct */
if ( (ssl = wolfSSL_new(ctx)) == NULL) {
err_sys("wolfSSL_new error");
}
/* Add cert to ctx */
if (wolfSSL_CTX_load_verify_locations(ctx, "cert.pem", 0) !=
SSL_SUCCESS) {
err_sys("Error loading ca-cert.pem");
}
printf("4\n");
/* Connect wolfssl to the socket, server, then send message */
wolfSSL_set_fd(ssl, sockfd);
/* this connect will send a grease ech and get the retry configs back */
ret = wolfSSL_connect(ssl);
if (ret != SSL_SUCCESS) {
printf( "%d %d\n", ret, wolfSSL_get_error( ssl, ret ) );
err_sys("Error wolfSSL_connect");
}
printf("5\n");
/* retrieve the retry configs sent by the server */
ret = wolfSSL_GetEchConfigs(ssl, ech_configs, &ech_configs_len);
if (ret != SSL_SUCCESS) {
printf( "%d %d\n", ret, wolfSSL_get_error( ssl, ret ) );
err_sys("Error wolfSSL_get_ech_configs");
}
printf("6\n");
/* frees all data before client termination */
wolfSSL_free(ssl);
close(sockfd);
/* now we create a new connection that will send the real ech */
/* create and set up socket */
sockfd = socket(AF_INET, SOCK_STREAM, 0);
memset(&servAddr, 0, sizeof(servAddr));
servAddr.sin_family = AF_INET;
servAddr.sin_port = htons(SERV_PORT);
// set the ip string to the cloudflare server
servAddr.sin_addr.s_addr = inet_addr( ip_string );
/* connect to socket */
connect(sockfd, (struct sockaddr *) &servAddr, sizeof(servAddr));
/* make new wolfSSL struct */
if ( (ssl = wolfSSL_new(ctx)) == NULL) {
err_sys("wolfSSL_new error");
}
// set the ech configs taken from dns
ret = wolfSSL_SetEchConfigs(ssl, ech_configs, ech_configs_len);
if ( ret != WOLFSSL_SUCCESS ) {
err_sys("wolfSSL_set_ech_configs error");
}
/* Connect wolfssl to the socket, server, then send message */
wolfSSL_set_fd(ssl, sockfd);
/* this connect will send the real ech */
ret = wolfSSL_connect(ssl);
if (ret != SSL_SUCCESS) {
printf( "%d %d\n", ret, wolfSSL_get_error( ssl, ret ) );
err_sys("Error wolfSSL_connect");
}
wolfSSL_write(ssl, message, strlen(message));
do
{
ret = wolfSSL_read( ssl, rd_buf, sizeof(rd_buf) );
printf( "%.*s", ret, rd_buf );
/* read until the chunk size is 0 */
} while ( rd_buf[0] != '0' );
wolfSSL_free(ssl);
wolfSSL_CTX_free(ctx);
wolfSSL_Cleanup();
}
using pem from https://gist.github.com/jpbland1/ad46617fcc40934b252ce031c7aa5969
Hi @FrontMage ,
This looks just like our example at https://github.com/wolfSSL/wolfssl-examples/blob/master/tls/client-ech.c. I can reproduce % ./client-ech -1 -313
. I suspect something changes since we wrote the example. Possibly the certificate needs updated.
I've asked @jpbland1 to review.
Thanks, David Garske, wolfSSL
Hi @FrontMage ,
@jpbland1 is still investigating the issue and will provide an update soon. He's confirmed something did change with CloudFlare's server causing the ECH illegal_paramter issue.
Thanks, David Garske, wolfSSL
@philljj please work with @jpbland1 to assist with this. Thanks
I'm on an M1 mac as well and getting a similar error message. Any logs I can provide to help?
Hi @mspiegel,
Thanks, but I can reproduce the Alert type: illegal_parameter
so I don't need logs.
I'm sorry for the slow reply in this thread, I will try to figure out this issue.
Thanks, Jordan
Hi @FrontMage and @mspiegel,
I'm sorry for the slow update. The root cause is a bug in our client side ECH when the server sends a Hello Retry Request (see: https://github.com/wolfSSL/wolfssl/issues/6802).
As a workaround in the meantime, for this example (https://github.com/wolfSSL/wolfssl-examples/blob/master/tls/client-ech.c) if you set X25519
in the curves list then the server does not need to send the HRR, and the example works again:
diff --git a/tls/client-ech.c b/tls/client-ech.c
index 045bac4..a618428 100644
--- a/tls/client-ech.c
+++ b/tls/client-ech.c
@@ -93,6 +93,12 @@ int main(void)
goto ctx_clean;
}
+ ret = wolfSSL_CTX_set1_curves_list(ctx, "X25519");
+ if (ret != WOLFSSL_SUCCESS) {
+ printf("wolfSSL_CTX_set1_curves_list error %d", ret);
+ goto ctx_clean;
+ }
+
/* make new wolfSSL struct */
if ((ssl = wolfSSL_new(ctx)) == NULL) {
printf("wolfSSL_new error");
After workaround:
$./client-ech
HTTP/1.1 200 OK
Access-Control-Allow-Origin: *
Cache-Control: no-cache
Cf-Ray: 83914558b0686b2e-DFW
Content-Type: text/plain
Expires: Thu, 01 Jan 1970 00:00:01 GMT
Server: cloudflare
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
Date: Thu, 21 Dec 2023 15:48:42 GMT
Transfer-Encoding: chunked
113
fl=724f29
h=crypto.cloudflare.com
ip=72.190.33.56
ts=1703173722.998
visit_scheme=https
uag=Mozilla/5.0 (X11; Linux x86_64; rv:105.0) Gecko/20100101 Firefox/105.0
colo=DFW
sliver=010-dfw09
http=http/1.1
loc=US
tls=TLSv1.3
sni=encrypted
warp=off
gateway=off
rbi=off
kex=X25519
0
This is obviously a workaround, and we should resolve the underlying issue.
Best, Jordan