nginx / unit

NGINX Unit - universal web app server - a lightweight and versatile open source server that simplifies the application stack by natively executing application code across eight different programming language runtimes.
https://unit.nginx.org
Apache License 2.0
5.25k stars 322 forks source link

Choosing TLS library at startup time #1209

Open rock59 opened 2 months ago

rock59 commented 2 months ago

Does Unit support choosing TLS library at startup time (not compile time)? For example chossing OpenSSL or GnuTLS at startup

ac000 commented 2 months ago

Hi,

AFAICT Unit really only supports OpenSSL.

For example the other TLS implementations do something like

const nxt_ssltls_lib_t  nxt_gnutls_lib = {                                      
    nxt_gnutls_server_init,                                                     
    NULL,                                                                       
};

nxt_ssltls_lib_t is not defined anywhere.

If I ./configure --gnutls

checking for GnuTLS library ... found
 + GnuTLS version: 3.8.4
checking for gnutls_transport_set_vec_push_function ... found
checking for gnutls_global_set_time_function ... found

OK, good.

  TLS support: ............... NO

Not so godd...

  CC     build/src/nxt_cert.o
src/nxt_cert.c: In function ‘nxt_cert_mem’:
src/nxt_cert.c:65:9: error: implicit declaration of function ‘nxt_openssl_log_error’; did you mean ‘nxt_main_log_error’? [-Werror=implicit-function-declaration]
   65 |         nxt_openssl_log_error(task, NXT_LOG_ALERT, "BIO_new_mem_buf() failed");
      |         ^~~~~~~~~~~~~~~~~~~~~
      |         nxt_main_log_error
cc1: all warnings being treated as errors

Oh dear...

If I ./configure --gnutls --openssl # because who knows?!

checking for GnuTLS library ... found
 + GnuTLS version: 3.8.4
checking for gnutls_transport_set_vec_push_function ... found
checking for gnutls_global_set_time_function ... found
...
  TLS support: ............... YES

Better I guess...

  CC     build/src/nxt_gnutls.o
src/nxt_gnutls.c:31:41: error: unknown type name ‘nxt_ssltls_conf_t’; did you mean ‘nxt_tls_conf_t’?
   31 | static nxt_int_t nxt_gnutls_server_init(nxt_ssltls_conf_t *conf);
      |                                         ^~~~~~~~~~~~~~~~~
      |                                         nxt_tls_conf_t
src/nxt_gnutls.c:32:41: error: unknown type name ‘nxt_ssltls_conf_t’; did you mean ‘nxt_tls_conf_t’?
   32 | static nxt_int_t nxt_gnutls_set_ciphers(nxt_ssltls_conf_t *conf);
      |                                         ^~~~~~~~~~~~~~~~~
      |                                         nxt_tls_conf_t
src/nxt_gnutls.c:34:53: error: unknown type name ‘nxt_ssltls_conf_t’; did you mean ‘nxt_tls_conf_t’?
   34 | static void nxt_gnutls_conn_init(nxt_thread_t *thr, nxt_ssltls_conf_t *conf,
      |                                                     ^~~~~~~~~~~~~~~~~
      |                                                     nxt_tls_conf_t

and on and on...

rock59 commented 2 months ago

@ac000 Thank you for your response

I used s2n-tls in one of my projects and I am very satisfied with the functionality and simplicity of s2n-tls. I am very interested in using s2n-tls in Unit, but I don't know enough about the internals of Unit. Does anyone know if Unit supports switching between different TLS libraries at startup time?

ac000 commented 2 months ago

It looks like the idea was to support TLS libraries other than OpenSSL, see; _src/nxtgnutls.c, _src/nxtcyassl.c & _src/nxtpolarssl.c, however it seems this work was never fully realised.

I've never really looked at the TLS code specifically, so this is just my current findings.

It looks like the TLS interface is abstracted out, in _src/nxtopenssl.c we have

const nxt_tls_lib_t  nxt_openssl_lib = {                                        
    .library_init = nxt_openssl_library_init,                                   
    .library_free = nxt_openssl_library_free,                                   

    .server_init = nxt_openssl_server_init,                                     
    .server_free = nxt_openssl_server_free,                                     
};                                                                              

static nxt_conn_io_t  nxt_openssl_conn_io = {                                   
    .read = nxt_conn_io_read,                                                   
    .recvbuf = nxt_openssl_conn_io_recvbuf,                                     

    .write = nxt_conn_io_write,                                                 
    .sendbuf = nxt_openssl_conn_io_sendbuf,                                     

    .shutdown = nxt_openssl_conn_io_shutdown,                                   
};

The existing alternate TLS APIs are not implementing this interface.

They were all introduced in the initial commit of Unit and haven't seen any meaningful work since then, it's possible they just came along from nginx.

Anyway at the very least in order to support your TLS library of choice you'd need to write an API on top of it implementing the above functions.

rock59 commented 2 months ago

@ac000 Thanks