src/stream/ngx_stream_ssl_module.c - nginx-1.31.3 nginx/ @ 42f8df65b

Global variables defined

Data types defined

Functions defined

Macros defined

Source code


  1. /*
  2. * Copyright (C) Igor Sysoev
  3. * Copyright (C) Nginx, Inc.
  4. */


  5. #include <ngx_config.h>
  6. #include <ngx_core.h>
  7. #include <ngx_stream.h>


  8. typedef ngx_int_t (*ngx_ssl_variable_handler_pt)(ngx_connection_t *c,
  9.     ngx_pool_t *pool, ngx_str_t *s);


  10. #define NGX_DEFAULT_CIPHERS     "HIGH:!aNULL:!MD5"
  11. #define NGX_DEFAULT_ECDH_CURVE  "auto"


  12. static ngx_int_t ngx_stream_ssl_handler(ngx_stream_session_t *s);
  13. static ngx_int_t ngx_stream_ssl_init_connection(ngx_ssl_t *ssl,
  14.     ngx_connection_t *c);
  15. static void ngx_stream_ssl_handshake_handler(ngx_connection_t *c);
  16. #ifdef SSL_CTRL_SET_TLSEXT_HOSTNAME
  17. static int ngx_stream_ssl_servername(ngx_ssl_conn_t *ssl_conn, int *ad,
  18.     void *arg);
  19. #endif
  20. #ifdef TLSEXT_TYPE_application_layer_protocol_negotiation
  21. static int ngx_stream_ssl_alpn_select(ngx_ssl_conn_t *ssl_conn,
  22.     const unsigned char **out, unsigned char *outlen,
  23.     const unsigned char *in, unsigned int inlen, void *arg);
  24. #endif
  25. #ifdef SSL_R_CERT_CB_ERROR
  26. static int ngx_stream_ssl_certificate(ngx_ssl_conn_t *ssl_conn, void *arg);
  27. #endif
  28. static ngx_int_t ngx_stream_ssl_static_variable(ngx_stream_session_t *s,
  29.     ngx_stream_variable_value_t *v, uintptr_t data);
  30. static ngx_int_t ngx_stream_ssl_variable(ngx_stream_session_t *s,
  31.     ngx_stream_variable_value_t *v, uintptr_t data);

  32. static ngx_int_t ngx_stream_ssl_add_variables(ngx_conf_t *cf);
  33. static void *ngx_stream_ssl_create_srv_conf(ngx_conf_t *cf);
  34. static char *ngx_stream_ssl_merge_srv_conf(ngx_conf_t *cf, void *parent,
  35.     void *child);

  36. static ngx_int_t ngx_stream_ssl_compile_certificates(ngx_conf_t *cf,
  37.     ngx_stream_ssl_srv_conf_t *conf);

  38. static char *ngx_stream_ssl_certificate_cache(ngx_conf_t *cf,
  39.     ngx_command_t *cmd, void *conf);
  40. static char *ngx_stream_ssl_password_file(ngx_conf_t *cf, ngx_command_t *cmd,
  41.     void *conf);
  42. static char *ngx_stream_ssl_session_cache(ngx_conf_t *cf, ngx_command_t *cmd,
  43.     void *conf);
  44. static char *ngx_stream_ssl_ocsp_cache(ngx_conf_t *cf, ngx_command_t *cmd,
  45.     void *conf);
  46. static char *ngx_stream_ssl_alpn(ngx_conf_t *cf, ngx_command_t *cmd,
  47.     void *conf);

  48. static char *ngx_stream_ssl_conf_command_check(ngx_conf_t *cf, void *post,
  49.     void *data);

  50. static ngx_int_t ngx_stream_ssl_init(ngx_conf_t *cf);


  51. static ngx_conf_bitmask_t  ngx_stream_ssl_protocols[] = {
  52.     { ngx_string("SSLv2"), NGX_SSL_SSLv2 },
  53.     { ngx_string("SSLv3"), NGX_SSL_SSLv3 },
  54.     { ngx_string("TLSv1"), NGX_SSL_TLSv1 },
  55.     { ngx_string("TLSv1.1"), NGX_SSL_TLSv1_1 },
  56.     { ngx_string("TLSv1.2"), NGX_SSL_TLSv1_2 },
  57.     { ngx_string("TLSv1.3"), NGX_SSL_TLSv1_3 },
  58.     { ngx_null_string, 0 }
  59. };


  60. static ngx_conf_enum_t  ngx_stream_ssl_verify[] = {
  61.     { ngx_string("off"), 0 },
  62.     { ngx_string("on"), 1 },
  63.     { ngx_string("optional"), 2 },
  64.     { ngx_string("optional_no_ca"), 3 },
  65.     { ngx_null_string, 0 }
  66. };


  67. static ngx_conf_enum_t  ngx_stream_ssl_ocsp[] = {
  68.     { ngx_string("off"), 0 },
  69.     { ngx_string("on"), 1 },
  70.     { ngx_string("leaf"), 2 },
  71.     { ngx_null_string, 0 }
  72. };


  73. static ngx_conf_post_t  ngx_stream_ssl_conf_command_post =
  74.     { ngx_stream_ssl_conf_command_check };


  75. static ngx_command_t  ngx_stream_ssl_commands[] = {

  76.     { ngx_string("ssl_handshake_timeout"),
  77.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  78.       ngx_conf_set_msec_slot,
  79.       NGX_STREAM_SRV_CONF_OFFSET,
  80.       offsetof(ngx_stream_ssl_srv_conf_t, handshake_timeout),
  81.       NULL },

  82.     { ngx_string("ssl_certificate"),
  83.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  84.       ngx_conf_set_str_array_slot,
  85.       NGX_STREAM_SRV_CONF_OFFSET,
  86.       offsetof(ngx_stream_ssl_srv_conf_t, certificates),
  87.       NULL },

  88.     { ngx_string("ssl_certificate_key"),
  89.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  90.       ngx_conf_set_str_array_slot,
  91.       NGX_STREAM_SRV_CONF_OFFSET,
  92.       offsetof(ngx_stream_ssl_srv_conf_t, certificate_keys),
  93.       NULL },

  94.     { ngx_string("ssl_certificate_cache"),
  95.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE123,
  96.       ngx_stream_ssl_certificate_cache,
  97.       NGX_STREAM_SRV_CONF_OFFSET,
  98.       0,
  99.       NULL },

  100.     { ngx_string("ssl_ech_file"),
  101.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  102.       ngx_conf_set_str_array_slot,
  103.       NGX_STREAM_SRV_CONF_OFFSET,
  104.       offsetof(ngx_stream_ssl_srv_conf_t, ech_files),
  105.       NULL },

  106.     { ngx_string("ssl_password_file"),
  107.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  108.       ngx_stream_ssl_password_file,
  109.       NGX_STREAM_SRV_CONF_OFFSET,
  110.       0,
  111.       NULL },

  112.     { ngx_string("ssl_certificate_compression"),
  113.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  114.       ngx_conf_set_flag_slot,
  115.       NGX_STREAM_SRV_CONF_OFFSET,
  116.       offsetof(ngx_stream_ssl_srv_conf_t, certificate_compression),
  117.       NULL },

  118.     { ngx_string("ssl_dhparam"),
  119.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  120.       ngx_conf_set_str_slot,
  121.       NGX_STREAM_SRV_CONF_OFFSET,
  122.       offsetof(ngx_stream_ssl_srv_conf_t, dhparam),
  123.       NULL },

  124.     { ngx_string("ssl_ecdh_curve"),
  125.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  126.       ngx_conf_set_str_slot,
  127.       NGX_STREAM_SRV_CONF_OFFSET,
  128.       offsetof(ngx_stream_ssl_srv_conf_t, ecdh_curve),
  129.       NULL },

  130.     { ngx_string("ssl_protocols"),
  131.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_1MORE,
  132.       ngx_conf_set_bitmask_slot,
  133.       NGX_STREAM_SRV_CONF_OFFSET,
  134.       offsetof(ngx_stream_ssl_srv_conf_t, protocols),
  135.       &ngx_stream_ssl_protocols },

  136.     { ngx_string("ssl_ciphers"),
  137.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  138.       ngx_conf_set_str_slot,
  139.       NGX_STREAM_SRV_CONF_OFFSET,
  140.       offsetof(ngx_stream_ssl_srv_conf_t, ciphers),
  141.       NULL },

  142.     { ngx_string("ssl_verify_client"),
  143.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  144.       ngx_conf_set_enum_slot,
  145.       NGX_STREAM_SRV_CONF_OFFSET,
  146.       offsetof(ngx_stream_ssl_srv_conf_t, verify),
  147.       &ngx_stream_ssl_verify },

  148.     { ngx_string("ssl_verify_depth"),
  149.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  150.       ngx_conf_set_num_slot,
  151.       NGX_STREAM_SRV_CONF_OFFSET,
  152.       offsetof(ngx_stream_ssl_srv_conf_t, verify_depth),
  153.       NULL },

  154.     { ngx_string("ssl_client_certificate"),
  155.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  156.       ngx_conf_set_str_slot,
  157.       NGX_STREAM_SRV_CONF_OFFSET,
  158.       offsetof(ngx_stream_ssl_srv_conf_t, client_certificate),
  159.       NULL },

  160.     { ngx_string("ssl_trusted_certificate"),
  161.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  162.       ngx_conf_set_str_slot,
  163.       NGX_STREAM_SRV_CONF_OFFSET,
  164.       offsetof(ngx_stream_ssl_srv_conf_t, trusted_certificate),
  165.       NULL },

  166.     { ngx_string("ssl_prefer_server_ciphers"),
  167.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  168.       ngx_conf_set_flag_slot,
  169.       NGX_STREAM_SRV_CONF_OFFSET,
  170.       offsetof(ngx_stream_ssl_srv_conf_t, prefer_server_ciphers),
  171.       NULL },

  172.     { ngx_string("ssl_session_cache"),
  173.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE12,
  174.       ngx_stream_ssl_session_cache,
  175.       NGX_STREAM_SRV_CONF_OFFSET,
  176.       0,
  177.       NULL },

  178.     { ngx_string("ssl_session_tickets"),
  179.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  180.       ngx_conf_set_flag_slot,
  181.       NGX_STREAM_SRV_CONF_OFFSET,
  182.       offsetof(ngx_stream_ssl_srv_conf_t, session_tickets),
  183.       NULL },

  184.     { ngx_string("ssl_session_ticket_key"),
  185.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  186.       ngx_conf_set_str_array_slot,
  187.       NGX_STREAM_SRV_CONF_OFFSET,
  188.       offsetof(ngx_stream_ssl_srv_conf_t, session_ticket_keys),
  189.       NULL },

  190.     { ngx_string("ssl_session_timeout"),
  191.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  192.       ngx_conf_set_sec_slot,
  193.       NGX_STREAM_SRV_CONF_OFFSET,
  194.       offsetof(ngx_stream_ssl_srv_conf_t, session_timeout),
  195.       NULL },

  196.     { ngx_string("ssl_crl"),
  197.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  198.       ngx_conf_set_str_slot,
  199.       NGX_STREAM_SRV_CONF_OFFSET,
  200.       offsetof(ngx_stream_ssl_srv_conf_t, crl),
  201.       NULL },

  202.     { ngx_string("ssl_ocsp"),
  203.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  204.       ngx_conf_set_enum_slot,
  205.       NGX_STREAM_SRV_CONF_OFFSET,
  206.       offsetof(ngx_stream_ssl_srv_conf_t, ocsp),
  207.       &ngx_stream_ssl_ocsp },

  208.     { ngx_string("ssl_ocsp_responder"),
  209.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  210.       ngx_conf_set_str_slot,
  211.       NGX_STREAM_SRV_CONF_OFFSET,
  212.       offsetof(ngx_stream_ssl_srv_conf_t, ocsp_responder),
  213.       NULL },

  214.     { ngx_string("ssl_ocsp_cache"),
  215.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  216.       ngx_stream_ssl_ocsp_cache,
  217.       NGX_STREAM_SRV_CONF_OFFSET,
  218.       0,
  219.       NULL },

  220.     { ngx_string("ssl_stapling"),
  221.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  222.       ngx_conf_set_flag_slot,
  223.       NGX_STREAM_SRV_CONF_OFFSET,
  224.       offsetof(ngx_stream_ssl_srv_conf_t, stapling),
  225.       NULL },

  226.     { ngx_string("ssl_stapling_file"),
  227.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  228.       ngx_conf_set_str_slot,
  229.       NGX_STREAM_SRV_CONF_OFFSET,
  230.       offsetof(ngx_stream_ssl_srv_conf_t, stapling_file),
  231.       NULL },

  232.     { ngx_string("ssl_stapling_responder"),
  233.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
  234.       ngx_conf_set_str_slot,
  235.       NGX_STREAM_SRV_CONF_OFFSET,
  236.       offsetof(ngx_stream_ssl_srv_conf_t, stapling_responder),
  237.       NULL },

  238.     { ngx_string("ssl_stapling_verify"),
  239.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  240.       ngx_conf_set_flag_slot,
  241.       NGX_STREAM_SRV_CONF_OFFSET,
  242.       offsetof(ngx_stream_ssl_srv_conf_t, stapling_verify),
  243.       NULL },

  244.     { ngx_string("ssl_conf_command"),
  245.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE2,
  246.       ngx_conf_set_keyval_slot,
  247.       NGX_STREAM_SRV_CONF_OFFSET,
  248.       offsetof(ngx_stream_ssl_srv_conf_t, conf_commands),
  249.       &ngx_stream_ssl_conf_command_post },

  250.     { ngx_string("ssl_reject_handshake"),
  251.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG,
  252.       ngx_conf_set_flag_slot,
  253.       NGX_STREAM_SRV_CONF_OFFSET,
  254.       offsetof(ngx_stream_ssl_srv_conf_t, reject_handshake),
  255.       NULL },

  256.     { ngx_string("ssl_alpn"),
  257.       NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_1MORE,
  258.       ngx_stream_ssl_alpn,
  259.       NGX_STREAM_SRV_CONF_OFFSET,
  260.       0,
  261.       NULL },

  262.       ngx_null_command
  263. };


  264. static ngx_stream_module_t  ngx_stream_ssl_module_ctx = {
  265.     ngx_stream_ssl_add_variables,          /* preconfiguration */
  266.     ngx_stream_ssl_init,                   /* postconfiguration */

  267.     NULL,                                  /* create main configuration */
  268.     NULL,                                  /* init main configuration */

  269.     ngx_stream_ssl_create_srv_conf,        /* create server configuration */
  270.     ngx_stream_ssl_merge_srv_conf          /* merge server configuration */
  271. };


  272. ngx_module_t  ngx_stream_ssl_module = {
  273.     NGX_MODULE_V1,
  274.     &ngx_stream_ssl_module_ctx,            /* module context */
  275.     ngx_stream_ssl_commands,               /* module directives */
  276.     NGX_STREAM_MODULE,                     /* module type */
  277.     NULL,                                  /* init master */
  278.     NULL,                                  /* init module */
  279.     NULL,                                  /* init process */
  280.     NULL,                                  /* init thread */
  281.     NULL,                                  /* exit thread */
  282.     NULL,                                  /* exit process */
  283.     NULL,                                  /* exit master */
  284.     NGX_MODULE_V1_PADDING
  285. };


  286. static ngx_stream_variable_t  ngx_stream_ssl_vars[] = {

  287.     { ngx_string("ssl_protocol"), NULL, ngx_stream_ssl_static_variable,
  288.       (uintptr_t) ngx_ssl_get_protocol, NGX_STREAM_VAR_CHANGEABLE, 0 },

  289.     { ngx_string("ssl_cipher"), NULL, ngx_stream_ssl_static_variable,
  290.       (uintptr_t) ngx_ssl_get_cipher_name, NGX_STREAM_VAR_CHANGEABLE, 0 },

  291.     { ngx_string("ssl_ciphers"), NULL, ngx_stream_ssl_variable,
  292.       (uintptr_t) ngx_ssl_get_ciphers, NGX_STREAM_VAR_CHANGEABLE, 0 },

  293.     { ngx_string("ssl_curve"), NULL, ngx_stream_ssl_variable,
  294.       (uintptr_t) ngx_ssl_get_curve, NGX_STREAM_VAR_CHANGEABLE, 0 },

  295.     { ngx_string("ssl_curves"), NULL, ngx_stream_ssl_variable,
  296.       (uintptr_t) ngx_ssl_get_curves, NGX_STREAM_VAR_CHANGEABLE, 0 },

  297.     { ngx_string("ssl_sigalg"), NULL, ngx_stream_ssl_variable,
  298.       (uintptr_t) ngx_ssl_get_sigalg, NGX_STREAM_VAR_CHANGEABLE, 0 },

  299.     { ngx_string("ssl_sigalgs"), NULL, ngx_stream_ssl_variable,
  300.       (uintptr_t) ngx_ssl_get_sigalgs, NGX_STREAM_VAR_CHANGEABLE, 0 },

  301.     { ngx_string("ssl_session_id"), NULL, ngx_stream_ssl_variable,
  302.       (uintptr_t) ngx_ssl_get_session_id, NGX_STREAM_VAR_CHANGEABLE, 0 },

  303.     { ngx_string("ssl_session_reused"), NULL, ngx_stream_ssl_variable,
  304.       (uintptr_t) ngx_ssl_get_session_reused, NGX_STREAM_VAR_CHANGEABLE, 0 },

  305.     { ngx_string("ssl_server_name"), NULL, ngx_stream_ssl_variable,
  306.       (uintptr_t) ngx_ssl_get_server_name, NGX_STREAM_VAR_CHANGEABLE, 0 },

  307.     { ngx_string("ssl_alpn_protocol"), NULL, ngx_stream_ssl_variable,
  308.       (uintptr_t) ngx_ssl_get_alpn_protocol, NGX_STREAM_VAR_CHANGEABLE, 0 },

  309.     { ngx_string("ssl_ech_status"), NULL, ngx_stream_ssl_variable,
  310.       (uintptr_t) ngx_ssl_get_ech_status, NGX_STREAM_VAR_CHANGEABLE, 0 },

  311.     { ngx_string("ssl_ech_outer_server_name"), NULL, ngx_stream_ssl_variable,
  312.       (uintptr_t) ngx_ssl_get_ech_outer_server_name,
  313.       NGX_STREAM_VAR_CHANGEABLE, 0 },

  314.     { ngx_string("ssl_client_cert"), NULL, ngx_stream_ssl_variable,
  315.       (uintptr_t) ngx_ssl_get_certificate, NGX_STREAM_VAR_CHANGEABLE, 0 },

  316.     { ngx_string("ssl_client_raw_cert"), NULL, ngx_stream_ssl_variable,
  317.       (uintptr_t) ngx_ssl_get_raw_certificate,
  318.       NGX_STREAM_VAR_CHANGEABLE, 0 },

  319.     { ngx_string("ssl_client_escaped_cert"), NULL, ngx_stream_ssl_variable,
  320.       (uintptr_t) ngx_ssl_get_escaped_certificate,
  321.       NGX_STREAM_VAR_CHANGEABLE, 0 },

  322.     { ngx_string("ssl_client_s_dn"), NULL, ngx_stream_ssl_variable,
  323.       (uintptr_t) ngx_ssl_get_subject_dn, NGX_STREAM_VAR_CHANGEABLE, 0 },

  324.     { ngx_string("ssl_client_i_dn"), NULL, ngx_stream_ssl_variable,
  325.       (uintptr_t) ngx_ssl_get_issuer_dn, NGX_STREAM_VAR_CHANGEABLE, 0 },

  326.     { ngx_string("ssl_client_serial"), NULL, ngx_stream_ssl_variable,
  327.       (uintptr_t) ngx_ssl_get_serial_number, NGX_STREAM_VAR_CHANGEABLE, 0 },

  328.     { ngx_string("ssl_client_fingerprint"), NULL, ngx_stream_ssl_variable,
  329.       (uintptr_t) ngx_ssl_get_fingerprint, NGX_STREAM_VAR_CHANGEABLE, 0 },

  330.     { ngx_string("ssl_client_verify"), NULL, ngx_stream_ssl_variable,
  331.       (uintptr_t) ngx_ssl_get_client_verify, NGX_STREAM_VAR_CHANGEABLE, 0 },

  332.     { ngx_string("ssl_client_v_start"), NULL, ngx_stream_ssl_variable,
  333.       (uintptr_t) ngx_ssl_get_client_v_start, NGX_STREAM_VAR_CHANGEABLE, 0 },

  334.     { ngx_string("ssl_client_v_end"), NULL, ngx_stream_ssl_variable,
  335.       (uintptr_t) ngx_ssl_get_client_v_end, NGX_STREAM_VAR_CHANGEABLE, 0 },

  336.     { ngx_string("ssl_client_v_remain"), NULL, ngx_stream_ssl_variable,
  337.       (uintptr_t) ngx_ssl_get_client_v_remain, NGX_STREAM_VAR_CHANGEABLE, 0 },

  338.     { ngx_string("ssl_client_sigalg"), NULL, ngx_stream_ssl_variable,
  339.       (uintptr_t) ngx_ssl_get_client_sigalg, NGX_STREAM_VAR_CHANGEABLE, 0 },

  340.       ngx_stream_null_variable
  341. };


  342. static ngx_str_t ngx_stream_ssl_sess_id_ctx = ngx_string("STREAM");


  343. static ngx_int_t
  344. ngx_stream_ssl_handler(ngx_stream_session_t *s)
  345. {
  346.     long                        rc;
  347.     X509                       *cert;
  348.     ngx_int_t                   rv;
  349.     const char                 *str;
  350.     ngx_connection_t           *c;
  351.     ngx_stream_ssl_srv_conf_t  *sscf;

  352.     if (!s->ssl) {
  353.         return NGX_OK;
  354.     }

  355.     c = s->connection;

  356.     sscf = ngx_stream_get_module_srv_conf(s, ngx_stream_ssl_module);

  357.     if (c->ssl == NULL) {
  358.         c->log->action = "SSL handshaking";

  359.         rv = ngx_stream_ssl_init_connection(&sscf->ssl, c);

  360.         if (rv != NGX_OK) {
  361.             return rv;
  362.         }
  363.     }

  364.     if (sscf->verify) {
  365.         rc = SSL_get_verify_result(c->ssl->connection);

  366.         if (rc != X509_V_OK
  367.             && (sscf->verify != 3 || !ngx_ssl_verify_error_optional(rc)))
  368.         {
  369.             ngx_log_error(NGX_LOG_INFO, c->log, 0,
  370.                           "client SSL certificate verify error: (%l:%s)",
  371.                           rc, X509_verify_cert_error_string(rc));

  372.             ngx_ssl_remove_cached_session(c->ssl->session_ctx,
  373.                                        (SSL_get0_session(c->ssl->connection)));
  374.             return NGX_ERROR;
  375.         }

  376.         if (sscf->verify == 1) {
  377.             cert = SSL_get_peer_certificate(c->ssl->connection);

  378.             if (cert == NULL) {
  379.                 ngx_log_error(NGX_LOG_INFO, c->log, 0,
  380.                               "client sent no required SSL certificate");

  381.                 ngx_ssl_remove_cached_session(c->ssl->session_ctx,
  382.                                        (SSL_get0_session(c->ssl->connection)));
  383.                 return NGX_ERROR;
  384.             }

  385.             X509_free(cert);
  386.         }

  387.         if (ngx_ssl_ocsp_get_status(c, &str) != NGX_OK) {
  388.             ngx_log_error(NGX_LOG_INFO, c->log, 0,
  389.                           "client SSL certificate verify error: %s", str);

  390.             ngx_ssl_remove_cached_session(c->ssl->session_ctx,
  391.                                        (SSL_get0_session(c->ssl->connection)));
  392.             return NGX_ERROR;
  393.         }
  394.     }

  395.     return NGX_OK;
  396. }


  397. static ngx_int_t
  398. ngx_stream_ssl_init_connection(ngx_ssl_t *ssl, ngx_connection_t *c)
  399. {
  400.     ngx_int_t                    rc;
  401.     ngx_stream_session_t        *s;
  402.     ngx_stream_ssl_srv_conf_t   *sscf;
  403.     ngx_stream_core_srv_conf_t  *cscf;

  404.     s = c->data;

  405.     cscf = ngx_stream_get_module_srv_conf(s, ngx_stream_core_module);

  406.     if (cscf->tcp_nodelay && ngx_tcp_nodelay(c) != NGX_OK) {
  407.         return NGX_ERROR;
  408.     }

  409.     if (ngx_ssl_create_connection(ssl, c, 0) != NGX_OK) {
  410.         return NGX_ERROR;
  411.     }

  412.     rc = ngx_ssl_handshake(c);

  413.     if (rc == NGX_ERROR) {
  414.         return NGX_ERROR;
  415.     }

  416.     if (rc == NGX_AGAIN) {
  417.         sscf = ngx_stream_get_module_srv_conf(s, ngx_stream_ssl_module);

  418.         ngx_add_timer(c->read, sscf->handshake_timeout);

  419.         c->ssl->handler = ngx_stream_ssl_handshake_handler;

  420.         return NGX_AGAIN;
  421.     }

  422.     /* rc == NGX_OK */

  423.     return NGX_OK;
  424. }


  425. static void
  426. ngx_stream_ssl_handshake_handler(ngx_connection_t *c)
  427. {
  428.     ngx_stream_session_t  *s;

  429.     s = c->data;

  430.     if (!c->ssl->handshaked) {
  431.         ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
  432.         return;
  433.     }

  434.     if (c->read->timer_set) {
  435.         ngx_del_timer(c->read);
  436.     }

  437.     ngx_stream_core_run_phases(s);
  438. }


  439. #ifdef SSL_CTRL_SET_TLSEXT_HOSTNAME

  440. static int
  441. ngx_stream_ssl_servername(ngx_ssl_conn_t *ssl_conn, int *ad, void *arg)
  442. {
  443.     ngx_int_t                    rc;
  444.     ngx_str_t                    host;
  445.     const char                  *servername;
  446.     ngx_connection_t            *c;
  447.     ngx_stream_session_t        *s;
  448.     ngx_stream_ssl_srv_conf_t   *sscf;
  449.     ngx_stream_core_srv_conf_t  *cscf;

  450.     c = ngx_ssl_get_connection(ssl_conn);

  451.     if (c->ssl->handshaked) {
  452.         *ad = SSL_AD_NO_RENEGOTIATION;
  453.         return SSL_TLSEXT_ERR_ALERT_FATAL;
  454.     }

  455.     if (c->ssl->sni_accepted) {
  456.         return SSL_TLSEXT_ERR_OK;
  457.     }

  458.     if (c->ssl->handshake_rejected) {
  459.         *ad = SSL_AD_UNRECOGNIZED_NAME;
  460.         return SSL_TLSEXT_ERR_ALERT_FATAL;
  461.     }

  462.     s = c->data;

  463.     if (arg) {
  464.         host = *(ngx_str_t *) arg;

  465.         if (host.data == NULL) {
  466.             ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0,
  467.                            "SSL server name: null");
  468.             goto done;
  469.         }

  470.     } else {
  471.         servername = SSL_get_servername(ssl_conn, TLSEXT_NAMETYPE_host_name);

  472.         if (servername == NULL) {
  473.             ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0,
  474.                            "SSL server name: null");
  475.             goto done;
  476.         }

  477.         host.len = ngx_strlen(servername);
  478.         host.data = (u_char *) servername;
  479.     }

  480.     ngx_log_debug1(NGX_LOG_DEBUG_STREAM, c->log, 0,
  481.                    "SSL server name: \"%V\"", &host);

  482.     if (host.len == 0) {
  483.         goto done;
  484.     }

  485.     rc = ngx_stream_validate_host(&host, c->pool, 1);

  486.     if (rc == NGX_ERROR) {
  487.         goto error;
  488.     }

  489.     if (rc == NGX_DECLINED) {
  490.         goto done;
  491.     }

  492.     rc = ngx_stream_find_virtual_server(s, &host, &cscf);

  493.     if (rc == NGX_ERROR) {
  494.         goto error;
  495.     }

  496.     if (rc == NGX_DECLINED) {
  497.         goto done;
  498.     }

  499.     s->srv_conf = cscf->ctx->srv_conf;

  500.     ngx_set_connection_log(c, cscf->error_log);

  501.     sscf = ngx_stream_get_module_srv_conf(cscf->ctx, ngx_stream_ssl_module);

  502.     if (sscf->ssl.ctx) {
  503.         if (SSL_set_SSL_CTX(ssl_conn, sscf->ssl.ctx) == NULL) {
  504.             goto error;
  505.         }

  506.         /*
  507.          * SSL_set_SSL_CTX() only changes certs as of 1.0.0d
  508.          * adjust other things we care about
  509.          */

  510.         SSL_set_verify(ssl_conn, SSL_CTX_get_verify_mode(sscf->ssl.ctx),
  511.                        SSL_CTX_get_verify_callback(sscf->ssl.ctx));

  512.         SSL_set_verify_depth(ssl_conn, SSL_CTX_get_verify_depth(sscf->ssl.ctx));

  513. #if OPENSSL_VERSION_NUMBER >= 0x009080dfL
  514.         /* only in 0.9.8m+ */
  515.         SSL_clear_options(ssl_conn, SSL_get_options(ssl_conn) &
  516.                                     ~SSL_CTX_get_options(sscf->ssl.ctx));
  517. #endif

  518.         SSL_set_options(ssl_conn, SSL_CTX_get_options(sscf->ssl.ctx));

  519. #ifdef SSL_OP_NO_RENEGOTIATION
  520.         SSL_set_options(ssl_conn, SSL_OP_NO_RENEGOTIATION);
  521. #endif
  522.     }

  523. done:

  524.     sscf = ngx_stream_get_module_srv_conf(s, ngx_stream_ssl_module);

  525.     if (sscf->reject_handshake) {
  526.         c->ssl->handshake_rejected = 1;
  527.         *ad = SSL_AD_UNRECOGNIZED_NAME;
  528.         return SSL_TLSEXT_ERR_ALERT_FATAL;
  529.     }

  530.     c->ssl->sni_accepted = 1;
  531.     return SSL_TLSEXT_ERR_OK;

  532. error:

  533.     *ad = SSL_AD_INTERNAL_ERROR;
  534.     return SSL_TLSEXT_ERR_ALERT_FATAL;
  535. }

  536. #endif


  537. #ifdef TLSEXT_TYPE_application_layer_protocol_negotiation

  538. static int
  539. ngx_stream_ssl_alpn_select(ngx_ssl_conn_t *ssl_conn, const unsigned char **out,
  540.     unsigned char *outlen, const unsigned char *in, unsigned int inlen,
  541.     void *arg)
  542. {
  543.     ngx_str_t         *alpn;
  544. #if (NGX_DEBUG)
  545.     unsigned int       i;
  546.     ngx_connection_t  *c;

  547.     c = ngx_ssl_get_connection(ssl_conn);

  548.     for (i = 0; i < inlen; i += in[i] + 1) {
  549.         ngx_log_debug2(NGX_LOG_DEBUG_STREAM, c->log, 0,
  550.                        "SSL ALPN supported by client: %*s",
  551.                        (size_t) in[i], &in[i + 1]);
  552.     }

  553. #endif

  554.     alpn = arg;

  555.     if (SSL_select_next_proto((unsigned char **) out, outlen, alpn->data,
  556.                               alpn->len, in, inlen)
  557.         != OPENSSL_NPN_NEGOTIATED)
  558.     {
  559.         return SSL_TLSEXT_ERR_ALERT_FATAL;
  560.     }

  561.     ngx_log_debug2(NGX_LOG_DEBUG_STREAM, c->log, 0,
  562.                    "SSL ALPN selected: %*s", (size_t) *outlen, *out);

  563.     return SSL_TLSEXT_ERR_OK;
  564. }

  565. #endif


  566. #ifdef SSL_R_CERT_CB_ERROR

  567. static int
  568. ngx_stream_ssl_certificate(ngx_ssl_conn_t *ssl_conn, void *arg)
  569. {
  570.     ngx_str_t                    cert, key;
  571.     ngx_uint_t                   i, nelts;
  572.     ngx_connection_t            *c;
  573.     ngx_stream_session_t        *s;
  574.     ngx_stream_ssl_srv_conf_t   *sscf;
  575.     ngx_stream_complex_value_t  *certs, *keys;

  576.     c = ngx_ssl_get_connection(ssl_conn);

  577.     if (c->ssl->handshaked) {
  578.         return 0;
  579.     }

  580.     s = c->data;

  581.     sscf = arg;

  582.     nelts = sscf->certificate_values->nelts;
  583.     certs = sscf->certificate_values->elts;
  584.     keys = sscf->certificate_key_values->elts;

  585.     for (i = 0; i < nelts; i++) {

  586.         if (ngx_stream_complex_value(s, &certs[i], &cert) != NGX_OK) {
  587.             return 0;
  588.         }

  589.         ngx_log_debug1(NGX_LOG_DEBUG_STREAM, c->log, 0,
  590.                        "ssl cert: \"%s\"", cert.data);

  591.         if (ngx_stream_complex_value(s, &keys[i], &key) != NGX_OK) {
  592.             return 0;
  593.         }

  594.         ngx_log_debug1(NGX_LOG_DEBUG_STREAM, c->log, 0,
  595.                        "ssl key: \"%s\"", key.data);

  596.         if (ngx_ssl_connection_certificate(c, c->pool, &cert, &key,
  597.                                            sscf->certificate_cache,
  598.                                            sscf->passwords)
  599.             != NGX_OK)
  600.         {
  601.             return 0;
  602.         }
  603.     }

  604.     return 1;
  605. }

  606. #endif


  607. static ngx_int_t
  608. ngx_stream_ssl_static_variable(ngx_stream_session_t *s,
  609.     ngx_stream_variable_value_t *v, uintptr_t data)
  610. {
  611.     ngx_ssl_variable_handler_pt  handler = (ngx_ssl_variable_handler_pt) data;

  612.     size_t     len;
  613.     ngx_str_t  str;

  614.     if (s->connection->ssl) {

  615.         (void) handler(s->connection, NULL, &str);

  616.         v->data = str.data;

  617.         for (len = 0; v->data[len]; len++) { /* void */ }

  618.         v->len = len;
  619.         v->valid = 1;
  620.         v->no_cacheable = 0;
  621.         v->not_found = 0;

  622.         return NGX_OK;
  623.     }

  624.     v->not_found = 1;

  625.     return NGX_OK;
  626. }


  627. static ngx_int_t
  628. ngx_stream_ssl_variable(ngx_stream_session_t *s,
  629.     ngx_stream_variable_value_t *v, uintptr_t data)
  630. {
  631.     ngx_ssl_variable_handler_pt  handler = (ngx_ssl_variable_handler_pt) data;

  632.     ngx_str_t  str;

  633.     if (s->connection->ssl) {

  634.         if (handler(s->connection, s->connection->pool, &str) != NGX_OK) {
  635.             return NGX_ERROR;
  636.         }

  637.         v->len = str.len;
  638.         v->data = str.data;

  639.         if (v->len) {
  640.             v->valid = 1;
  641.             v->no_cacheable = 0;
  642.             v->not_found = 0;

  643.             return NGX_OK;
  644.         }
  645.     }

  646.     v->not_found = 1;

  647.     return NGX_OK;
  648. }


  649. static ngx_int_t
  650. ngx_stream_ssl_add_variables(ngx_conf_t *cf)
  651. {
  652.     ngx_stream_variable_t  *var, *v;

  653.     for (v = ngx_stream_ssl_vars; v->name.len; v++) {
  654.         var = ngx_stream_add_variable(cf, &v->name, v->flags);
  655.         if (var == NULL) {
  656.             return NGX_ERROR;
  657.         }

  658.         var->get_handler = v->get_handler;
  659.         var->data = v->data;
  660.     }

  661.     return NGX_OK;
  662. }


  663. static void *
  664. ngx_stream_ssl_create_srv_conf(ngx_conf_t *cf)
  665. {
  666.     ngx_stream_ssl_srv_conf_t  *sscf;

  667.     sscf = ngx_pcalloc(cf->pool, sizeof(ngx_stream_ssl_srv_conf_t));
  668.     if (sscf == NULL) {
  669.         return NULL;
  670.     }

  671.     /*
  672.      * set by ngx_pcalloc():
  673.      *
  674.      *     sscf->protocols = 0;
  675.      *     sscf->certificate_values = NULL;
  676.      *     sscf->dhparam = { 0, NULL };
  677.      *     sscf->ecdh_curve = { 0, NULL };
  678.      *     sscf->client_certificate = { 0, NULL };
  679.      *     sscf->trusted_certificate = { 0, NULL };
  680.      *     sscf->crl = { 0, NULL };
  681.      *     sscf->alpn = { 0, NULL };
  682.      *     sscf->ciphers = { 0, NULL };
  683.      *     sscf->shm_zone = NULL;
  684.      *     sscf->ocsp_responder = { 0, NULL };
  685.      *     sscf->stapling_file = { 0, NULL };
  686.      *     sscf->stapling_responder = { 0, NULL };
  687.      */

  688.     sscf->handshake_timeout = NGX_CONF_UNSET_MSEC;
  689.     sscf->certificates = NGX_CONF_UNSET_PTR;
  690.     sscf->certificate_keys = NGX_CONF_UNSET_PTR;
  691.     sscf->certificate_cache = NGX_CONF_UNSET_PTR;
  692.     sscf->ech_files = NGX_CONF_UNSET_PTR;
  693.     sscf->passwords = NGX_CONF_UNSET_PTR;
  694.     sscf->conf_commands = NGX_CONF_UNSET_PTR;
  695.     sscf->prefer_server_ciphers = NGX_CONF_UNSET;
  696.     sscf->certificate_compression = NGX_CONF_UNSET;
  697.     sscf->reject_handshake = NGX_CONF_UNSET;
  698.     sscf->verify = NGX_CONF_UNSET_UINT;
  699.     sscf->verify_depth = NGX_CONF_UNSET_UINT;
  700.     sscf->builtin_session_cache = NGX_CONF_UNSET;
  701.     sscf->session_timeout = NGX_CONF_UNSET;
  702.     sscf->session_tickets = NGX_CONF_UNSET;
  703.     sscf->session_ticket_keys = NGX_CONF_UNSET_PTR;
  704.     sscf->ocsp = NGX_CONF_UNSET_UINT;
  705.     sscf->ocsp_cache_zone = NGX_CONF_UNSET_PTR;
  706.     sscf->stapling = NGX_CONF_UNSET;
  707.     sscf->stapling_verify = NGX_CONF_UNSET;

  708.     return sscf;
  709. }


  710. static char *
  711. ngx_stream_ssl_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child)
  712. {
  713.     ngx_stream_ssl_srv_conf_t *prev = parent;
  714.     ngx_stream_ssl_srv_conf_t *conf = child;

  715.     ngx_pool_cleanup_t  *cln;

  716.     ngx_conf_merge_msec_value(conf->handshake_timeout,
  717.                          prev->handshake_timeout, 60000);

  718.     ngx_conf_merge_value(conf->session_timeout,
  719.                          prev->session_timeout, 300);

  720.     ngx_conf_merge_value(conf->prefer_server_ciphers,
  721.                          prev->prefer_server_ciphers, 0);

  722.     ngx_conf_merge_value(conf->certificate_compression,
  723.                          prev->certificate_compression, 0);

  724.     ngx_conf_merge_value(conf->reject_handshake, prev->reject_handshake, 0);

  725.     ngx_conf_merge_bitmask_value(conf->protocols, prev->protocols,
  726.                          (NGX_CONF_BITMASK_SET|NGX_SSL_DEFAULT_PROTOCOLS));

  727.     ngx_conf_merge_uint_value(conf->verify, prev->verify, 0);
  728.     ngx_conf_merge_uint_value(conf->verify_depth, prev->verify_depth, 1);

  729.     ngx_conf_merge_ptr_value(conf->certificates, prev->certificates, NULL);
  730.     ngx_conf_merge_ptr_value(conf->certificate_keys, prev->certificate_keys,
  731.                          NULL);

  732.     ngx_conf_merge_ptr_value(conf->certificate_cache, prev->certificate_cache,
  733.                          NULL);

  734.     ngx_conf_merge_ptr_value(conf->ech_files, prev->ech_files, NULL);

  735.     ngx_conf_merge_ptr_value(conf->passwords, prev->passwords, NULL);

  736.     ngx_conf_merge_str_value(conf->dhparam, prev->dhparam, "");

  737.     ngx_conf_merge_str_value(conf->client_certificate, prev->client_certificate,
  738.                          "");
  739.     ngx_conf_merge_str_value(conf->trusted_certificate,
  740.                          prev->trusted_certificate, "");
  741.     ngx_conf_merge_str_value(conf->crl, prev->crl, "");
  742.     ngx_conf_merge_str_value(conf->alpn, prev->alpn, "");

  743.     ngx_conf_merge_str_value(conf->ecdh_curve, prev->ecdh_curve,
  744.                          NGX_DEFAULT_ECDH_CURVE);

  745.     ngx_conf_merge_str_value(conf->ciphers, prev->ciphers, NGX_DEFAULT_CIPHERS);

  746.     ngx_conf_merge_ptr_value(conf->conf_commands, prev->conf_commands, NULL);

  747.     ngx_conf_merge_uint_value(conf->ocsp, prev->ocsp, 0);
  748.     ngx_conf_merge_str_value(conf->ocsp_responder, prev->ocsp_responder, "");
  749.     ngx_conf_merge_ptr_value(conf->ocsp_cache_zone,
  750.                          prev->ocsp_cache_zone, NULL);

  751.     ngx_conf_merge_value(conf->stapling, prev->stapling, 0);
  752.     ngx_conf_merge_value(conf->stapling_verify, prev->stapling_verify, 0);
  753.     ngx_conf_merge_str_value(conf->stapling_file, prev->stapling_file, "");
  754.     ngx_conf_merge_str_value(conf->stapling_responder,
  755.                          prev->stapling_responder, "");

  756.     conf->ssl.log = cf->log;

  757.     if (conf->certificates) {

  758.         if (conf->certificate_keys == NULL
  759.             || conf->certificate_keys->nelts < conf->certificates->nelts)
  760.         {
  761.             ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  762.                           "no \"ssl_certificate_key\" is defined "
  763.                           "for certificate \"%V\"",
  764.                           ((ngx_str_t *) conf->certificates->elts)
  765.                           + conf->certificates->nelts - 1);
  766.             return NGX_CONF_ERROR;
  767.         }

  768.     } else if (!conf->reject_handshake) {
  769.         return NGX_CONF_OK;
  770.     }

  771.     if (ngx_ssl_create(&conf->ssl, conf->protocols, NULL) != NGX_OK) {
  772.         return NGX_CONF_ERROR;
  773.     }

  774.     cln = ngx_pool_cleanup_add(cf->pool, 0);
  775.     if (cln == NULL) {
  776.         ngx_ssl_cleanup_ctx(&conf->ssl);
  777.         return NGX_CONF_ERROR;
  778.     }

  779.     cln->handler = ngx_ssl_cleanup_ctx;
  780.     cln->data = &conf->ssl;

  781. #ifdef SSL_CTRL_SET_TLSEXT_HOSTNAME
  782.     {
  783.     static ngx_ssl_client_hello_arg cb = { ngx_stream_ssl_servername };

  784.     if (ngx_ssl_set_client_hello_callback(&conf->ssl, &cb) != NGX_OK) {
  785.         return NGX_CONF_ERROR;
  786.     }

  787.     SSL_CTX_set_tlsext_servername_callback(conf->ssl.ctx,
  788.                                            ngx_stream_ssl_servername);
  789.     }
  790. #endif

  791. #ifdef TLSEXT_TYPE_application_layer_protocol_negotiation
  792.     if (conf->alpn.len) {
  793.         SSL_CTX_set_alpn_select_cb(conf->ssl.ctx, ngx_stream_ssl_alpn_select,
  794.                                    &conf->alpn);
  795.     }
  796. #endif

  797.     if (ngx_ssl_ciphers(cf, &conf->ssl, &conf->ciphers,
  798.                         conf->prefer_server_ciphers)
  799.         != NGX_OK)
  800.     {
  801.         return NGX_CONF_ERROR;
  802.     }

  803.     if (ngx_stream_ssl_compile_certificates(cf, conf) != NGX_OK) {
  804.         return NGX_CONF_ERROR;
  805.     }

  806.     if (conf->certificate_values) {

  807. #ifdef SSL_R_CERT_CB_ERROR

  808.         /* install callback to lookup certificates */

  809.         SSL_CTX_set_cert_cb(conf->ssl.ctx, ngx_stream_ssl_certificate, conf);

  810. #else
  811.         ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  812.                       "variables in "
  813.                       "\"ssl_certificate\" and \"ssl_certificate_key\" "
  814.                       "directives are not supported on this platform");
  815.         return NGX_CONF_ERROR;
  816. #endif

  817.     } else if (conf->certificates) {

  818.         /* configure certificates */

  819.         if (ngx_ssl_certificates(cf, &conf->ssl, conf->certificates,
  820.                                  conf->certificate_keys, conf->passwords)
  821.             != NGX_OK)
  822.         {
  823.             return NGX_CONF_ERROR;
  824.         }

  825.         if (ngx_ssl_certificate_compression(cf, &conf->ssl,
  826.                                             conf->certificate_compression)
  827.             != NGX_OK)
  828.         {
  829.             return NGX_CONF_ERROR;
  830.         }
  831.     }

  832.     if (conf->verify) {

  833.         if (conf->verify != 3
  834.             && conf->client_certificate.len == 0
  835.             && conf->trusted_certificate.len == 0)
  836.         {
  837.             ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  838.                           "no ssl_client_certificate or "
  839.                           "ssl_trusted_certificate for ssl_verify_client");
  840.             return NGX_CONF_ERROR;
  841.         }

  842.         if (ngx_ssl_client_certificate(cf, &conf->ssl,
  843.                                        &conf->client_certificate,
  844.                                        conf->verify_depth)
  845.             != NGX_OK)
  846.         {
  847.             return NGX_CONF_ERROR;
  848.         }
  849.     }

  850.     if (ngx_ssl_trusted_certificate(cf, &conf->ssl,
  851.                                     &conf->trusted_certificate,
  852.                                     conf->verify_depth)
  853.         != NGX_OK)
  854.     {
  855.         return NGX_CONF_ERROR;
  856.     }

  857.     if (ngx_ssl_crl(cf, &conf->ssl, &conf->crl) != NGX_OK) {
  858.         return NGX_CONF_ERROR;
  859.     }

  860.     if (conf->ocsp) {

  861.         if (conf->verify == 3) {
  862.             ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  863.                           "\"ssl_ocsp\" is incompatible with "
  864.                           "\"ssl_verify_client optional_no_ca\"");
  865.             return NGX_CONF_ERROR;
  866.         }

  867.         if (ngx_ssl_ocsp(cf, &conf->ssl, &conf->ocsp_responder, conf->ocsp,
  868.                          conf->ocsp_cache_zone)
  869.             != NGX_OK)
  870.         {
  871.             return NGX_CONF_ERROR;
  872.         }
  873.     }

  874.     if (ngx_ssl_dhparam(cf, &conf->ssl, &conf->dhparam) != NGX_OK) {
  875.         return NGX_CONF_ERROR;
  876.     }

  877.     if (ngx_ssl_ech_files(cf, &conf->ssl, conf->ech_files) != NGX_OK) {
  878.         return NGX_CONF_ERROR;
  879.     }

  880.     if (ngx_ssl_ecdh_curve(cf, &conf->ssl, &conf->ecdh_curve) != NGX_OK) {
  881.         return NGX_CONF_ERROR;
  882.     }

  883.     ngx_conf_merge_value(conf->builtin_session_cache,
  884.                          prev->builtin_session_cache, NGX_SSL_NONE_SCACHE);

  885.     if (conf->shm_zone == NULL) {
  886.         conf->shm_zone = prev->shm_zone;
  887.     }

  888.     if (ngx_ssl_session_cache(&conf->ssl, &ngx_stream_ssl_sess_id_ctx,
  889.                               conf->certificates, conf->builtin_session_cache,
  890.                               conf->shm_zone, conf->session_timeout)
  891.         != NGX_OK)
  892.     {
  893.         return NGX_CONF_ERROR;
  894.     }

  895.     ngx_conf_merge_value(conf->session_tickets,
  896.                          prev->session_tickets, 1);

  897. #ifdef SSL_OP_NO_TICKET
  898.     if (!conf->session_tickets) {
  899.         SSL_CTX_set_options(conf->ssl.ctx, SSL_OP_NO_TICKET);
  900.     }
  901. #endif

  902.     ngx_conf_merge_ptr_value(conf->session_ticket_keys,
  903.                          prev->session_ticket_keys, NULL);

  904.     if (ngx_ssl_session_ticket_keys(cf, &conf->ssl, conf->session_ticket_keys)
  905.         != NGX_OK)
  906.     {
  907.         return NGX_CONF_ERROR;
  908.     }

  909.     if (conf->stapling) {

  910.         if (conf->certificate_compression) {
  911.             ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  912.                           "\"ssl_stapling\" is incompatible with "
  913.                           "\"ssl_certificate_compression\"");
  914.             return NGX_CONF_ERROR;
  915.         }

  916.         if (ngx_ssl_stapling(cf, &conf->ssl, &conf->stapling_file,
  917.                              &conf->stapling_responder, conf->stapling_verify)
  918.             != NGX_OK)
  919.         {
  920.             return NGX_CONF_ERROR;
  921.         }
  922.     }

  923.     if (ngx_ssl_conf_commands(cf, &conf->ssl, conf->conf_commands) != NGX_OK) {
  924.         return NGX_CONF_ERROR;
  925.     }

  926.     return NGX_CONF_OK;
  927. }


  928. static ngx_int_t
  929. ngx_stream_ssl_compile_certificates(ngx_conf_t *cf,
  930.     ngx_stream_ssl_srv_conf_t *conf)
  931. {
  932.     ngx_str_t                           *cert, *key;
  933.     ngx_uint_t                           i, nelts;
  934.     ngx_stream_complex_value_t          *cv;
  935.     ngx_stream_compile_complex_value_t   ccv;

  936.     if (conf->certificates == NULL) {
  937.         return NGX_OK;
  938.     }

  939.     cert = conf->certificates->elts;
  940.     key = conf->certificate_keys->elts;
  941.     nelts = conf->certificates->nelts;

  942.     for (i = 0; i < nelts; i++) {

  943.         if (ngx_stream_script_variables_count(&cert[i])) {
  944.             goto found;
  945.         }

  946.         if (ngx_stream_script_variables_count(&key[i])) {
  947.             goto found;
  948.         }
  949.     }

  950.     return NGX_OK;

  951. found:

  952.     conf->certificate_values = ngx_array_create(cf->pool, nelts,
  953.                                            sizeof(ngx_stream_complex_value_t));
  954.     if (conf->certificate_values == NULL) {
  955.         return NGX_ERROR;
  956.     }

  957.     conf->certificate_key_values = ngx_array_create(cf->pool, nelts,
  958.                                            sizeof(ngx_stream_complex_value_t));
  959.     if (conf->certificate_key_values == NULL) {
  960.         return NGX_ERROR;
  961.     }

  962.     for (i = 0; i < nelts; i++) {

  963.         cv = ngx_array_push(conf->certificate_values);
  964.         if (cv == NULL) {
  965.             return NGX_ERROR;
  966.         }

  967.         ngx_memzero(&ccv, sizeof(ngx_stream_compile_complex_value_t));

  968.         ccv.cf = cf;
  969.         ccv.value = &cert[i];
  970.         ccv.complex_value = cv;
  971.         ccv.zero = 1;

  972.         if (ngx_stream_compile_complex_value(&ccv) != NGX_OK) {
  973.             return NGX_ERROR;
  974.         }

  975.         cv = ngx_array_push(conf->certificate_key_values);
  976.         if (cv == NULL) {
  977.             return NGX_ERROR;
  978.         }

  979.         ngx_memzero(&ccv, sizeof(ngx_stream_compile_complex_value_t));

  980.         ccv.cf = cf;
  981.         ccv.value = &key[i];
  982.         ccv.complex_value = cv;
  983.         ccv.zero = 1;

  984.         if (ngx_stream_compile_complex_value(&ccv) != NGX_OK) {
  985.             return NGX_ERROR;
  986.         }
  987.     }

  988.     conf->passwords = ngx_ssl_preserve_passwords(cf, conf->passwords);
  989.     if (conf->passwords == NULL) {
  990.         return NGX_ERROR;
  991.     }

  992.     return NGX_OK;
  993. }


  994. static char *
  995. ngx_stream_ssl_certificate_cache(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
  996. {
  997.     ngx_stream_ssl_srv_conf_t *sscf = conf;

  998.     time_t       inactive, valid;
  999.     ngx_str_t   *value, s;
  1000.     ngx_int_t    max;
  1001.     ngx_uint_t   i;

  1002.     if (sscf->certificate_cache != NGX_CONF_UNSET_PTR) {
  1003.         return "is duplicate";
  1004.     }

  1005.     value = cf->args->elts;

  1006.     max = 0;
  1007.     inactive = 10;
  1008.     valid = 60;

  1009.     for (i = 1; i < cf->args->nelts; i++) {

  1010.         if (ngx_strncmp(value[i].data, "max=", 4) == 0) {

  1011.             max = ngx_atoi(value[i].data + 4, value[i].len - 4);
  1012.             if (max <= 0) {
  1013.                 goto failed;
  1014.             }

  1015.             continue;
  1016.         }

  1017.         if (ngx_strncmp(value[i].data, "inactive=", 9) == 0) {

  1018.             s.len = value[i].len - 9;
  1019.             s.data = value[i].data + 9;

  1020.             inactive = ngx_parse_time(&s, 1);
  1021.             if (inactive == (time_t) NGX_ERROR) {
  1022.                 goto failed;
  1023.             }

  1024.             continue;
  1025.         }

  1026.         if (ngx_strncmp(value[i].data, "valid=", 6) == 0) {

  1027.             s.len = value[i].len - 6;
  1028.             s.data = value[i].data + 6;

  1029.             valid = ngx_parse_time(&s, 1);
  1030.             if (valid == (time_t) NGX_ERROR) {
  1031.                 goto failed;
  1032.             }

  1033.             continue;
  1034.         }

  1035.         if (ngx_strcmp(value[i].data, "off") == 0) {

  1036.             sscf->certificate_cache = NULL;

  1037.             continue;
  1038.         }

  1039.     failed:

  1040.         ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1041.                            "invalid parameter \"%V\"", &value[i]);
  1042.         return NGX_CONF_ERROR;
  1043.     }

  1044.     if (sscf->certificate_cache == NULL) {
  1045.         return NGX_CONF_OK;
  1046.     }

  1047.     if (max == 0) {
  1048.         ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1049.                            "\"ssl_certificate_cache\" must have "
  1050.                            "the \"max\" parameter");
  1051.         return NGX_CONF_ERROR;
  1052.     }

  1053.     sscf->certificate_cache = ngx_ssl_cache_init(cf->pool, max, valid,
  1054.                                                  inactive);
  1055.     if (sscf->certificate_cache == NULL) {
  1056.         return NGX_CONF_ERROR;
  1057.     }

  1058.     return NGX_CONF_OK;
  1059. }


  1060. static char *
  1061. ngx_stream_ssl_password_file(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
  1062. {
  1063.     ngx_stream_ssl_srv_conf_t  *sscf = conf;

  1064.     ngx_str_t  *value;

  1065.     if (sscf->passwords != NGX_CONF_UNSET_PTR) {
  1066.         return "is duplicate";
  1067.     }

  1068.     value = cf->args->elts;

  1069.     sscf->passwords = ngx_ssl_read_password_file(cf, &value[1]);

  1070.     if (sscf->passwords == NULL) {
  1071.         return NGX_CONF_ERROR;
  1072.     }

  1073.     return NGX_CONF_OK;
  1074. }


  1075. static char *
  1076. ngx_stream_ssl_session_cache(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
  1077. {
  1078.     ngx_stream_ssl_srv_conf_t  *sscf = conf;

  1079.     size_t       len;
  1080.     ngx_str_t   *value, name, size;
  1081.     ngx_int_t    n;
  1082.     ngx_uint_t   i, j;

  1083.     value = cf->args->elts;

  1084.     for (i = 1; i < cf->args->nelts; i++) {

  1085.         if (ngx_strcmp(value[i].data, "off") == 0) {
  1086.             sscf->builtin_session_cache = NGX_SSL_NO_SCACHE;
  1087.             continue;
  1088.         }

  1089.         if (ngx_strcmp(value[i].data, "none") == 0) {
  1090.             sscf->builtin_session_cache = NGX_SSL_NONE_SCACHE;
  1091.             continue;
  1092.         }

  1093.         if (ngx_strcmp(value[i].data, "builtin") == 0) {
  1094.             sscf->builtin_session_cache = NGX_SSL_DFLT_BUILTIN_SCACHE;
  1095.             continue;
  1096.         }

  1097.         if (value[i].len > sizeof("builtin:") - 1
  1098.             && ngx_strncmp(value[i].data, "builtin:", sizeof("builtin:") - 1)
  1099.                == 0)
  1100.         {
  1101.             n = ngx_atoi(value[i].data + sizeof("builtin:") - 1,
  1102.                          value[i].len - (sizeof("builtin:") - 1));

  1103.             if (n == NGX_ERROR) {
  1104.                 goto invalid;
  1105.             }

  1106.             sscf->builtin_session_cache = n;

  1107.             continue;
  1108.         }

  1109.         if (value[i].len > sizeof("shared:") - 1
  1110.             && ngx_strncmp(value[i].data, "shared:", sizeof("shared:") - 1)
  1111.                == 0)
  1112.         {
  1113.             len = 0;

  1114.             for (j = sizeof("shared:") - 1; j < value[i].len; j++) {
  1115.                 if (value[i].data[j] == ':') {
  1116.                     break;
  1117.                 }

  1118.                 len++;
  1119.             }

  1120.             if (len == 0 || j == value[i].len) {
  1121.                 goto invalid;
  1122.             }

  1123.             name.len = len;
  1124.             name.data = value[i].data + sizeof("shared:") - 1;

  1125.             size.len = value[i].len - j - 1;
  1126.             size.data = name.data + len + 1;

  1127.             n = ngx_parse_size(&size);

  1128.             if (n == NGX_ERROR) {
  1129.                 goto invalid;
  1130.             }

  1131.             if (n < (ngx_int_t) (8 * ngx_pagesize)) {
  1132.                 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1133.                                    "session cache \"%V\" is too small",
  1134.                                    &value[i]);

  1135.                 return NGX_CONF_ERROR;
  1136.             }

  1137.             sscf->shm_zone = ngx_shared_memory_add(cf, &name, n,
  1138.                                                    &ngx_stream_ssl_module);
  1139.             if (sscf->shm_zone == NULL) {
  1140.                 return NGX_CONF_ERROR;
  1141.             }

  1142.             sscf->shm_zone->init = ngx_ssl_session_cache_init;

  1143.             continue;
  1144.         }

  1145.         goto invalid;
  1146.     }

  1147.     if (sscf->shm_zone && sscf->builtin_session_cache == NGX_CONF_UNSET) {
  1148.         sscf->builtin_session_cache = NGX_SSL_NO_BUILTIN_SCACHE;
  1149.     }

  1150.     return NGX_CONF_OK;

  1151. invalid:

  1152.     ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1153.                        "invalid session cache \"%V\"", &value[i]);

  1154.     return NGX_CONF_ERROR;
  1155. }


  1156. static char *
  1157. ngx_stream_ssl_ocsp_cache(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
  1158. {
  1159.     ngx_stream_ssl_srv_conf_t *sscf = conf;

  1160.     size_t       len;
  1161.     ngx_int_t    n;
  1162.     ngx_str_t   *value, name, size;
  1163.     ngx_uint_t   j;

  1164.     if (sscf->ocsp_cache_zone != NGX_CONF_UNSET_PTR) {
  1165.         return "is duplicate";
  1166.     }

  1167.     value = cf->args->elts;

  1168.     if (ngx_strcmp(value[1].data, "off") == 0) {
  1169.         sscf->ocsp_cache_zone = NULL;
  1170.         return NGX_CONF_OK;
  1171.     }

  1172.     if (value[1].len <= sizeof("shared:") - 1
  1173.         || ngx_strncmp(value[1].data, "shared:", sizeof("shared:") - 1) != 0)
  1174.     {
  1175.         goto invalid;
  1176.     }

  1177.     len = 0;

  1178.     for (j = sizeof("shared:") - 1; j < value[1].len; j++) {
  1179.         if (value[1].data[j] == ':') {
  1180.             break;
  1181.         }

  1182.         len++;
  1183.     }

  1184.     if (len == 0 || j == value[1].len) {
  1185.         goto invalid;
  1186.     }

  1187.     name.len = len;
  1188.     name.data = value[1].data + sizeof("shared:") - 1;

  1189.     size.len = value[1].len - j - 1;
  1190.     size.data = name.data + len + 1;

  1191.     n = ngx_parse_size(&size);

  1192.     if (n == NGX_ERROR) {
  1193.         goto invalid;
  1194.     }

  1195.     if (n < (ngx_int_t) (8 * ngx_pagesize)) {
  1196.         ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1197.                            "OCSP cache \"%V\" is too small", &value[1]);

  1198.         return NGX_CONF_ERROR;
  1199.     }

  1200.     sscf->ocsp_cache_zone = ngx_shared_memory_add(cf, &name, n,
  1201.                                                   &ngx_stream_ssl_module_ctx);
  1202.     if (sscf->ocsp_cache_zone == NULL) {
  1203.         return NGX_CONF_ERROR;
  1204.     }

  1205.     sscf->ocsp_cache_zone->init = ngx_ssl_ocsp_cache_init;

  1206.     return NGX_CONF_OK;

  1207. invalid:

  1208.     ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1209.                        "invalid OCSP cache \"%V\"", &value[1]);

  1210.     return NGX_CONF_ERROR;
  1211. }


  1212. static char *
  1213. ngx_stream_ssl_alpn(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
  1214. {
  1215. #ifdef TLSEXT_TYPE_application_layer_protocol_negotiation

  1216.     ngx_stream_ssl_srv_conf_t  *sscf = conf;

  1217.     u_char      *p;
  1218.     size_t       len;
  1219.     ngx_str_t   *value;
  1220.     ngx_uint_t   i;

  1221.     if (sscf->alpn.len) {
  1222.         return "is duplicate";
  1223.     }

  1224.     value = cf->args->elts;

  1225.     len = 0;

  1226.     for (i = 1; i < cf->args->nelts; i++) {

  1227.         if (value[i].len > 255) {
  1228.             return "protocol too long";
  1229.         }

  1230.         len += value[i].len + 1;
  1231.     }

  1232.     sscf->alpn.data = ngx_pnalloc(cf->pool, len);
  1233.     if (sscf->alpn.data == NULL) {
  1234.         return NGX_CONF_ERROR;
  1235.     }

  1236.     p = sscf->alpn.data;

  1237.     for (i = 1; i < cf->args->nelts; i++) {
  1238.         *p++ = value[i].len;
  1239.         p = ngx_cpymem(p, value[i].data, value[i].len);
  1240.     }

  1241.     sscf->alpn.len = len;

  1242.     return NGX_CONF_OK;

  1243. #else
  1244.     ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
  1245.                        "the \"ssl_alpn\" directive requires OpenSSL "
  1246.                        "with ALPN support");
  1247.     return NGX_CONF_ERROR;
  1248. #endif
  1249. }


  1250. static char *
  1251. ngx_stream_ssl_conf_command_check(ngx_conf_t *cf, void *post, void *data)
  1252. {
  1253. #ifndef SSL_CONF_FLAG_FILE
  1254.     return "is not supported on this platform";
  1255. #else
  1256.     return NGX_CONF_OK;
  1257. #endif
  1258. }


  1259. static ngx_int_t
  1260. ngx_stream_ssl_init(ngx_conf_t *cf)
  1261. {
  1262.     ngx_uint_t                     a, p, s;
  1263.     ngx_stream_handler_pt         *h;
  1264.     ngx_stream_conf_addr_t        *addr;
  1265.     ngx_stream_conf_port_t        *port;
  1266.     ngx_stream_ssl_srv_conf_t     *sscf;
  1267.     ngx_stream_core_srv_conf_t   **cscfp, *cscf;
  1268.     ngx_stream_core_main_conf_t   *cmcf;

  1269.     cmcf = ngx_stream_conf_get_module_main_conf(cf, ngx_stream_core_module);
  1270.     cscfp = cmcf->servers.elts;

  1271.     for (s = 0; s < cmcf->servers.nelts; s++) {

  1272.         sscf = cscfp[s]->ctx->srv_conf[ngx_stream_ssl_module.ctx_index];

  1273.         if (sscf->ssl.ctx == NULL) {
  1274.             continue;
  1275.         }

  1276.         cscf = cscfp[s]->ctx->srv_conf[ngx_stream_core_module.ctx_index];

  1277.         if (sscf->stapling) {
  1278.             if (ngx_ssl_stapling_resolver(cf, &sscf->ssl, cscf->resolver,
  1279.                                           cscf->resolver_timeout)
  1280.                 != NGX_OK)
  1281.             {
  1282.                 return NGX_ERROR;
  1283.             }
  1284.         }

  1285.         if (sscf->ocsp) {
  1286.             if (ngx_ssl_ocsp_resolver(cf, &sscf->ssl, cscf->resolver,
  1287.                                       cscf->resolver_timeout)
  1288.                 != NGX_OK)
  1289.             {
  1290.                 return NGX_ERROR;
  1291.             }
  1292.         }
  1293.     }

  1294.     h = ngx_array_push(&cmcf->phases[NGX_STREAM_SSL_PHASE].handlers);
  1295.     if (h == NULL) {
  1296.         return NGX_ERROR;
  1297.     }

  1298.     *h = ngx_stream_ssl_handler;

  1299.     if (cmcf->ports == NULL) {
  1300.         return NGX_OK;
  1301.     }

  1302.     port = cmcf->ports->elts;
  1303.     for (p = 0; p < cmcf->ports->nelts; p++) {

  1304.         addr = port[p].addrs.elts;
  1305.         for (a = 0; a < port[p].addrs.nelts; a++) {

  1306.             if (!addr[a].opt.ssl) {
  1307.                 continue;
  1308.             }

  1309.             cscf = addr[a].default_server;
  1310.             sscf = cscf->ctx->srv_conf[ngx_stream_ssl_module.ctx_index];

  1311.             if (sscf->certificates) {
  1312.                 continue;
  1313.             }

  1314.             if (!sscf->reject_handshake) {
  1315.                 ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  1316.                               "no \"ssl_certificate\" is defined for "
  1317.                               "the \"listen ... ssl\" directive in %s:%ui",
  1318.                               cscf->file_name, cscf->line);
  1319.                 return NGX_ERROR;
  1320.             }

  1321.             /*
  1322.              * if no certificates are defined in the default server,
  1323.              * check all non-default server blocks
  1324.              */

  1325.             cscfp = addr[a].servers.elts;
  1326.             for (s = 0; s < addr[a].servers.nelts; s++) {

  1327.                 cscf = cscfp[s];
  1328.                 sscf = cscf->ctx->srv_conf[ngx_stream_ssl_module.ctx_index];

  1329.                 if (sscf->certificates || sscf->reject_handshake) {
  1330.                     continue;
  1331.                 }

  1332.                 ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
  1333.                               "no \"ssl_certificate\" is defined for "
  1334.                               "the \"listen ... ssl\" directive in %s:%ui",
  1335.                               cscf->file_name, cscf->line);
  1336.                 return NGX_ERROR;
  1337.             }
  1338.         }
  1339.     }

  1340.     return NGX_OK;
  1341. }