Quellcode durchsuchen

Add callback to allow OCSP stapling

Tim Rühsen vor 6 Jahren
Ursprung
Commit
3751044dc8
5 geänderte Dateien mit 88 neuen und 4 gelöschten Zeilen
  1. 4 0
      ChangeLog
  2. 13 0
      doc/libmicrohttpd.texi
  3. 20 3
      src/include/microhttpd.h
  4. 43 1
      src/microhttpd/daemon.c
  5. 8 0
      src/microhttpd/internal.h

+ 4 - 0
ChangeLog

@@ -1,3 +1,7 @@
+Tue Jul 16 19:56:14 CEST 2019
+	Add MHD_OPTION_HTTPS_CERT_CALLBACK2 to allow OCSP stapling
+   and MHD_FEATURE_HTTPS_CERT_CALLBACK2 to check for. -TR
+
 Fri Jul 05 2019 22:30:40 MSK
 	Releasing libmicrohttpd 0.9.65. -EG
 

+ 13 - 0
doc/libmicrohttpd.texi

@@ -892,6 +892,19 @@ information provided.  The callback is expected to access the SNI data
 using gnutls_server_name_get().  Using this option requires GnuTLS 3.0
 or higher.
 
+@item MHD_OPTION_HTTPS_CERT_CALLBACK2
+@cindex SSL
+@cindex TLS
+@cindex SNI
+@cindex OCSP
+Use a callback to determine which X.509 certificate should be
+used for a given HTTPS connection.  This option should be
+followed by a argument of type `gnutls_certificate_retrieve_function3 *`.
+This option provides an
+alternative/extension to #MHD_OPTION_HTTPS_CERT_CALLBACK.
+You must use this version if you want to use OCSP stapling.
+Using this option requires GnuTLS 3.6.3 or higher.
+
 @item MHD_OPTION_GNUTLS_PSK_CRED_HANDLER
 @cindex SSL
 @cindex TLS

+ 20 - 3
src/include/microhttpd.h

@@ -132,7 +132,7 @@ typedef intptr_t ssize_t;
  * Current version of the library.
  * 0x01093001 = 1.9.30-1.
  */
-#define MHD_VERSION 0x00096501
+#define MHD_VERSION 0x00096502
 
 /**
  * MHD-internal return code for "YES".
@@ -1646,7 +1646,18 @@ enum MHD_OPTION
    * gnutls_psk_set_server_credentials_function. It is used to
    * retrieve the shared key for a given username.
    */
-  MHD_OPTION_GNUTLS_PSK_CRED_HANDLER = 30
+  MHD_OPTION_GNUTLS_PSK_CRED_HANDLER = 30,
+
+  /**
+   * Use a callback to determine which X.509 certificate should be
+   * used for a given HTTPS connection.  This option should be
+   * followed by a argument of type `gnutls_certificate_retrieve_function3 *`.
+   * This option provides an
+   * alternative/extension to #MHD_OPTION_HTTPS_CERT_CALLBACK.
+	* You must use this version if you want to use OCSP stapling.
+   * Using this option requires GnuTLS 3.6.3 or higher.
+   */
+  MHD_OPTION_HTTPS_CERT_CALLBACK2 = 31
 };
 
 
@@ -3927,7 +3938,13 @@ enum MHD_FEATURE
   /**
    * Get whether MHD supports threads.
    */
-  MHD_FEATURE_THREADS
+  MHD_FEATURE_THREADS = 22,
+
+  /**
+   * Get whether option #MHD_OPTION_HTTPS_CERT_CALLBACK2 is
+   * supported.
+   */
+  MHD_FEATURE_HTTPS_CERT_CALLBACK2 = 23
 };
 
 

+ 43 - 1
src/microhttpd/daemon.c

@@ -546,6 +546,14 @@ MHD_init_daemon_certificate (struct MHD_Daemon *daemon)
                                                  daemon->cert_callback);
     }
 #endif
+#if GNUTLS_VERSION_NUMBER >= 0x030603
+  else if (NULL != daemon->cert_callback2)
+    {
+      gnutls_certificate_set_retrieve_function3 (daemon->x509_cred,
+                                                 daemon->cert_callback2);
+    }
+#endif
+
   if (NULL != daemon->https_mem_trust)
     {
       size_t paramlen;
@@ -634,6 +642,10 @@ MHD_init_daemon_certificate (struct MHD_Daemon *daemon)
   if (NULL != daemon->cert_callback)
     return 0;
 #endif
+#if GNUTLS_VERSION_NUMBER >= 0x030603
+  else if (NULL != daemon->cert_callback2)
+    return 0;
+#endif
 #ifdef HAVE_MESSAGES
   MHD_DLOG (daemon,
             "You need to specify a certificate and key location\n");
@@ -2540,7 +2552,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
 #if (GNUTLS_VERSION_NUMBER+0 >= 0x030605)
       if (0 != (daemon->options & MHD_USE_INSECURE_TLS_EARLY_DATA))
 	flags |= GNUTLS_ENABLE_EARLY_DATA;
-#endif      
+#endif
       connection->tls_state = MHD_TLS_CONN_INIT;
       MHD_set_https_callbacks (connection);
       gnutls_init (&connection->tls_session,
@@ -4930,6 +4942,9 @@ parse_options_va (struct MHD_Daemon *daemon,
 #if GNUTLS_VERSION_MAJOR >= 3
   gnutls_certificate_retrieve_function2 *pgcrf;
 #endif
+#if GNUTLS_VERSION_NUMBER >= 0x030603
+  gnutls_certificate_retrieve_function3 *pgcrf2;
+#endif
 #endif /* HTTPS_SUPPORT */
 
   while (MHD_OPTION_END != (opt = (enum MHD_OPTION) va_arg (ap, int)))
@@ -5195,6 +5210,26 @@ parse_options_va (struct MHD_Daemon *daemon,
                         opt);
 #endif
           break;
+#endif
+        case MHD_OPTION_HTTPS_CERT_CALLBACK2:
+#if GNUTLS_VERSION_NUMBER < 0x030603
+#ifdef HAVE_MESSAGES
+          MHD_DLOG (daemon,
+                    _("MHD_OPTION_HTTPS_CERT_CALLBACK2 requires building MHD with GnuTLS >= 3.6.3\n"));
+#endif
+          return MHD_NO;
+#else
+          pgcrf2 = va_arg (ap,
+                          gnutls_certificate_retrieve_function3 *);
+          if (0 != (daemon->options & MHD_USE_TLS))
+            daemon->cert_callback2 = pgcrf2;
+          else
+#ifdef HAVE_MESSAGES
+              MHD_DLOG (daemon,
+                        _("MHD HTTPS option %d passed to MHD but MHD_USE_TLS not set\n"),
+                        opt);
+#endif
+          break;
 #endif
 #endif /* HTTPS_SUPPORT */
 #ifdef DAUTH_SUPPORT
@@ -5347,6 +5382,7 @@ parse_options_va (struct MHD_Daemon *daemon,
 		case MHD_OPTION_HTTPS_PRIORITIES:
 		case MHD_OPTION_ARRAY:
                 case MHD_OPTION_HTTPS_CERT_CALLBACK:
+                case MHD_OPTION_HTTPS_CERT_CALLBACK2:
 		  if (MHD_YES != parse_options (daemon,
 						servaddr,
 						opt,
@@ -6960,6 +6996,12 @@ MHD_is_feature_supported(enum MHD_FEATURE feature)
 #else  /* !HTTPS_SUPPORT || GNUTLS_VERSION_MAJOR < 3 */
       return MHD_NO;
 #endif /* !HTTPS_SUPPORT || GNUTLS_VERSION_MAJOR < 3 */
+    case MHD_FEATURE_HTTPS_CERT_CALLBACK2:
+#if defined(HTTPS_SUPPORT) && GNUTLS_VERSION_NUMBER >= 0x030603
+      return MHD_YES;
+#else  /* !HTTPS_SUPPORT || GNUTLS_VERSION_NUMBER < 0x030603 */
+      return MHD_NO;
+#endif /* !HTTPS_SUPPORT || GNUTLS_VERSION_NUMBER < 0x030603 */
     case MHD_FEATURE_IPv6:
 #ifdef HAVE_INET6
       return MHD_YES;

+ 8 - 0
src/microhttpd/internal.h

@@ -1670,6 +1670,14 @@ struct MHD_Daemon
   void *cred_callback_cls;
 #endif
 
+#if GNUTLS_VERSION_NUMBER >= 0x030603
+  /**
+   * Function that can be used to obtain the certificate.  Needed
+   * for OCSP stapling support.  See #MHD_OPTION_HTTPS_CERT_CALLBACK2.
+   */
+  gnutls_certificate_retrieve_function3 *cert_callback2;
+#endif
+
   /**
    * Pointer to our SSL/TLS key (in ASCII) in memory.
    */